mirror of
https://github.com/microsoft/PowerToys.git
synced 2025-12-16 11:48:06 +01:00
[FancyZones]Monitor identification (#19077)
* moved monitors identifying * changed device id * get wmi info * convert old data * save/load applied layouts * changed monitor identification * id comparison * save/load app zone history * moved com and security init * update ids in editor * lib fix * updated tests * changed comparison * tests * updated id comparison * updated log * moved definition * spell check * resolve conflicts * refactoring * update serial numbers if possible
This commit is contained in:
3
.github/actions/spell-check/expect.txt
vendored
3
.github/actions/spell-check/expect.txt
vendored
@@ -667,6 +667,8 @@ globals
|
|||||||
GNumber
|
GNumber
|
||||||
google
|
google
|
||||||
GPTR
|
GPTR
|
||||||
|
GSM
|
||||||
|
gsuberland
|
||||||
gtm
|
gtm
|
||||||
gui
|
gui
|
||||||
guiddef
|
guiddef
|
||||||
@@ -2103,6 +2105,7 @@ Udp
|
|||||||
uefi
|
uefi
|
||||||
UHash
|
UHash
|
||||||
UIA
|
UIA
|
||||||
|
uid
|
||||||
Uid
|
Uid
|
||||||
uint
|
uint
|
||||||
uintptr
|
uintptr
|
||||||
|
|||||||
@@ -110,7 +110,7 @@
|
|||||||
<Link>
|
<Link>
|
||||||
<SubSystem>Windows</SubSystem>
|
<SubSystem>Windows</SubSystem>
|
||||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||||
<AdditionalDependencies>shcore.lib;shlwapi.lib;DbgHelp.lib;uxtheme.lib;dwmapi.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
<AdditionalDependencies>shcore.lib;shlwapi.lib;DbgHelp.lib;uxtheme.lib;dwmapi.lib;wbemuuid.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
||||||
</Link>
|
</Link>
|
||||||
</ItemDefinitionGroup>
|
</ItemDefinitionGroup>
|
||||||
<ItemDefinitionGroup Condition="'$(Configuration)'=='Release'">
|
<ItemDefinitionGroup Condition="'$(Configuration)'=='Release'">
|
||||||
@@ -128,7 +128,7 @@
|
|||||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||||
<OptimizeReferences>true</OptimizeReferences>
|
<OptimizeReferences>true</OptimizeReferences>
|
||||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||||
<AdditionalDependencies>shcore.lib;shlwapi.lib;DbgHelp.lib;uxtheme.lib;dwmapi.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
<AdditionalDependencies>shcore.lib;shlwapi.lib;DbgHelp.lib;uxtheme.lib;dwmapi.lib;wbemuuid.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
||||||
</Link>
|
</Link>
|
||||||
</ItemDefinitionGroup>
|
</ItemDefinitionGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|||||||
@@ -2,6 +2,7 @@
|
|||||||
#include "EditorParameters.h"
|
#include "EditorParameters.h"
|
||||||
|
|
||||||
#include <FancyZonesLib/FancyZonesWindowProperties.h>
|
#include <FancyZonesLib/FancyZonesWindowProperties.h>
|
||||||
|
#include <FancyZonesLib/MonitorUtils.h>
|
||||||
#include <FancyZonesLib/on_thread_executor.h>
|
#include <FancyZonesLib/on_thread_executor.h>
|
||||||
#include <FancyZonesLib/Settings.h>
|
#include <FancyZonesLib/Settings.h>
|
||||||
#include <FancyZonesLib/VirtualDesktop.h>
|
#include <FancyZonesLib/VirtualDesktop.h>
|
||||||
@@ -22,6 +23,8 @@ namespace JsonUtils
|
|||||||
struct MonitorInfo
|
struct MonitorInfo
|
||||||
{
|
{
|
||||||
std::wstring monitorName;
|
std::wstring monitorName;
|
||||||
|
std::wstring monitorInstanceId;
|
||||||
|
std::wstring monitorSerialNumber;
|
||||||
std::wstring virtualDesktop;
|
std::wstring virtualDesktop;
|
||||||
int dpi;
|
int dpi;
|
||||||
int top;
|
int top;
|
||||||
@@ -37,6 +40,8 @@ namespace JsonUtils
|
|||||||
json::JsonObject result{};
|
json::JsonObject result{};
|
||||||
|
|
||||||
result.SetNamedValue(NonLocalizable::EditorParametersIds::MonitorNameId, json::value(monitor.monitorName));
|
result.SetNamedValue(NonLocalizable::EditorParametersIds::MonitorNameId, json::value(monitor.monitorName));
|
||||||
|
result.SetNamedValue(NonLocalizable::EditorParametersIds::MonitorInstanceId, json::value(monitor.monitorInstanceId));
|
||||||
|
result.SetNamedValue(NonLocalizable::EditorParametersIds::MonitorSerialNumberId, json::value(monitor.monitorSerialNumber));
|
||||||
result.SetNamedValue(NonLocalizable::EditorParametersIds::VirtualDesktopId, json::value(monitor.virtualDesktop));
|
result.SetNamedValue(NonLocalizable::EditorParametersIds::VirtualDesktopId, json::value(monitor.virtualDesktop));
|
||||||
result.SetNamedValue(NonLocalizable::EditorParametersIds::Dpi, json::value(monitor.dpi));
|
result.SetNamedValue(NonLocalizable::EditorParametersIds::Dpi, json::value(monitor.dpi));
|
||||||
result.SetNamedValue(NonLocalizable::EditorParametersIds::TopCoordinate, json::value(monitor.top));
|
result.SetNamedValue(NonLocalizable::EditorParametersIds::TopCoordinate, json::value(monitor.top));
|
||||||
@@ -82,7 +87,7 @@ bool EditorParameters::Save() noexcept
|
|||||||
const auto virtualDesktopIdStr = FancyZonesUtils::GuidToString(VirtualDesktop::instance().GetCurrentVirtualDesktopId());
|
const auto virtualDesktopIdStr = FancyZonesUtils::GuidToString(VirtualDesktop::instance().GetCurrentVirtualDesktopId());
|
||||||
if (!virtualDesktopIdStr)
|
if (!virtualDesktopIdStr)
|
||||||
{
|
{
|
||||||
Logger::error(L"Save editor params: no virtual desktop id");
|
Logger::error(L"Save editor params: invalid virtual desktop id");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -124,13 +129,7 @@ bool EditorParameters::Save() noexcept
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// device id map for correct device ids
|
auto monitors = MonitorUtils::IdentifyMonitors();
|
||||||
std::unordered_map<std::wstring, DWORD> displayDeviceIdxMap;
|
|
||||||
|
|
||||||
std::vector<std::pair<HMONITOR, MONITORINFOEX>> allMonitors;
|
|
||||||
dpiUnawareThread.submit(OnThreadExecutor::task_t{ [&]() {
|
|
||||||
allMonitors = FancyZonesUtils::GetAllMonitorInfo<&MONITORINFOEX::rcWork>();
|
|
||||||
} }).wait();
|
|
||||||
|
|
||||||
HMONITOR targetMonitor{};
|
HMONITOR targetMonitor{};
|
||||||
if (FancyZonesSettings::settings().use_cursorpos_editor_startupscreen)
|
if (FancyZonesSettings::settings().use_cursorpos_editor_startupscreen)
|
||||||
@@ -150,21 +149,29 @@ bool EditorParameters::Save() noexcept
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
for (auto& monitorData : allMonitors)
|
for (auto& monitorData : monitors)
|
||||||
{
|
{
|
||||||
HMONITOR monitor = monitorData.first;
|
HMONITOR monitor = monitorData.monitor;
|
||||||
auto monitorInfo = monitorData.second;
|
|
||||||
|
MONITORINFOEX monitorInfo{};
|
||||||
|
dpiUnawareThread.submit(OnThreadExecutor::task_t{ [&] {
|
||||||
|
monitorInfo.cbSize = sizeof(monitorInfo);
|
||||||
|
if (!GetMonitorInfo(monitor, &monitorInfo))
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
} }).wait();
|
||||||
|
|
||||||
JsonUtils::MonitorInfo monitorJson;
|
JsonUtils::MonitorInfo monitorJson;
|
||||||
|
|
||||||
std::wstring deviceId = FancyZonesUtils::GetDisplayDeviceId(monitorInfo.szDevice, displayDeviceIdxMap);
|
|
||||||
|
|
||||||
if (monitor == targetMonitor)
|
if (monitor == targetMonitor)
|
||||||
{
|
{
|
||||||
monitorJson.isSelected = true; /* Is monitor selected for the main editor window opening */
|
monitorJson.isSelected = true; /* Is monitor selected for the main editor window opening */
|
||||||
}
|
}
|
||||||
|
|
||||||
monitorJson.monitorName = FancyZonesUtils::TrimDeviceId(deviceId);
|
monitorJson.monitorName = monitorData.deviceId.id;
|
||||||
|
monitorJson.monitorInstanceId = monitorData.deviceId.instanceId;
|
||||||
|
monitorJson.monitorSerialNumber = monitorData.serialNumber;
|
||||||
monitorJson.virtualDesktop = virtualDesktopIdStr.value();
|
monitorJson.virtualDesktop = virtualDesktopIdStr.value();
|
||||||
|
|
||||||
UINT dpi = 0;
|
UINT dpi = 0;
|
||||||
|
|||||||
@@ -6,6 +6,8 @@ namespace NonLocalizable
|
|||||||
{
|
{
|
||||||
const static wchar_t* Dpi = L"dpi";
|
const static wchar_t* Dpi = L"dpi";
|
||||||
const static wchar_t* MonitorNameId = L"monitor";
|
const static wchar_t* MonitorNameId = L"monitor";
|
||||||
|
const static wchar_t* MonitorInstanceId = L"monitor-instance-id";
|
||||||
|
const static wchar_t* MonitorSerialNumberId = L"monitor-serial-number";
|
||||||
const static wchar_t* VirtualDesktopId = L"virtual-desktop";
|
const static wchar_t* VirtualDesktopId = L"virtual-desktop";
|
||||||
const static wchar_t* TopCoordinate = L"top-coordinate";
|
const static wchar_t* TopCoordinate = L"top-coordinate";
|
||||||
const static wchar_t* LeftCoordinate = L"left-coordinate";
|
const static wchar_t* LeftCoordinate = L"left-coordinate";
|
||||||
|
|||||||
@@ -146,7 +146,7 @@ public:
|
|||||||
|
|
||||||
LRESULT WndProc(HWND, UINT, WPARAM, LPARAM) noexcept;
|
LRESULT WndProc(HWND, UINT, WPARAM, LPARAM) noexcept;
|
||||||
void OnDisplayChange(DisplayChangeType changeType) noexcept;
|
void OnDisplayChange(DisplayChangeType changeType) noexcept;
|
||||||
void AddWorkArea(HMONITOR monitor, const std::wstring& deviceId) noexcept;
|
void AddWorkArea(HMONITOR monitor, const FancyZonesDataTypes::WorkAreaId& id) noexcept;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
static LRESULT CALLBACK s_WndProc(HWND, UINT, WPARAM, LPARAM) noexcept;
|
static LRESULT CALLBACK s_WndProc(HWND, UINT, WPARAM, LPARAM) noexcept;
|
||||||
@@ -250,6 +250,22 @@ FancyZones::Run() noexcept
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Initialize COM. Needed for WMI monitor identifying
|
||||||
|
HRESULT comInitHres = CoInitializeEx(0, COINIT_MULTITHREADED);
|
||||||
|
if (FAILED(comInitHres))
|
||||||
|
{
|
||||||
|
Logger::error(L"Failed to initialize COM library. {}", get_last_error_or_default(comInitHres));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Initialize security. Needed for WMI monitor identifying
|
||||||
|
HRESULT comSecurityInitHres = CoInitializeSecurity(NULL, -1, NULL, NULL, RPC_C_AUTHN_LEVEL_DEFAULT, RPC_C_IMP_LEVEL_IMPERSONATE, NULL, EOAC_NONE, NULL);
|
||||||
|
if (FAILED(comSecurityInitHres))
|
||||||
|
{
|
||||||
|
Logger::error(L"Failed to initialize security. {}", get_last_error_or_default(comSecurityInitHres));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
m_dpiUnawareThread.submit(OnThreadExecutor::task_t{ [] {
|
m_dpiUnawareThread.submit(OnThreadExecutor::task_t{ [] {
|
||||||
SetThreadDpiAwarenessContext(DPI_AWARENESS_CONTEXT_UNAWARE);
|
SetThreadDpiAwarenessContext(DPI_AWARENESS_CONTEXT_UNAWARE);
|
||||||
SetThreadDpiHostingBehavior(DPI_HOSTING_BEHAVIOR_MIXED);
|
SetThreadDpiHostingBehavior(DPI_HOSTING_BEHAVIOR_MIXED);
|
||||||
@@ -278,6 +294,8 @@ FancyZones::Destroy() noexcept
|
|||||||
DestroyWindow(m_window);
|
DestroyWindow(m_window);
|
||||||
m_window = nullptr;
|
m_window = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
CoUninitialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
// IFancyZonesCallback
|
// IFancyZonesCallback
|
||||||
@@ -674,6 +692,11 @@ void FancyZones::OnDisplayChange(DisplayChangeType changeType) noexcept
|
|||||||
if (changeType == DisplayChangeType::Initialization)
|
if (changeType == DisplayChangeType::Initialization)
|
||||||
{
|
{
|
||||||
RegisterVirtualDesktopUpdates();
|
RegisterVirtualDesktopUpdates();
|
||||||
|
|
||||||
|
// id format of applied-layouts and app-zone-history was changed in 0.60
|
||||||
|
auto monitors = MonitorUtils::IdentifyMonitors();
|
||||||
|
AppliedLayouts::instance().AdjustWorkAreaIds(monitors);
|
||||||
|
AppZoneHistory::instance().AdjustWorkAreaIds(monitors);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -689,7 +712,7 @@ void FancyZones::OnDisplayChange(DisplayChangeType changeType) noexcept
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void FancyZones::AddWorkArea(HMONITOR monitor, const std::wstring& deviceId) noexcept
|
void FancyZones::AddWorkArea(HMONITOR monitor, const FancyZonesDataTypes::WorkAreaId& id) noexcept
|
||||||
{
|
{
|
||||||
if (m_workAreaHandler.IsNewWorkArea(VirtualDesktop::instance().GetCurrentVirtualDesktopId(), monitor))
|
if (m_workAreaHandler.IsNewWorkArea(VirtualDesktop::instance().GetCurrentVirtualDesktopId(), monitor))
|
||||||
{
|
{
|
||||||
@@ -699,26 +722,14 @@ void FancyZones::AddWorkArea(HMONITOR monitor, const std::wstring& deviceId) noe
|
|||||||
Logger::debug(L"Add new work area on virtual desktop {}", virtualDesktopIdStr.get());
|
Logger::debug(L"Add new work area on virtual desktop {}", virtualDesktopIdStr.get());
|
||||||
}
|
}
|
||||||
|
|
||||||
FancyZonesDataTypes::DeviceIdData uniqueId;
|
FancyZonesDataTypes::WorkAreaId parentId{};
|
||||||
uniqueId.virtualDesktopId = VirtualDesktop::instance().GetCurrentVirtualDesktopId();
|
|
||||||
|
|
||||||
if (monitor)
|
|
||||||
{
|
|
||||||
uniqueId.deviceName = FancyZonesUtils::TrimDeviceId(deviceId);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
uniqueId.deviceName = ZonedWindowProperties::MultiMonitorDeviceID;
|
|
||||||
}
|
|
||||||
|
|
||||||
FancyZonesDataTypes::DeviceIdData parentId{};
|
|
||||||
auto parentArea = m_workAreaHandler.GetWorkArea(VirtualDesktop::instance().GetPreviousVirtualDesktopId(), monitor);
|
auto parentArea = m_workAreaHandler.GetWorkArea(VirtualDesktop::instance().GetPreviousVirtualDesktopId(), monitor);
|
||||||
if (parentArea)
|
if (parentArea)
|
||||||
{
|
{
|
||||||
parentId = parentArea->UniqueId();
|
parentId = parentArea->UniqueId();
|
||||||
}
|
}
|
||||||
|
|
||||||
auto workArea = MakeWorkArea(m_hinstance, monitor, uniqueId, parentId);
|
auto workArea = MakeWorkArea(m_hinstance, monitor, id, parentId);
|
||||||
if (workArea)
|
if (workArea)
|
||||||
{
|
{
|
||||||
m_workAreaHandler.AddWorkArea(VirtualDesktop::instance().GetCurrentVirtualDesktopId(), monitor, workArea);
|
m_workAreaHandler.AddWorkArea(VirtualDesktop::instance().GetCurrentVirtualDesktopId(), monitor, workArea);
|
||||||
@@ -745,34 +756,23 @@ void FancyZones::UpdateWorkAreas() noexcept
|
|||||||
{
|
{
|
||||||
if (FancyZonesSettings::settings().spanZonesAcrossMonitors)
|
if (FancyZonesSettings::settings().spanZonesAcrossMonitors)
|
||||||
{
|
{
|
||||||
AddWorkArea(nullptr, {});
|
FancyZonesDataTypes::WorkAreaId workAreaId;
|
||||||
|
workAreaId.virtualDesktopId = VirtualDesktop::instance().GetCurrentVirtualDesktopId();
|
||||||
|
workAreaId.monitorId = { .deviceId = ZonedWindowProperties::MultiMonitorDeviceID };
|
||||||
|
|
||||||
|
AddWorkArea(nullptr, workAreaId);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// Mapping between display device name and device index (operating system identifies each display device with an index value).
|
auto monitors = MonitorUtils::IdentifyMonitors();
|
||||||
std::unordered_map<std::wstring, DWORD> displayDeviceIdxMap;
|
for (const auto& monitor : monitors)
|
||||||
struct capture
|
|
||||||
{
|
{
|
||||||
FancyZones* fancyZones;
|
FancyZonesDataTypes::WorkAreaId workAreaId;
|
||||||
std::unordered_map<std::wstring, DWORD>* displayDeviceIdx;
|
workAreaId.virtualDesktopId = VirtualDesktop::instance().GetCurrentVirtualDesktopId();
|
||||||
};
|
workAreaId.monitorId = monitor;
|
||||||
|
|
||||||
auto callback = [](HMONITOR monitor, HDC, RECT*, LPARAM data) -> BOOL {
|
AddWorkArea(monitor.monitor, workAreaId);
|
||||||
capture* params = reinterpret_cast<capture*>(data);
|
}
|
||||||
MONITORINFOEX mi{ { .cbSize = sizeof(mi) } };
|
|
||||||
if (GetMonitorInfoW(monitor, &mi))
|
|
||||||
{
|
|
||||||
auto& displayDeviceIdxMap = *(params->displayDeviceIdx);
|
|
||||||
FancyZones* fancyZones = params->fancyZones;
|
|
||||||
|
|
||||||
std::wstring deviceId = FancyZonesUtils::GetDisplayDeviceId(mi.szDevice, displayDeviceIdxMap);
|
|
||||||
fancyZones->AddWorkArea(monitor, deviceId);
|
|
||||||
}
|
|
||||||
return TRUE;
|
|
||||||
};
|
|
||||||
|
|
||||||
capture capture{ this, &displayDeviceIdxMap };
|
|
||||||
EnumDisplayMonitors(nullptr, nullptr, callback, reinterpret_cast<LPARAM>(&capture));
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -8,6 +8,7 @@
|
|||||||
#include <FancyZonesLib/GuidUtils.h>
|
#include <FancyZonesLib/GuidUtils.h>
|
||||||
#include <FancyZonesLib/FancyZonesWindowProperties.h>
|
#include <FancyZonesLib/FancyZonesWindowProperties.h>
|
||||||
#include <FancyZonesLib/JsonHelpers.h>
|
#include <FancyZonesLib/JsonHelpers.h>
|
||||||
|
#include <FancyZonesLib/MonitorUtils.h>
|
||||||
#include <FancyZonesLib/VirtualDesktop.h>
|
#include <FancyZonesLib/VirtualDesktop.h>
|
||||||
#include <FancyZonesLib/util.h>
|
#include <FancyZonesLib/util.h>
|
||||||
|
|
||||||
@@ -16,7 +17,7 @@ namespace JsonUtils
|
|||||||
struct AppZoneHistoryJSON
|
struct AppZoneHistoryJSON
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
static std::optional<FancyZonesDataTypes::DeviceIdData> DeviceIdFromJson(const json::JsonObject& json)
|
static std::optional<FancyZonesDataTypes::WorkAreaId> DeviceIdFromJson(const json::JsonObject& json)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
@@ -24,6 +25,8 @@ namespace JsonUtils
|
|||||||
{
|
{
|
||||||
json::JsonObject device = json.GetNamedObject(NonLocalizable::AppZoneHistoryIds::DeviceID);
|
json::JsonObject device = json.GetNamedObject(NonLocalizable::AppZoneHistoryIds::DeviceID);
|
||||||
std::wstring monitor = device.GetNamedString(NonLocalizable::AppZoneHistoryIds::MonitorID).c_str();
|
std::wstring monitor = device.GetNamedString(NonLocalizable::AppZoneHistoryIds::MonitorID).c_str();
|
||||||
|
std::wstring monitorInstance = device.GetNamedString(NonLocalizable::AppZoneHistoryIds::MonitorInstanceID, L"").c_str();
|
||||||
|
std::wstring monitorSerialNumber = device.GetNamedString(NonLocalizable::AppZoneHistoryIds::MonitorSerialNumberID, L"").c_str();
|
||||||
std::wstring virtualDesktop = device.GetNamedString(NonLocalizable::AppZoneHistoryIds::VirtualDesktopID).c_str();
|
std::wstring virtualDesktop = device.GetNamedString(NonLocalizable::AppZoneHistoryIds::VirtualDesktopID).c_str();
|
||||||
|
|
||||||
auto virtualDesktopGuid = FancyZonesUtils::GuidFromString(virtualDesktop);
|
auto virtualDesktopGuid = FancyZonesUtils::GuidFromString(virtualDesktop);
|
||||||
@@ -32,8 +35,25 @@ namespace JsonUtils
|
|||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
}
|
}
|
||||||
|
|
||||||
return FancyZonesDataTypes::DeviceIdData{
|
FancyZonesDataTypes::DeviceId deviceId{};
|
||||||
.deviceName = monitor,
|
if (monitorInstance.empty())
|
||||||
|
{
|
||||||
|
// old data
|
||||||
|
deviceId = MonitorUtils::Display::ConvertObsoleteDeviceId(monitor);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
deviceId.id = monitor;
|
||||||
|
deviceId.instanceId = monitorInstance;
|
||||||
|
}
|
||||||
|
|
||||||
|
FancyZonesDataTypes::MonitorId monitorId{
|
||||||
|
.deviceId = deviceId,
|
||||||
|
.serialNumber = monitorSerialNumber
|
||||||
|
};
|
||||||
|
|
||||||
|
return FancyZonesDataTypes::WorkAreaId{
|
||||||
|
.monitorId = monitorId,
|
||||||
.virtualDesktopId = virtualDesktopGuid.value(),
|
.virtualDesktopId = virtualDesktopGuid.value(),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@@ -46,8 +66,8 @@ namespace JsonUtils
|
|||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
}
|
}
|
||||||
|
|
||||||
return FancyZonesDataTypes::DeviceIdData{
|
return FancyZonesDataTypes::WorkAreaId{
|
||||||
.deviceName = bcDeviceId->deviceName,
|
.monitorId = { .deviceId = MonitorUtils::Display::ConvertObsoleteDeviceId(bcDeviceId->deviceName) },
|
||||||
.virtualDesktopId = bcDeviceId->virtualDesktopId,
|
.virtualDesktopId = bcDeviceId->virtualDesktopId,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@@ -80,7 +100,7 @@ namespace JsonUtils
|
|||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
}
|
}
|
||||||
|
|
||||||
data.deviceId = deviceIdOpt.value();
|
data.workAreaId = deviceIdOpt.value();
|
||||||
data.zoneSetUuid = json.GetNamedString(NonLocalizable::AppZoneHistoryIds::LayoutIdID);
|
data.zoneSetUuid = json.GetNamedString(NonLocalizable::AppZoneHistoryIds::LayoutIdID);
|
||||||
|
|
||||||
if (!FancyZonesUtils::IsValidGuid(data.zoneSetUuid))
|
if (!FancyZonesUtils::IsValidGuid(data.zoneSetUuid))
|
||||||
@@ -152,8 +172,11 @@ namespace JsonUtils
|
|||||||
}
|
}
|
||||||
|
|
||||||
json::JsonObject device{};
|
json::JsonObject device{};
|
||||||
device.SetNamedValue(NonLocalizable::AppZoneHistoryIds::MonitorID, json::value(data.deviceId.deviceName));
|
device.SetNamedValue(NonLocalizable::AppZoneHistoryIds::MonitorID, json::value(data.workAreaId.monitorId.deviceId.id));
|
||||||
auto virtualDesktopStr = FancyZonesUtils::GuidToString(data.deviceId.virtualDesktopId);
|
device.SetNamedValue(NonLocalizable::AppZoneHistoryIds::MonitorInstanceID, json::value(data.workAreaId.monitorId.deviceId.instanceId));
|
||||||
|
device.SetNamedValue(NonLocalizable::AppZoneHistoryIds::MonitorSerialNumberID, json::value(data.workAreaId.monitorId.serialNumber));
|
||||||
|
|
||||||
|
auto virtualDesktopStr = FancyZonesUtils::GuidToString(data.workAreaId.virtualDesktopId);
|
||||||
if (virtualDesktopStr)
|
if (virtualDesktopStr)
|
||||||
{
|
{
|
||||||
device.SetNamedValue(NonLocalizable::AppZoneHistoryIds::VirtualDesktopID, json::value(virtualDesktopStr.value()));
|
device.SetNamedValue(NonLocalizable::AppZoneHistoryIds::VirtualDesktopID, json::value(virtualDesktopStr.value()));
|
||||||
@@ -255,9 +278,9 @@ void AppZoneHistory::SaveData()
|
|||||||
auto updatedVector = dataVector;
|
auto updatedVector = dataVector;
|
||||||
for (auto& data : updatedVector)
|
for (auto& data : updatedVector)
|
||||||
{
|
{
|
||||||
if (!VirtualDesktop::instance().IsVirtualDesktopIdSavedInRegistry(data.deviceId.virtualDesktopId))
|
if (!VirtualDesktop::instance().IsVirtualDesktopIdSavedInRegistry(data.workAreaId.virtualDesktopId))
|
||||||
{
|
{
|
||||||
data.deviceId.virtualDesktopId = GUID_NULL;
|
data.workAreaId.virtualDesktopId = GUID_NULL;
|
||||||
dirtyFlag = true;
|
dirtyFlag = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -275,9 +298,40 @@ void AppZoneHistory::SaveData()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool AppZoneHistory::SetAppLastZones(HWND window, const FancyZonesDataTypes::DeviceIdData& deviceId, const std::wstring& zoneSetId, const ZoneIndexSet& zoneIndexSet)
|
void AppZoneHistory::AdjustWorkAreaIds(const std::vector<FancyZonesDataTypes::MonitorId>& ids)
|
||||||
{
|
{
|
||||||
if (IsAnotherWindowOfApplicationInstanceZoned(window, deviceId))
|
bool dirtyFlag = false;
|
||||||
|
|
||||||
|
for (auto iter = m_history.begin(); iter != m_history.end(); ++iter)
|
||||||
|
{
|
||||||
|
auto& [app, data] = *iter;
|
||||||
|
for (auto& dataIter = data.begin(); dataIter != data.end(); ++dataIter)
|
||||||
|
{
|
||||||
|
auto& dataMonitorId = dataIter->workAreaId.monitorId;
|
||||||
|
if (dataMonitorId.serialNumber.empty() && !dataMonitorId.deviceId.isDefault())
|
||||||
|
{
|
||||||
|
for (const auto& monitorId : ids)
|
||||||
|
{
|
||||||
|
if (dataMonitorId.deviceId.id == monitorId.deviceId.id && dataMonitorId.deviceId.instanceId == monitorId.deviceId.instanceId)
|
||||||
|
{
|
||||||
|
dataMonitorId.serialNumber = monitorId.serialNumber;
|
||||||
|
dirtyFlag = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (dirtyFlag)
|
||||||
|
{
|
||||||
|
SaveData();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bool AppZoneHistory::SetAppLastZones(HWND window, const FancyZonesDataTypes::WorkAreaId& workAreaId, const std::wstring& zoneSetId, const ZoneIndexSet& zoneIndexSet)
|
||||||
|
{
|
||||||
|
if (IsAnotherWindowOfApplicationInstanceZoned(window, workAreaId))
|
||||||
{
|
{
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@@ -288,7 +342,7 @@ bool AppZoneHistory::SetAppLastZones(HWND window, const FancyZonesDataTypes::Dev
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
Logger::info(L"Add app zone history, device: {}, layout: {}", deviceId.toString(), zoneSetId);
|
Logger::info(L"Add app zone history, device: {}, layout: {}", workAreaId.toString(), zoneSetId);
|
||||||
|
|
||||||
DWORD processId = 0;
|
DWORD processId = 0;
|
||||||
GetWindowThreadProcessId(window, &processId);
|
GetWindowThreadProcessId(window, &processId);
|
||||||
@@ -299,7 +353,7 @@ bool AppZoneHistory::SetAppLastZones(HWND window, const FancyZonesDataTypes::Dev
|
|||||||
auto& perDesktopData = history->second;
|
auto& perDesktopData = history->second;
|
||||||
for (auto& data : perDesktopData)
|
for (auto& data : perDesktopData)
|
||||||
{
|
{
|
||||||
if (data.deviceId == deviceId)
|
if (data.workAreaId == workAreaId)
|
||||||
{
|
{
|
||||||
// application already has history on this work area, update it with new window position
|
// application already has history on this work area, update it with new window position
|
||||||
data.processIdToHandleMap[processId] = window;
|
data.processIdToHandleMap[processId] = window;
|
||||||
@@ -315,7 +369,7 @@ bool AppZoneHistory::SetAppLastZones(HWND window, const FancyZonesDataTypes::Dev
|
|||||||
processIdToHandleMap[processId] = window;
|
processIdToHandleMap[processId] = window;
|
||||||
FancyZonesDataTypes::AppZoneHistoryData data{ .processIdToHandleMap = processIdToHandleMap,
|
FancyZonesDataTypes::AppZoneHistoryData data{ .processIdToHandleMap = processIdToHandleMap,
|
||||||
.zoneSetUuid = zoneSetId,
|
.zoneSetUuid = zoneSetId,
|
||||||
.deviceId = deviceId,
|
.workAreaId = workAreaId,
|
||||||
.zoneIndexSet = zoneIndexSet };
|
.zoneIndexSet = zoneIndexSet };
|
||||||
|
|
||||||
if (m_history.contains(processPath))
|
if (m_history.contains(processPath))
|
||||||
@@ -333,9 +387,9 @@ bool AppZoneHistory::SetAppLastZones(HWND window, const FancyZonesDataTypes::Dev
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool AppZoneHistory::RemoveAppLastZone(HWND window, const FancyZonesDataTypes::DeviceIdData& deviceId, const std::wstring_view& zoneSetId)
|
bool AppZoneHistory::RemoveAppLastZone(HWND window, const FancyZonesDataTypes::WorkAreaId& workAreaId, const std::wstring_view& zoneSetId)
|
||||||
{
|
{
|
||||||
Logger::info(L"Add app zone history, device: {}, layout: {}", deviceId.toString(), zoneSetId);
|
Logger::info(L"Add app zone history, device: {}, layout: {}", workAreaId.toString(), zoneSetId);
|
||||||
|
|
||||||
auto processPath = get_process_path_waiting_uwp(window);
|
auto processPath = get_process_path_waiting_uwp(window);
|
||||||
if (!processPath.empty())
|
if (!processPath.empty())
|
||||||
@@ -346,9 +400,9 @@ bool AppZoneHistory::RemoveAppLastZone(HWND window, const FancyZonesDataTypes::D
|
|||||||
auto& perDesktopData = history->second;
|
auto& perDesktopData = history->second;
|
||||||
for (auto data = std::begin(perDesktopData); data != std::end(perDesktopData);)
|
for (auto data = std::begin(perDesktopData); data != std::end(perDesktopData);)
|
||||||
{
|
{
|
||||||
if (data->deviceId == deviceId && data->zoneSetUuid == zoneSetId)
|
if (data->workAreaId == workAreaId && data->zoneSetUuid == zoneSetId)
|
||||||
{
|
{
|
||||||
if (!IsAnotherWindowOfApplicationInstanceZoned(window, deviceId))
|
if (!IsAnotherWindowOfApplicationInstanceZoned(window, workAreaId))
|
||||||
{
|
{
|
||||||
DWORD processId = 0;
|
DWORD processId = 0;
|
||||||
GetWindowThreadProcessId(window, &processId);
|
GetWindowThreadProcessId(window, &processId);
|
||||||
@@ -396,7 +450,7 @@ const AppZoneHistory::TAppZoneHistoryMap& AppZoneHistory::GetFullAppZoneHistory(
|
|||||||
return m_history;
|
return m_history;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::optional<FancyZonesDataTypes::AppZoneHistoryData> AppZoneHistory::GetZoneHistory(const std::wstring& appPath, const FancyZonesDataTypes::DeviceIdData& deviceId) const noexcept
|
std::optional<FancyZonesDataTypes::AppZoneHistoryData> AppZoneHistory::GetZoneHistory(const std::wstring& appPath, const FancyZonesDataTypes::WorkAreaId& workAreaId) const noexcept
|
||||||
{
|
{
|
||||||
auto app = appPath;
|
auto app = appPath;
|
||||||
auto pos = appPath.find_last_of('\\');
|
auto pos = appPath.find_last_of('\\');
|
||||||
@@ -405,10 +459,10 @@ std::optional<FancyZonesDataTypes::AppZoneHistoryData> AppZoneHistory::GetZoneHi
|
|||||||
app = appPath.substr(pos + 1);
|
app = appPath.substr(pos + 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto srcVirtualDesktopIDStr = FancyZonesUtils::GuidToString(deviceId.virtualDesktopId);
|
auto srcVirtualDesktopIDStr = FancyZonesUtils::GuidToString(workAreaId.virtualDesktopId);
|
||||||
if (srcVirtualDesktopIDStr)
|
if (srcVirtualDesktopIDStr)
|
||||||
{
|
{
|
||||||
Logger::debug(L"Get {} zone history on monitor: {}, virtual desktop: {}", app, deviceId.deviceName, srcVirtualDesktopIDStr.value());
|
Logger::debug(L"Get {} zone history on monitor: {}, virtual desktop: {}", app, workAreaId.toString(), srcVirtualDesktopIDStr.value());
|
||||||
}
|
}
|
||||||
|
|
||||||
auto iter = m_history.find(appPath);
|
auto iter = m_history.find(appPath);
|
||||||
@@ -421,15 +475,15 @@ std::optional<FancyZonesDataTypes::AppZoneHistoryData> AppZoneHistory::GetZoneHi
|
|||||||
auto historyVector = iter->second;
|
auto historyVector = iter->second;
|
||||||
for (const auto& history : historyVector)
|
for (const auto& history : historyVector)
|
||||||
{
|
{
|
||||||
if (history.deviceId.deviceName == deviceId.deviceName)
|
if (history.workAreaId == workAreaId)
|
||||||
{
|
{
|
||||||
auto vdStr = FancyZonesUtils::GuidToString(history.deviceId.virtualDesktopId);
|
auto vdStr = FancyZonesUtils::GuidToString(history.workAreaId.virtualDesktopId);
|
||||||
if (vdStr)
|
if (vdStr)
|
||||||
{
|
{
|
||||||
Logger::debug(L"App zone history found on the device {} with virtual desktop {}", history.deviceId.deviceName, vdStr.value());
|
Logger::debug(L"App zone history found on the device {} with virtual desktop {}", history.workAreaId.toString(), vdStr.value());
|
||||||
}
|
}
|
||||||
|
|
||||||
if (history.deviceId.virtualDesktopId == deviceId.virtualDesktopId || history.deviceId.virtualDesktopId == GUID_NULL)
|
if (history.workAreaId.virtualDesktopId == workAreaId.virtualDesktopId || history.workAreaId.virtualDesktopId == GUID_NULL)
|
||||||
{
|
{
|
||||||
return history;
|
return history;
|
||||||
}
|
}
|
||||||
@@ -439,7 +493,7 @@ std::optional<FancyZonesDataTypes::AppZoneHistoryData> AppZoneHistory::GetZoneHi
|
|||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool AppZoneHistory::IsAnotherWindowOfApplicationInstanceZoned(HWND window, const FancyZonesDataTypes::DeviceIdData& deviceId) const noexcept
|
bool AppZoneHistory::IsAnotherWindowOfApplicationInstanceZoned(HWND window, const FancyZonesDataTypes::WorkAreaId& workAreaId) const noexcept
|
||||||
{
|
{
|
||||||
auto processPath = get_process_path_waiting_uwp(window);
|
auto processPath = get_process_path_waiting_uwp(window);
|
||||||
if (!processPath.empty())
|
if (!processPath.empty())
|
||||||
@@ -450,7 +504,7 @@ bool AppZoneHistory::IsAnotherWindowOfApplicationInstanceZoned(HWND window, cons
|
|||||||
auto& perDesktopData = history->second;
|
auto& perDesktopData = history->second;
|
||||||
for (auto& data : perDesktopData)
|
for (auto& data : perDesktopData)
|
||||||
{
|
{
|
||||||
if (data.deviceId == deviceId)
|
if (data.workAreaId == workAreaId)
|
||||||
{
|
{
|
||||||
DWORD processId = 0;
|
DWORD processId = 0;
|
||||||
GetWindowThreadProcessId(window, &processId);
|
GetWindowThreadProcessId(window, &processId);
|
||||||
@@ -473,7 +527,7 @@ bool AppZoneHistory::IsAnotherWindowOfApplicationInstanceZoned(HWND window, cons
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
void AppZoneHistory::UpdateProcessIdToHandleMap(HWND window, const FancyZonesDataTypes::DeviceIdData& deviceId)
|
void AppZoneHistory::UpdateProcessIdToHandleMap(HWND window, const FancyZonesDataTypes::WorkAreaId& workAreaId)
|
||||||
{
|
{
|
||||||
auto processPath = get_process_path_waiting_uwp(window);
|
auto processPath = get_process_path_waiting_uwp(window);
|
||||||
if (!processPath.empty())
|
if (!processPath.empty())
|
||||||
@@ -484,7 +538,7 @@ void AppZoneHistory::UpdateProcessIdToHandleMap(HWND window, const FancyZonesDat
|
|||||||
auto& perDesktopData = history->second;
|
auto& perDesktopData = history->second;
|
||||||
for (auto& data : perDesktopData)
|
for (auto& data : perDesktopData)
|
||||||
{
|
{
|
||||||
if (data.deviceId == deviceId)
|
if (data.workAreaId == workAreaId)
|
||||||
{
|
{
|
||||||
DWORD processId = 0;
|
DWORD processId = 0;
|
||||||
GetWindowThreadProcessId(window, &processId);
|
GetWindowThreadProcessId(window, &processId);
|
||||||
@@ -496,7 +550,7 @@ void AppZoneHistory::UpdateProcessIdToHandleMap(HWND window, const FancyZonesDat
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ZoneIndexSet AppZoneHistory::GetAppLastZoneIndexSet(HWND window, const FancyZonesDataTypes::DeviceIdData& deviceId, const std::wstring_view& zoneSetId) const
|
ZoneIndexSet AppZoneHistory::GetAppLastZoneIndexSet(HWND window, const FancyZonesDataTypes::WorkAreaId& workAreaId, const std::wstring_view& zoneSetId) const
|
||||||
{
|
{
|
||||||
auto processPath = get_process_path_waiting_uwp(window);
|
auto processPath = get_process_path_waiting_uwp(window);
|
||||||
if (processPath.empty())
|
if (processPath.empty())
|
||||||
@@ -505,7 +559,7 @@ ZoneIndexSet AppZoneHistory::GetAppLastZoneIndexSet(HWND window, const FancyZone
|
|||||||
return {};
|
return {};
|
||||||
}
|
}
|
||||||
|
|
||||||
auto srcVirtualDesktopIDStr = FancyZonesUtils::GuidToString(deviceId.virtualDesktopId);
|
auto srcVirtualDesktopIDStr = FancyZonesUtils::GuidToString(workAreaId.virtualDesktopId);
|
||||||
auto app = processPath;
|
auto app = processPath;
|
||||||
auto pos = processPath.find_last_of('\\');
|
auto pos = processPath.find_last_of('\\');
|
||||||
if (pos != std::string::npos && pos + 1 < processPath.length())
|
if (pos != std::string::npos && pos + 1 < processPath.length())
|
||||||
@@ -515,7 +569,7 @@ ZoneIndexSet AppZoneHistory::GetAppLastZoneIndexSet(HWND window, const FancyZone
|
|||||||
|
|
||||||
if (srcVirtualDesktopIDStr)
|
if (srcVirtualDesktopIDStr)
|
||||||
{
|
{
|
||||||
Logger::debug(L"Get {} zone history on monitor: {}, virtual desktop: {}", app, deviceId.deviceName, srcVirtualDesktopIDStr.value());
|
Logger::debug(L"Get {} zone history on monitor: {}, virtual desktop: {}", app, workAreaId.toString(), srcVirtualDesktopIDStr.value());
|
||||||
}
|
}
|
||||||
|
|
||||||
auto history = m_history.find(processPath);
|
auto history = m_history.find(processPath);
|
||||||
@@ -527,15 +581,15 @@ ZoneIndexSet AppZoneHistory::GetAppLastZoneIndexSet(HWND window, const FancyZone
|
|||||||
const auto& perDesktopData = history->second;
|
const auto& perDesktopData = history->second;
|
||||||
for (const auto& data : perDesktopData)
|
for (const auto& data : perDesktopData)
|
||||||
{
|
{
|
||||||
if (data.zoneSetUuid == zoneSetId && data.deviceId.deviceName == deviceId.deviceName)
|
if (data.zoneSetUuid == zoneSetId && data.workAreaId == workAreaId)
|
||||||
{
|
{
|
||||||
auto vdStr = FancyZonesUtils::GuidToString(data.deviceId.virtualDesktopId);
|
auto vdStr = FancyZonesUtils::GuidToString(data.workAreaId.virtualDesktopId);
|
||||||
if (vdStr)
|
if (vdStr)
|
||||||
{
|
{
|
||||||
Logger::debug(L"App zone history found on the device {} with virtual desktop {}", data.deviceId.deviceName, vdStr.value());
|
Logger::debug(L"App zone history found on the device {} with virtual desktop {}", data.workAreaId.toString(), vdStr.value());
|
||||||
}
|
}
|
||||||
|
|
||||||
if (data.deviceId.virtualDesktopId == deviceId.virtualDesktopId || data.deviceId.virtualDesktopId == GUID_NULL)
|
if (data.workAreaId.virtualDesktopId == workAreaId.virtualDesktopId || data.workAreaId.virtualDesktopId == GUID_NULL)
|
||||||
{
|
{
|
||||||
return data.zoneIndexSet;
|
return data.zoneIndexSet;
|
||||||
}
|
}
|
||||||
@@ -573,9 +627,9 @@ void AppZoneHistory::SyncVirtualDesktops()
|
|||||||
{
|
{
|
||||||
for (auto& data : perDesktopData)
|
for (auto& data : perDesktopData)
|
||||||
{
|
{
|
||||||
if (data.deviceId.virtualDesktopId == GUID_NULL)
|
if (data.workAreaId.virtualDesktopId == GUID_NULL)
|
||||||
{
|
{
|
||||||
data.deviceId.virtualDesktopId = savedInRegistryVirtualDesktopID.value();
|
data.workAreaId.virtualDesktopId = savedInRegistryVirtualDesktopID.value();
|
||||||
dirtyFlag = true;
|
dirtyFlag = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -598,9 +652,9 @@ void AppZoneHistory::RemoveDeletedVirtualDesktops(const std::vector<GUID>& activ
|
|||||||
auto& perDesktopData = it->second;
|
auto& perDesktopData = it->second;
|
||||||
for (auto desktopIt = std::begin(perDesktopData); desktopIt != std::end(perDesktopData);)
|
for (auto desktopIt = std::begin(perDesktopData); desktopIt != std::end(perDesktopData);)
|
||||||
{
|
{
|
||||||
if (desktopIt->deviceId.virtualDesktopId != GUID_NULL && !active.contains(desktopIt->deviceId.virtualDesktopId))
|
if (desktopIt->workAreaId.virtualDesktopId != GUID_NULL && !active.contains(desktopIt->workAreaId.virtualDesktopId))
|
||||||
{
|
{
|
||||||
auto virtualDesktopIdStr = FancyZonesUtils::GuidToString(desktopIt->deviceId.virtualDesktopId);
|
auto virtualDesktopIdStr = FancyZonesUtils::GuidToString(desktopIt->workAreaId.virtualDesktopId);
|
||||||
if (virtualDesktopIdStr)
|
if (virtualDesktopIdStr)
|
||||||
{
|
{
|
||||||
Logger::info(L"Remove Virtual Desktop id {} from app-zone-history", virtualDesktopIdStr.value());
|
Logger::info(L"Remove Virtual Desktop id {} from app-zone-history", virtualDesktopIdStr.value());
|
||||||
|
|||||||
@@ -17,6 +17,8 @@ namespace NonLocalizable
|
|||||||
const static wchar_t* DeviceIdID = L"device-id";
|
const static wchar_t* DeviceIdID = L"device-id";
|
||||||
const static wchar_t* DeviceID = L"device";
|
const static wchar_t* DeviceID = L"device";
|
||||||
const static wchar_t* MonitorID = L"monitor";
|
const static wchar_t* MonitorID = L"monitor";
|
||||||
|
const static wchar_t* MonitorInstanceID = L"monitor-instance";
|
||||||
|
const static wchar_t* MonitorSerialNumberID = L"serial-number";
|
||||||
const static wchar_t* VirtualDesktopID = L"virtual-desktop";
|
const static wchar_t* VirtualDesktopID = L"virtual-desktop";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -39,18 +41,19 @@ public:
|
|||||||
|
|
||||||
void LoadData();
|
void LoadData();
|
||||||
void SaveData();
|
void SaveData();
|
||||||
|
void AdjustWorkAreaIds(const std::vector<FancyZonesDataTypes::MonitorId>& ids);
|
||||||
|
|
||||||
bool SetAppLastZones(HWND window, const FancyZonesDataTypes::DeviceIdData& deviceId, const std::wstring& zoneSetId, const ZoneIndexSet& zoneIndexSet);
|
bool SetAppLastZones(HWND window, const FancyZonesDataTypes::WorkAreaId& workAreaId, const std::wstring& zoneSetId, const ZoneIndexSet& zoneIndexSet);
|
||||||
bool RemoveAppLastZone(HWND window, const FancyZonesDataTypes::DeviceIdData& deviceId, const std::wstring_view& zoneSetId);
|
bool RemoveAppLastZone(HWND window, const FancyZonesDataTypes::WorkAreaId& workAreaId, const std::wstring_view& zoneSetId);
|
||||||
|
|
||||||
void RemoveApp(const std::wstring& appPath);
|
void RemoveApp(const std::wstring& appPath);
|
||||||
|
|
||||||
const TAppZoneHistoryMap& GetFullAppZoneHistory() const noexcept;
|
const TAppZoneHistoryMap& GetFullAppZoneHistory() const noexcept;
|
||||||
std::optional<FancyZonesDataTypes::AppZoneHistoryData> GetZoneHistory(const std::wstring& appPath, const FancyZonesDataTypes::DeviceIdData& deviceId) const noexcept;
|
std::optional<FancyZonesDataTypes::AppZoneHistoryData> GetZoneHistory(const std::wstring& appPath, const FancyZonesDataTypes::WorkAreaId& workAreaId) const noexcept;
|
||||||
|
|
||||||
bool IsAnotherWindowOfApplicationInstanceZoned(HWND window, const FancyZonesDataTypes::DeviceIdData& deviceId) const noexcept;
|
bool IsAnotherWindowOfApplicationInstanceZoned(HWND window, const FancyZonesDataTypes::WorkAreaId& workAreaId) const noexcept;
|
||||||
void UpdateProcessIdToHandleMap(HWND window, const FancyZonesDataTypes::DeviceIdData& deviceId);
|
void UpdateProcessIdToHandleMap(HWND window, const FancyZonesDataTypes::WorkAreaId& workAreaId);
|
||||||
ZoneIndexSet GetAppLastZoneIndexSet(HWND window, const FancyZonesDataTypes::DeviceIdData& deviceId, const std::wstring_view& zoneSetId) const;
|
ZoneIndexSet GetAppLastZoneIndexSet(HWND window, const FancyZonesDataTypes::WorkAreaId& workAreaId, const std::wstring_view& zoneSetId) const;
|
||||||
|
|
||||||
void SyncVirtualDesktops();
|
void SyncVirtualDesktops();
|
||||||
void RemoveDeletedVirtualDesktops(const std::vector<GUID>& activeDesktops);
|
void RemoveDeletedVirtualDesktops(const std::vector<GUID>& activeDesktops);
|
||||||
|
|||||||
@@ -9,6 +9,7 @@
|
|||||||
#include <FancyZonesLib/FancyZonesData/LayoutDefaults.h>
|
#include <FancyZonesLib/FancyZonesData/LayoutDefaults.h>
|
||||||
#include <FancyZonesLib/FancyZonesWinHookEventIDs.h>
|
#include <FancyZonesLib/FancyZonesWinHookEventIDs.h>
|
||||||
#include <FancyZonesLib/JsonHelpers.h>
|
#include <FancyZonesLib/JsonHelpers.h>
|
||||||
|
#include <FancyZonesLib/MonitorUtils.h>
|
||||||
#include <FancyZonesLib/VirtualDesktop.h>
|
#include <FancyZonesLib/VirtualDesktop.h>
|
||||||
#include <FancyZonesLib/util.h>
|
#include <FancyZonesLib/util.h>
|
||||||
|
|
||||||
@@ -72,7 +73,7 @@ namespace JsonUtils
|
|||||||
struct AppliedLayoutsJSON
|
struct AppliedLayoutsJSON
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
static std::optional<FancyZonesDataTypes::DeviceIdData> DeviceIdFromJson(const json::JsonObject& json)
|
static std::optional<FancyZonesDataTypes::WorkAreaId> WorkAreaIdFromJson(const json::JsonObject& json)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
@@ -80,6 +81,8 @@ namespace JsonUtils
|
|||||||
{
|
{
|
||||||
json::JsonObject device = json.GetNamedObject(NonLocalizable::AppliedLayoutsIds::DeviceID);
|
json::JsonObject device = json.GetNamedObject(NonLocalizable::AppliedLayoutsIds::DeviceID);
|
||||||
std::wstring monitor = device.GetNamedString(NonLocalizable::AppliedLayoutsIds::MonitorID).c_str();
|
std::wstring monitor = device.GetNamedString(NonLocalizable::AppliedLayoutsIds::MonitorID).c_str();
|
||||||
|
std::wstring monitorInstance = device.GetNamedString(NonLocalizable::AppliedLayoutsIds::MonitorInstanceID, L"").c_str();
|
||||||
|
std::wstring monitorSerialNumber = device.GetNamedString(NonLocalizable::AppliedLayoutsIds::MonitorSerialNumberID, L"").c_str();
|
||||||
std::wstring virtualDesktop = device.GetNamedString(NonLocalizable::AppliedLayoutsIds::VirtualDesktopID).c_str();
|
std::wstring virtualDesktop = device.GetNamedString(NonLocalizable::AppliedLayoutsIds::VirtualDesktopID).c_str();
|
||||||
|
|
||||||
auto virtualDesktopGuid = FancyZonesUtils::GuidFromString(virtualDesktop);
|
auto virtualDesktopGuid = FancyZonesUtils::GuidFromString(virtualDesktop);
|
||||||
@@ -88,8 +91,25 @@ namespace JsonUtils
|
|||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
}
|
}
|
||||||
|
|
||||||
return FancyZonesDataTypes::DeviceIdData{
|
FancyZonesDataTypes::DeviceId deviceId{};
|
||||||
.deviceName = monitor,
|
if (monitorInstance.empty())
|
||||||
|
{
|
||||||
|
// old data
|
||||||
|
deviceId = MonitorUtils::Display::ConvertObsoleteDeviceId(monitor);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
deviceId.id = monitor;
|
||||||
|
deviceId.instanceId = monitorInstance;
|
||||||
|
}
|
||||||
|
|
||||||
|
FancyZonesDataTypes::MonitorId monitorId{
|
||||||
|
.deviceId = deviceId,
|
||||||
|
.serialNumber = monitorSerialNumber
|
||||||
|
};
|
||||||
|
|
||||||
|
return FancyZonesDataTypes::WorkAreaId{
|
||||||
|
.monitorId = monitorId,
|
||||||
.virtualDesktopId = virtualDesktopGuid.value(),
|
.virtualDesktopId = virtualDesktopGuid.value(),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@@ -102,8 +122,8 @@ namespace JsonUtils
|
|||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
}
|
}
|
||||||
|
|
||||||
return FancyZonesDataTypes::DeviceIdData{
|
return FancyZonesDataTypes::WorkAreaId{
|
||||||
.deviceName = bcDeviceId->deviceName,
|
.monitorId = { .deviceId = MonitorUtils::Display::ConvertObsoleteDeviceId(bcDeviceId->deviceName) },
|
||||||
.virtualDesktopId = bcDeviceId->virtualDesktopId,
|
.virtualDesktopId = bcDeviceId->virtualDesktopId,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@@ -115,7 +135,7 @@ namespace JsonUtils
|
|||||||
}
|
}
|
||||||
|
|
||||||
public:
|
public:
|
||||||
FancyZonesDataTypes::DeviceIdData deviceId;
|
FancyZonesDataTypes::WorkAreaId workAreaId;
|
||||||
Layout data;
|
Layout data;
|
||||||
|
|
||||||
static std::optional<AppliedLayoutsJSON> FromJson(const json::JsonObject& json)
|
static std::optional<AppliedLayoutsJSON> FromJson(const json::JsonObject& json)
|
||||||
@@ -124,7 +144,7 @@ namespace JsonUtils
|
|||||||
{
|
{
|
||||||
AppliedLayoutsJSON result;
|
AppliedLayoutsJSON result;
|
||||||
|
|
||||||
auto deviceIdOpt = DeviceIdFromJson(json);
|
auto deviceIdOpt = WorkAreaIdFromJson(json);
|
||||||
if (!deviceIdOpt.has_value())
|
if (!deviceIdOpt.has_value())
|
||||||
{
|
{
|
||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
@@ -136,7 +156,7 @@ namespace JsonUtils
|
|||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
}
|
}
|
||||||
|
|
||||||
result.deviceId = std::move(deviceIdOpt.value());
|
result.workAreaId = std::move(deviceIdOpt.value());
|
||||||
result.data = std::move(layout.value());
|
result.data = std::move(layout.value());
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@@ -149,9 +169,11 @@ namespace JsonUtils
|
|||||||
static json::JsonObject ToJson(const AppliedLayoutsJSON& value)
|
static json::JsonObject ToJson(const AppliedLayoutsJSON& value)
|
||||||
{
|
{
|
||||||
json::JsonObject device{};
|
json::JsonObject device{};
|
||||||
device.SetNamedValue(NonLocalizable::AppliedLayoutsIds::MonitorID, json::value(value.deviceId.deviceName));
|
device.SetNamedValue(NonLocalizable::AppliedLayoutsIds::MonitorID, json::value(value.workAreaId.monitorId.deviceId.id));
|
||||||
|
device.SetNamedValue(NonLocalizable::AppliedLayoutsIds::MonitorInstanceID, json::value(value.workAreaId.monitorId.deviceId.instanceId));
|
||||||
|
device.SetNamedValue(NonLocalizable::AppliedLayoutsIds::MonitorSerialNumberID, json::value(value.workAreaId.monitorId.serialNumber));
|
||||||
|
|
||||||
auto virtualDesktopStr = FancyZonesUtils::GuidToString(value.deviceId.virtualDesktopId);
|
auto virtualDesktopStr = FancyZonesUtils::GuidToString(value.workAreaId.virtualDesktopId);
|
||||||
if (virtualDesktopStr)
|
if (virtualDesktopStr)
|
||||||
{
|
{
|
||||||
device.SetNamedValue(NonLocalizable::AppliedLayoutsIds::VirtualDesktopID, json::value(virtualDesktopStr.value()));
|
device.SetNamedValue(NonLocalizable::AppliedLayoutsIds::VirtualDesktopID, json::value(virtualDesktopStr.value()));
|
||||||
@@ -176,9 +198,9 @@ namespace JsonUtils
|
|||||||
{
|
{
|
||||||
// skip default layouts in case if they were applied to different resolutions on the same monitor.
|
// skip default layouts in case if they were applied to different resolutions on the same monitor.
|
||||||
// NOTE: keep the default layout check for users who update PT version from the v0.57
|
// NOTE: keep the default layout check for users who update PT version from the v0.57
|
||||||
if (!map.contains(obj->deviceId) && !isLayoutDefault(obj->data))
|
if (!map.contains(obj->workAreaId) && !isLayoutDefault(obj->data))
|
||||||
{
|
{
|
||||||
map[obj->deviceId] = std::move(obj->data);
|
map[obj->workAreaId] = std::move(obj->data);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -194,7 +216,7 @@ namespace JsonUtils
|
|||||||
for (const auto& [id, data] : map)
|
for (const auto& [id, data] : map)
|
||||||
{
|
{
|
||||||
AppliedLayoutsJSON obj{};
|
AppliedLayoutsJSON obj{};
|
||||||
obj.deviceId = id;
|
obj.workAreaId = id;
|
||||||
obj.data = data;
|
obj.data = data;
|
||||||
layoutArray.Append(AppliedLayoutsJSON::ToJson(obj));
|
layoutArray.Append(AppliedLayoutsJSON::ToJson(obj));
|
||||||
}
|
}
|
||||||
@@ -268,6 +290,41 @@ void AppliedLayouts::SaveData()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void AppliedLayouts::AdjustWorkAreaIds(const std::vector<FancyZonesDataTypes::MonitorId>& ids)
|
||||||
|
{
|
||||||
|
bool dirtyFlag = false;
|
||||||
|
|
||||||
|
std::vector<std::pair<FancyZonesDataTypes::WorkAreaId, std::wstring>> replaceWithSerialNumber{};
|
||||||
|
for (auto iter = m_layouts.begin(); iter != m_layouts.end(); ++iter)
|
||||||
|
{
|
||||||
|
const auto& [id, layout] = *iter;
|
||||||
|
if (id.monitorId.serialNumber.empty() && !id.monitorId.deviceId.isDefault())
|
||||||
|
{
|
||||||
|
for (const auto& monitorId : ids)
|
||||||
|
{
|
||||||
|
if (id.monitorId.deviceId.id == monitorId.deviceId.id && id.monitorId.deviceId.instanceId == monitorId.deviceId.instanceId)
|
||||||
|
{
|
||||||
|
replaceWithSerialNumber.push_back({ id, monitorId.serialNumber });
|
||||||
|
dirtyFlag = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (const auto& id : replaceWithSerialNumber)
|
||||||
|
{
|
||||||
|
auto mapEntry = m_layouts.extract(id.first);
|
||||||
|
mapEntry.key().monitorId.serialNumber = id.second;
|
||||||
|
m_layouts.insert(std::move(mapEntry));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (dirtyFlag)
|
||||||
|
{
|
||||||
|
SaveData();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void AppliedLayouts::SyncVirtualDesktops()
|
void AppliedLayouts::SyncVirtualDesktops()
|
||||||
{
|
{
|
||||||
// Explorer persists current virtual desktop identifier to registry on a per session basis,
|
// Explorer persists current virtual desktop identifier to registry on a per session basis,
|
||||||
@@ -292,7 +349,7 @@ void AppliedLayouts::SyncVirtualDesktops()
|
|||||||
|
|
||||||
bool dirtyFlag = false;
|
bool dirtyFlag = false;
|
||||||
|
|
||||||
std::vector<FancyZonesDataTypes::DeviceIdData> replaceWithCurrentId{};
|
std::vector<FancyZonesDataTypes::WorkAreaId> replaceWithCurrentId{};
|
||||||
|
|
||||||
for (const auto& [id, data] : m_layouts)
|
for (const auto& [id, data] : m_layouts)
|
||||||
{
|
{
|
||||||
@@ -351,7 +408,7 @@ void AppliedLayouts::RemoveDeletedVirtualDesktops(const std::vector<GUID>& activ
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
std::optional<Layout> AppliedLayouts::GetDeviceLayout(const FancyZonesDataTypes::DeviceIdData& id) const noexcept
|
std::optional<Layout> AppliedLayouts::GetDeviceLayout(const FancyZonesDataTypes::WorkAreaId& id) const noexcept
|
||||||
{
|
{
|
||||||
auto iter = m_layouts.find(id);
|
auto iter = m_layouts.find(id);
|
||||||
if (iter != m_layouts.end())
|
if (iter != m_layouts.end())
|
||||||
@@ -367,19 +424,19 @@ const AppliedLayouts::TAppliedLayoutsMap& AppliedLayouts::GetAppliedLayoutMap()
|
|||||||
return m_layouts;
|
return m_layouts;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool AppliedLayouts::IsLayoutApplied(const FancyZonesDataTypes::DeviceIdData& id) const noexcept
|
bool AppliedLayouts::IsLayoutApplied(const FancyZonesDataTypes::WorkAreaId& id) const noexcept
|
||||||
{
|
{
|
||||||
auto iter = m_layouts.find(id);
|
auto iter = m_layouts.find(id);
|
||||||
return iter != m_layouts.end();
|
return iter != m_layouts.end();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool AppliedLayouts::ApplyLayout(const FancyZonesDataTypes::DeviceIdData& deviceId, Layout layout)
|
bool AppliedLayouts::ApplyLayout(const FancyZonesDataTypes::WorkAreaId& deviceId, Layout layout)
|
||||||
{
|
{
|
||||||
m_layouts[deviceId] = std::move(layout);
|
m_layouts[deviceId] = std::move(layout);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool AppliedLayouts::ApplyDefaultLayout(const FancyZonesDataTypes::DeviceIdData& deviceId)
|
bool AppliedLayouts::ApplyDefaultLayout(const FancyZonesDataTypes::WorkAreaId& deviceId)
|
||||||
{
|
{
|
||||||
Logger::info(L"Set default layout on {}", deviceId.toString());
|
Logger::info(L"Set default layout on {}", deviceId.toString());
|
||||||
|
|
||||||
@@ -408,7 +465,7 @@ bool AppliedLayouts::ApplyDefaultLayout(const FancyZonesDataTypes::DeviceIdData&
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool AppliedLayouts::CloneLayout(const FancyZonesDataTypes::DeviceIdData& srcId, const FancyZonesDataTypes::DeviceIdData& dstId)
|
bool AppliedLayouts::CloneLayout(const FancyZonesDataTypes::WorkAreaId& srcId, const FancyZonesDataTypes::WorkAreaId& dstId)
|
||||||
{
|
{
|
||||||
if (srcId == dstId || m_layouts.find(srcId) == m_layouts.end())
|
if (srcId == dstId || m_layouts.find(srcId) == m_layouts.end())
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -18,6 +18,8 @@ namespace NonLocalizable
|
|||||||
const static wchar_t* DeviceIdID = L"device-id";
|
const static wchar_t* DeviceIdID = L"device-id";
|
||||||
const static wchar_t* DeviceID = L"device";
|
const static wchar_t* DeviceID = L"device";
|
||||||
const static wchar_t* MonitorID = L"monitor";
|
const static wchar_t* MonitorID = L"monitor";
|
||||||
|
const static wchar_t* MonitorInstanceID = L"monitor-instance";
|
||||||
|
const static wchar_t* MonitorSerialNumberID = L"serial-number";
|
||||||
const static wchar_t* VirtualDesktopID = L"virtual-desktop";
|
const static wchar_t* VirtualDesktopID = L"virtual-desktop";
|
||||||
const static wchar_t* AppliedLayoutID = L"applied-layout";
|
const static wchar_t* AppliedLayoutID = L"applied-layout";
|
||||||
const static wchar_t* UuidID = L"uuid";
|
const static wchar_t* UuidID = L"uuid";
|
||||||
@@ -32,7 +34,7 @@ namespace NonLocalizable
|
|||||||
class AppliedLayouts
|
class AppliedLayouts
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
using TAppliedLayoutsMap = std::unordered_map<FancyZonesDataTypes::DeviceIdData, Layout>;
|
using TAppliedLayoutsMap = std::unordered_map<FancyZonesDataTypes::WorkAreaId, Layout>;
|
||||||
|
|
||||||
static AppliedLayouts& instance();
|
static AppliedLayouts& instance();
|
||||||
|
|
||||||
@@ -47,18 +49,19 @@ public:
|
|||||||
|
|
||||||
void LoadData();
|
void LoadData();
|
||||||
void SaveData();
|
void SaveData();
|
||||||
|
void AdjustWorkAreaIds(const std::vector<FancyZonesDataTypes::MonitorId>& ids);
|
||||||
|
|
||||||
void SyncVirtualDesktops();
|
void SyncVirtualDesktops();
|
||||||
void RemoveDeletedVirtualDesktops(const std::vector<GUID>& activeDesktops);
|
void RemoveDeletedVirtualDesktops(const std::vector<GUID>& activeDesktops);
|
||||||
|
|
||||||
std::optional<Layout> GetDeviceLayout(const FancyZonesDataTypes::DeviceIdData& id) const noexcept;
|
std::optional<Layout> GetDeviceLayout(const FancyZonesDataTypes::WorkAreaId& id) const noexcept;
|
||||||
const TAppliedLayoutsMap& GetAppliedLayoutMap() const noexcept;
|
const TAppliedLayoutsMap& GetAppliedLayoutMap() const noexcept;
|
||||||
|
|
||||||
bool IsLayoutApplied(const FancyZonesDataTypes::DeviceIdData& id) const noexcept;
|
bool IsLayoutApplied(const FancyZonesDataTypes::WorkAreaId& id) const noexcept;
|
||||||
|
|
||||||
bool ApplyLayout(const FancyZonesDataTypes::DeviceIdData& deviceId, Layout layout);
|
bool ApplyLayout(const FancyZonesDataTypes::WorkAreaId& deviceId, Layout layout);
|
||||||
bool ApplyDefaultLayout(const FancyZonesDataTypes::DeviceIdData& deviceId);
|
bool ApplyDefaultLayout(const FancyZonesDataTypes::WorkAreaId& deviceId);
|
||||||
bool CloneLayout(const FancyZonesDataTypes::DeviceIdData& srcId, const FancyZonesDataTypes::DeviceIdData& dstId);
|
bool CloneLayout(const FancyZonesDataTypes::WorkAreaId& srcId, const FancyZonesDataTypes::WorkAreaId& dstId);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
AppliedLayouts();
|
AppliedLayouts();
|
||||||
|
|||||||
@@ -128,8 +128,24 @@ namespace FancyZonesDataTypes
|
|||||||
|
|
||||||
return high + 1;
|
return high + 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::wstring DeviceId::toString() const noexcept
|
||||||
|
{
|
||||||
|
return id + L"_" + instanceId;
|
||||||
|
}
|
||||||
|
|
||||||
std::wstring DeviceIdData::toString() const
|
bool DeviceId::isDefault() const noexcept
|
||||||
|
{
|
||||||
|
static const std::wstring defaultMonitorId = L"Default_Monitor";
|
||||||
|
return id == defaultMonitorId;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::wstring MonitorId::toString() const noexcept
|
||||||
|
{
|
||||||
|
return deviceId.toString() + L"_" + serialNumber;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::wstring WorkAreaId::toString() const noexcept
|
||||||
{
|
{
|
||||||
wil::unique_cotaskmem_string virtualDesktopIdStr;
|
wil::unique_cotaskmem_string virtualDesktopIdStr;
|
||||||
if (!SUCCEEDED(StringFromCLSID(virtualDesktopId, &virtualDesktopIdStr)))
|
if (!SUCCEEDED(StringFromCLSID(virtualDesktopId, &virtualDesktopIdStr)))
|
||||||
@@ -137,7 +153,7 @@ namespace FancyZonesDataTypes
|
|||||||
return std::wstring();
|
return std::wstring();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::wstring result = deviceName + L"_" + virtualDesktopIdStr.get();
|
std::wstring result = monitorId.toString() + L"_" + virtualDesktopIdStr.get();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -113,20 +113,38 @@ namespace FancyZonesDataTypes
|
|||||||
ZoneSetLayoutType type;
|
ZoneSetLayoutType type;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct DeviceIdData
|
struct DeviceId
|
||||||
{
|
{
|
||||||
std::wstring deviceName = L"FallbackDevice";
|
std::wstring id;
|
||||||
|
std::wstring instanceId;
|
||||||
|
|
||||||
|
bool isDefault() const noexcept;
|
||||||
|
std::wstring toString() const noexcept;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct MonitorId
|
||||||
|
{
|
||||||
|
HMONITOR monitor;
|
||||||
|
DeviceId deviceId;
|
||||||
|
std::wstring serialNumber;
|
||||||
|
|
||||||
|
std::wstring toString() const noexcept;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct WorkAreaId
|
||||||
|
{
|
||||||
|
MonitorId monitorId;
|
||||||
GUID virtualDesktopId;
|
GUID virtualDesktopId;
|
||||||
|
|
||||||
std::wstring toString() const;
|
std::wstring toString() const noexcept;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct AppZoneHistoryData
|
struct AppZoneHistoryData
|
||||||
{
|
{
|
||||||
std::unordered_map<DWORD, HWND> processIdToHandleMap; // Maps process id(DWORD) of application to zoned window handle(HWND)
|
std::unordered_map<DWORD, HWND> processIdToHandleMap; // Maps process id(DWORD) of application to zoned window handle(HWND)
|
||||||
|
|
||||||
std::wstring zoneSetUuid;
|
std::wstring zoneSetUuid;
|
||||||
DeviceIdData deviceId;
|
WorkAreaId workAreaId;
|
||||||
ZoneIndexSet zoneIndexSet;
|
ZoneIndexSet zoneIndexSet;
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -144,33 +162,86 @@ namespace FancyZonesDataTypes
|
|||||||
return lhs.type == rhs.type && lhs.uuid == rhs.uuid;
|
return lhs.type == rhs.type && lhs.uuid == rhs.uuid;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline bool operator==(const DeviceIdData& lhs, const DeviceIdData& rhs)
|
|
||||||
{
|
|
||||||
return lhs.deviceName.compare(rhs.deviceName) == 0 && (lhs.virtualDesktopId == rhs.virtualDesktopId || lhs.virtualDesktopId == GUID_NULL || rhs.virtualDesktopId == GUID_NULL);
|
|
||||||
}
|
|
||||||
|
|
||||||
inline bool operator!=(const DeviceIdData& lhs, const DeviceIdData& rhs)
|
|
||||||
{
|
|
||||||
return !(lhs == rhs);
|
|
||||||
}
|
|
||||||
|
|
||||||
inline bool operator<(const DeviceIdData& lhs, const DeviceIdData& rhs)
|
|
||||||
{
|
|
||||||
return lhs.deviceName.compare(rhs.deviceName) < 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline bool operator==(const DeviceInfoData& lhs, const DeviceInfoData& rhs)
|
inline bool operator==(const DeviceInfoData& lhs, const DeviceInfoData& rhs)
|
||||||
{
|
{
|
||||||
return lhs.activeZoneSet == rhs.activeZoneSet && lhs.showSpacing == rhs.showSpacing && lhs.spacing == rhs.spacing && lhs.zoneCount == rhs.zoneCount && lhs.sensitivityRadius == rhs.sensitivityRadius;
|
return lhs.activeZoneSet == rhs.activeZoneSet && lhs.showSpacing == rhs.showSpacing && lhs.spacing == rhs.spacing && lhs.zoneCount == rhs.zoneCount && lhs.sensitivityRadius == rhs.sensitivityRadius;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline bool operator==(const DeviceId& lhs, const DeviceId& rhs)
|
||||||
|
{
|
||||||
|
if (lhs.isDefault())
|
||||||
|
{
|
||||||
|
return lhs.instanceId == rhs.instanceId;
|
||||||
|
}
|
||||||
|
|
||||||
|
return lhs.id == rhs.id;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline bool operator<(const DeviceId& lhs, const DeviceId& rhs)
|
||||||
|
{
|
||||||
|
return lhs.id < rhs.id || lhs.instanceId < rhs.instanceId;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline bool operator==(const MonitorId& lhs, const MonitorId& rhs)
|
||||||
|
{
|
||||||
|
if (lhs.monitor && rhs.monitor)
|
||||||
|
{
|
||||||
|
return lhs.monitor == rhs.monitor;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!lhs.serialNumber.empty() || !rhs.serialNumber.empty())
|
||||||
|
{
|
||||||
|
bool serialNumbersEqual = lhs.serialNumber == rhs.serialNumber;
|
||||||
|
if (!serialNumbersEqual)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return lhs.deviceId == rhs.deviceId;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline bool operator==(const WorkAreaId& lhs, const WorkAreaId& rhs)
|
||||||
|
{
|
||||||
|
bool vdEqual = (lhs.virtualDesktopId == rhs.virtualDesktopId || lhs.virtualDesktopId == GUID_NULL || rhs.virtualDesktopId == GUID_NULL);
|
||||||
|
return vdEqual && lhs.monitorId == rhs.monitorId;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline bool operator!=(const WorkAreaId& lhs, const WorkAreaId& rhs)
|
||||||
|
{
|
||||||
|
bool vdEqual = (lhs.virtualDesktopId == rhs.virtualDesktopId || lhs.virtualDesktopId == GUID_NULL || rhs.virtualDesktopId == GUID_NULL);
|
||||||
|
return !vdEqual || lhs.monitorId != rhs.monitorId;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline bool operator<(const WorkAreaId& lhs, const WorkAreaId& rhs)
|
||||||
|
{
|
||||||
|
if (lhs.monitorId.monitor && rhs.monitorId.monitor)
|
||||||
|
{
|
||||||
|
return lhs.monitorId.monitor < rhs.monitorId.monitor;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (lhs.virtualDesktopId != GUID_NULL || rhs.virtualDesktopId != GUID_NULL)
|
||||||
|
{
|
||||||
|
return lhs.virtualDesktopId.Data1 < rhs.virtualDesktopId.Data1 ||
|
||||||
|
lhs.virtualDesktopId.Data2 < rhs.virtualDesktopId.Data2 ||
|
||||||
|
lhs.virtualDesktopId.Data3 < rhs.virtualDesktopId.Data3;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!lhs.monitorId.serialNumber.empty() || rhs.monitorId.serialNumber.empty())
|
||||||
|
{
|
||||||
|
return lhs.monitorId.serialNumber < rhs.monitorId.serialNumber;
|
||||||
|
}
|
||||||
|
|
||||||
|
return lhs.monitorId.deviceId < rhs.monitorId.deviceId;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
namespace std
|
namespace std
|
||||||
{
|
{
|
||||||
template<>
|
template<>
|
||||||
struct hash<FancyZonesDataTypes::DeviceIdData>
|
struct hash<FancyZonesDataTypes::WorkAreaId>
|
||||||
{
|
{
|
||||||
size_t operator()(const FancyZonesDataTypes::DeviceIdData& Value) const
|
size_t operator()(const FancyZonesDataTypes::WorkAreaId& Value) const
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,6 +10,7 @@
|
|||||||
#include <FancyZonesLib/FancyZonesData/LayoutDefaults.h>
|
#include <FancyZonesLib/FancyZonesData/LayoutDefaults.h>
|
||||||
#include <FancyZonesLib/FancyZonesData/LayoutHotkeys.h>
|
#include <FancyZonesLib/FancyZonesData/LayoutHotkeys.h>
|
||||||
#include <FancyZonesLib/FancyZonesData/LayoutTemplates.h>
|
#include <FancyZonesLib/FancyZonesData/LayoutTemplates.h>
|
||||||
|
#include <FancyZonesLib/MonitorUtils.h>
|
||||||
|
|
||||||
#include <common/logger/logger.h>
|
#include <common/logger/logger.h>
|
||||||
|
|
||||||
@@ -272,8 +273,8 @@ namespace
|
|||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
}
|
}
|
||||||
|
|
||||||
data.deviceId = FancyZonesDataTypes::DeviceIdData{
|
data.workAreaId = FancyZonesDataTypes::WorkAreaId{
|
||||||
.deviceName = deviceId->deviceName,
|
.monitorId = { .deviceId = MonitorUtils::Display::ConvertObsoleteDeviceId(deviceId->deviceName) },
|
||||||
.virtualDesktopId = deviceId->virtualDesktopId
|
.virtualDesktopId = deviceId->virtualDesktopId
|
||||||
};
|
};
|
||||||
data.zoneSetUuid = json.GetNamedString(NonLocalizable::ZoneSetUuidStr);
|
data.zoneSetUuid = json.GetNamedString(NonLocalizable::ZoneSetUuidStr);
|
||||||
|
|||||||
@@ -1,49 +1,280 @@
|
|||||||
#include "pch.h"
|
#include "pch.h"
|
||||||
#include "MonitorUtils.h"
|
#include "MonitorUtils.h"
|
||||||
|
|
||||||
|
#include <WbemCli.h>
|
||||||
|
#include <comutil.h>
|
||||||
|
|
||||||
#include <FancyZonesLib/WindowUtils.h>
|
#include <FancyZonesLib/WindowUtils.h>
|
||||||
|
#include <FancyZonesLib/util.h>
|
||||||
|
|
||||||
|
#include <common/logger/logger.h>
|
||||||
|
#include <common/utils/winapi_error.h>
|
||||||
|
|
||||||
namespace MonitorUtils
|
namespace MonitorUtils
|
||||||
{
|
{
|
||||||
constexpr int CUSTOM_POSITIONING_LEFT_TOP_PADDING = 16;
|
constexpr int CUSTOM_POSITIONING_LEFT_TOP_PADDING = 16;
|
||||||
|
|
||||||
inline int RectWidth(const RECT& rect)
|
namespace WMI
|
||||||
{
|
{
|
||||||
return rect.right - rect.left;
|
FancyZonesDataTypes::DeviceId SplitWMIDeviceId(const std::wstring& str) noexcept
|
||||||
}
|
|
||||||
|
|
||||||
inline int RectHeight(const RECT& rect)
|
|
||||||
{
|
|
||||||
return rect.bottom - rect.top;
|
|
||||||
}
|
|
||||||
|
|
||||||
RECT FitOnScreen(const RECT& windowRect, const RECT& originMonitorRect, const RECT& destMonitorRect)
|
|
||||||
{
|
|
||||||
// New window position on active monitor. If window fits the screen, this will be final position.
|
|
||||||
int left = destMonitorRect.left + (windowRect.left - originMonitorRect.left);
|
|
||||||
int top = destMonitorRect.top + (windowRect.top - originMonitorRect.top);
|
|
||||||
int W = RectWidth(windowRect);
|
|
||||||
int H = RectHeight(windowRect);
|
|
||||||
|
|
||||||
if ((left < destMonitorRect.left) || (left + W > destMonitorRect.right))
|
|
||||||
{
|
{
|
||||||
// Set left window border to left border of screen (add padding). Resize window width if needed.
|
// format: DISPLAY\{device id}\{instance id}
|
||||||
left = destMonitorRect.left + CUSTOM_POSITIONING_LEFT_TOP_PADDING;
|
// example: DISPLAY\GSM0001\4&125707d6&0&UID28741_0
|
||||||
W = min(W, RectWidth(destMonitorRect) - CUSTOM_POSITIONING_LEFT_TOP_PADDING);
|
// output: { GSM0001, 4&125707d6&0&UID28741 }
|
||||||
}
|
|
||||||
if ((top < destMonitorRect.top) || (top + H > destMonitorRect.bottom))
|
size_t nameStartPos = str.find_first_of('\\');
|
||||||
{
|
size_t uidStartPos = str.find_last_of('\\');
|
||||||
// Set top window border to top border of screen (add padding). Resize window height if needed.
|
size_t uidEndPos = str.find_last_of('_');
|
||||||
top = destMonitorRect.top + CUSTOM_POSITIONING_LEFT_TOP_PADDING;
|
|
||||||
H = min(H, RectHeight(destMonitorRect) - CUSTOM_POSITIONING_LEFT_TOP_PADDING);
|
if (nameStartPos == std::string::npos || uidStartPos == std::string::npos || uidEndPos == std::string::npos)
|
||||||
|
{
|
||||||
|
return { .id = str };
|
||||||
|
}
|
||||||
|
|
||||||
|
return { .id = str.substr(nameStartPos + 1, uidStartPos - nameStartPos - 1), .instanceId = str.substr(uidStartPos + 1, uidEndPos - uidStartPos - 1) };
|
||||||
}
|
}
|
||||||
|
|
||||||
return { .left = left,
|
std::wstring GetWMIProp(IWbemClassObject* wbemClassObj, std::wstring_view prop)
|
||||||
.top = top,
|
{
|
||||||
.right = left + W,
|
if (!wbemClassObj)
|
||||||
.bottom = top + H };
|
{
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
VARIANT vtProp{};
|
||||||
|
|
||||||
|
// Get the value of the Name property
|
||||||
|
auto hres = wbemClassObj->Get(prop.data(), 0, &vtProp, 0, 0);
|
||||||
|
if (FAILED(hres))
|
||||||
|
{
|
||||||
|
Logger::error(L"Get {} Error code = {} ", prop, get_last_error_or_default(hres));
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
std::wstring result{};
|
||||||
|
switch (vtProp.vt)
|
||||||
|
{
|
||||||
|
case VT_BSTR: //BSTR
|
||||||
|
{
|
||||||
|
result = vtProp.bstrVal;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case VT_ARRAY: // parray
|
||||||
|
case 8195: // also parray
|
||||||
|
{
|
||||||
|
std::u32string str(static_cast<const char32_t*>(vtProp.parray->pvData));
|
||||||
|
std::wstring wstr;
|
||||||
|
for (const char32_t& c : str)
|
||||||
|
{
|
||||||
|
wstr += (wchar_t)c;
|
||||||
|
}
|
||||||
|
|
||||||
|
result = wstr;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
VariantClear(&vtProp);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::vector<FancyZonesDataTypes::MonitorId> GetHardwareMonitorIds()
|
||||||
|
{
|
||||||
|
HRESULT hres;
|
||||||
|
|
||||||
|
// Obtain the initial locator to Windows Management
|
||||||
|
// on a particular host computer.
|
||||||
|
IWbemLocator* pLocator = 0;
|
||||||
|
|
||||||
|
hres = CoCreateInstance(CLSID_WbemLocator, 0, CLSCTX_INPROC_SERVER, IID_IWbemLocator, (LPVOID*)&pLocator);
|
||||||
|
if (FAILED(hres))
|
||||||
|
{
|
||||||
|
Logger::error(L"Failed to create IWbemLocator object. {}", get_last_error_or_default(hres));
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
IWbemServices* pServices = 0;
|
||||||
|
hres = pLocator->ConnectServer(_bstr_t(L"ROOT\\WMI"), NULL, NULL, 0, NULL, 0, 0, &pServices);
|
||||||
|
if (FAILED(hres))
|
||||||
|
{
|
||||||
|
Logger::error(L"Could not connect WMI server. {}", get_last_error_or_default(hres));
|
||||||
|
pLocator->Release();
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set the IWbemServices proxy so that impersonation
|
||||||
|
// of the user (client) occurs.
|
||||||
|
hres = CoSetProxyBlanket(pServices, RPC_C_AUTHN_WINNT, RPC_C_AUTHZ_NONE, NULL, RPC_C_AUTHN_LEVEL_CALL, RPC_C_IMP_LEVEL_IMPERSONATE, NULL, EOAC_NONE);
|
||||||
|
if (FAILED(hres))
|
||||||
|
{
|
||||||
|
Logger::error(L"Could not set proxy blanket. {}", get_last_error_or_default(hres));
|
||||||
|
pServices->Release();
|
||||||
|
pLocator->Release();
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
// Use the IWbemServices pointer to make requests of WMI.
|
||||||
|
// Make requests here:
|
||||||
|
IEnumWbemClassObject* pEnumerator = NULL;
|
||||||
|
hres = pServices->ExecQuery(bstr_t("WQL"), bstr_t("SELECT * FROM WmiMonitorID"), WBEM_FLAG_FORWARD_ONLY | WBEM_FLAG_RETURN_IMMEDIATELY, NULL, &pEnumerator);
|
||||||
|
if (FAILED(hres))
|
||||||
|
{
|
||||||
|
Logger::error(L"Query for monitors failed. {}", get_last_error_or_default(hres));
|
||||||
|
pServices->Release();
|
||||||
|
pLocator->Release();
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
IWbemClassObject* pClassObject;
|
||||||
|
ULONG uReturn = 0;
|
||||||
|
|
||||||
|
std::vector<FancyZonesDataTypes::MonitorId> result{};
|
||||||
|
while (pEnumerator)
|
||||||
|
{
|
||||||
|
hres = pEnumerator->Next(WBEM_INFINITE, 1, &pClassObject, &uReturn);
|
||||||
|
|
||||||
|
if (0 == uReturn)
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
LPSAFEARRAY pFieldArray = NULL;
|
||||||
|
hres = pClassObject->GetNames(NULL, WBEM_FLAG_ALWAYS, NULL, &pFieldArray);
|
||||||
|
if (FAILED(hres))
|
||||||
|
{
|
||||||
|
Logger::error(L"Failed to get field names. {}", get_last_error_or_default(hres));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto name = GetWMIProp(pClassObject, L"InstanceName");
|
||||||
|
|
||||||
|
FancyZonesDataTypes::MonitorId data{};
|
||||||
|
data.deviceId = SplitWMIDeviceId(name);
|
||||||
|
data.serialNumber = GetWMIProp(pClassObject, L"SerialNumberID");
|
||||||
|
|
||||||
|
Logger::info(L"InstanceName: {}", name);
|
||||||
|
Logger::info(L"Serial number: {}", data.serialNumber);
|
||||||
|
|
||||||
|
result.emplace_back(std::move(data));
|
||||||
|
|
||||||
|
pClassObject->Release();
|
||||||
|
pClassObject = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
pServices->Release();
|
||||||
|
pLocator->Release();
|
||||||
|
pEnumerator->Release();
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
namespace Display
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::DeviceId SplitDisplayDeviceId(const std::wstring& str) noexcept
|
||||||
|
{
|
||||||
|
// format: \\?\DISPLAY#{device id}#{instance id}#{some other id}
|
||||||
|
// example: \\?\DISPLAY#GSM1388#4&125707d6&0&UID8388688#{e6f07b5f-ee97-4a90-b076-33f57bf4eaa7}
|
||||||
|
// output: { GSM1388, 4&125707d6&0&UID8388688 }
|
||||||
|
|
||||||
|
size_t nameStartPos = str.find_first_of('#');
|
||||||
|
size_t uidStartPos = str.find('#', nameStartPos + 1);
|
||||||
|
size_t uidEndPos = str.find('#', uidStartPos + 1);
|
||||||
|
|
||||||
|
if (nameStartPos == std::string::npos || uidStartPos == std::string::npos || uidEndPos == std::string::npos)
|
||||||
|
{
|
||||||
|
return { str, L"" };
|
||||||
|
}
|
||||||
|
|
||||||
|
return { .id = str.substr(nameStartPos + 1, uidStartPos - nameStartPos - 1), .instanceId = str.substr(uidStartPos + 1, uidEndPos - uidStartPos - 1) };
|
||||||
|
}
|
||||||
|
|
||||||
|
FancyZonesDataTypes::DeviceId ConvertObsoleteDeviceId(const std::wstring& str) noexcept
|
||||||
|
{
|
||||||
|
// format: {device id}#{instance id}
|
||||||
|
// example: GSM1388#4&125707d6&0&UID8388688
|
||||||
|
// output: { GSM1388, 4&125707d6&0&UID8388688 }
|
||||||
|
|
||||||
|
size_t dividerPos = str.find_first_of('#');
|
||||||
|
|
||||||
|
if (dividerPos == std::string::npos)
|
||||||
|
{
|
||||||
|
return { str, L"" };
|
||||||
|
}
|
||||||
|
|
||||||
|
return { .id = str.substr(0, dividerPos), .instanceId = str.substr(dividerPos + 1) };
|
||||||
|
}
|
||||||
|
|
||||||
|
std::vector<FancyZonesDataTypes::MonitorId> GetDisplays()
|
||||||
|
{
|
||||||
|
auto allMonitors = FancyZonesUtils::GetAllMonitorInfo<&MONITORINFOEX::rcWork>();
|
||||||
|
std::unordered_map<std::wstring, DWORD> displayDeviceIdxMap;
|
||||||
|
std::vector<FancyZonesDataTypes::MonitorId> result{};
|
||||||
|
|
||||||
|
for (auto& monitorData : allMonitors)
|
||||||
|
{
|
||||||
|
auto monitorInfo = monitorData.second;
|
||||||
|
|
||||||
|
DISPLAY_DEVICE displayDevice{ .cb = sizeof(displayDevice) };
|
||||||
|
std::wstring deviceId;
|
||||||
|
auto enumRes = EnumDisplayDevicesW(monitorInfo.szDevice, displayDeviceIdxMap[monitorInfo.szDevice], &displayDevice, EDD_GET_DEVICE_INTERFACE_NAME);
|
||||||
|
|
||||||
|
if (!enumRes)
|
||||||
|
{
|
||||||
|
Logger::error(L"EnumDisplayDevicesW error: {}", get_last_error_or_default(GetLastError()));
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
Logger::info(L"Display: {}", displayDevice.DeviceID);
|
||||||
|
result.push_back({ .monitor = monitorData.first, .deviceId = SplitDisplayDeviceId(displayDevice.DeviceID) });
|
||||||
|
}
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
namespace
|
||||||
|
{
|
||||||
|
inline int RectWidth(const RECT& rect)
|
||||||
|
{
|
||||||
|
return rect.right - rect.left;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline int RectHeight(const RECT& rect)
|
||||||
|
{
|
||||||
|
return rect.bottom - rect.top;
|
||||||
|
}
|
||||||
|
|
||||||
|
RECT FitOnScreen(const RECT& windowRect, const RECT& originMonitorRect, const RECT& destMonitorRect)
|
||||||
|
{
|
||||||
|
// New window position on active monitor. If window fits the screen, this will be final position.
|
||||||
|
int left = destMonitorRect.left + (windowRect.left - originMonitorRect.left);
|
||||||
|
int top = destMonitorRect.top + (windowRect.top - originMonitorRect.top);
|
||||||
|
int W = RectWidth(windowRect);
|
||||||
|
int H = RectHeight(windowRect);
|
||||||
|
|
||||||
|
if ((left < destMonitorRect.left) || (left + W > destMonitorRect.right))
|
||||||
|
{
|
||||||
|
// Set left window border to left border of screen (add padding). Resize window width if needed.
|
||||||
|
left = destMonitorRect.left + CUSTOM_POSITIONING_LEFT_TOP_PADDING;
|
||||||
|
W = min(W, RectWidth(destMonitorRect) - CUSTOM_POSITIONING_LEFT_TOP_PADDING);
|
||||||
|
}
|
||||||
|
if ((top < destMonitorRect.top) || (top + H > destMonitorRect.bottom))
|
||||||
|
{
|
||||||
|
// Set top window border to top border of screen (add padding). Resize window height if needed.
|
||||||
|
top = destMonitorRect.top + CUSTOM_POSITIONING_LEFT_TOP_PADDING;
|
||||||
|
H = min(H, RectHeight(destMonitorRect) - CUSTOM_POSITIONING_LEFT_TOP_PADDING);
|
||||||
|
}
|
||||||
|
|
||||||
|
return { .left = left,
|
||||||
|
.top = top,
|
||||||
|
.right = left + W,
|
||||||
|
.bottom = top + H };
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void OpenWindowOnActiveMonitor(HWND window, HMONITOR monitor) noexcept
|
void OpenWindowOnActiveMonitor(HWND window, HMONITOR monitor) noexcept
|
||||||
{
|
{
|
||||||
// By default Windows opens new window on primary monitor.
|
// By default Windows opens new window on primary monitor.
|
||||||
@@ -73,4 +304,25 @@ namespace MonitorUtils
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::vector<FancyZonesDataTypes::MonitorId> IdentifyMonitors() noexcept
|
||||||
|
{
|
||||||
|
Logger::info(L"Identifying monitors");
|
||||||
|
|
||||||
|
auto displays = Display::GetDisplays();
|
||||||
|
auto monitors = WMI::GetHardwareMonitorIds();
|
||||||
|
|
||||||
|
for (const auto& monitor : monitors)
|
||||||
|
{
|
||||||
|
for (auto& display : displays)
|
||||||
|
{
|
||||||
|
if (monitor.deviceId.id == display.deviceId.id)
|
||||||
|
{
|
||||||
|
display.serialNumber = monitor.serialNumber;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return displays;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@@ -1,6 +1,22 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
#include <FancyZonesLib/FancyZonesDataTypes.h>
|
||||||
|
|
||||||
namespace MonitorUtils
|
namespace MonitorUtils
|
||||||
{
|
{
|
||||||
|
namespace Display
|
||||||
|
{
|
||||||
|
std::vector<FancyZonesDataTypes::MonitorId> GetDisplays();
|
||||||
|
FancyZonesDataTypes::DeviceId SplitDisplayDeviceId(const std::wstring& str) noexcept;
|
||||||
|
FancyZonesDataTypes::DeviceId ConvertObsoleteDeviceId(const std::wstring& str) noexcept;
|
||||||
|
}
|
||||||
|
|
||||||
|
namespace WMI
|
||||||
|
{
|
||||||
|
std::vector<FancyZonesDataTypes::MonitorId> GetHardwareMonitorIds();
|
||||||
|
FancyZonesDataTypes::DeviceId SplitWMIDeviceId(const std::wstring& str) noexcept;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::vector<FancyZonesDataTypes::MonitorId> IdentifyMonitors() noexcept;
|
||||||
void OpenWindowOnActiveMonitor(HWND window, HMONITOR monitor) noexcept;
|
void OpenWindowOnActiveMonitor(HWND window, HMONITOR monitor) noexcept;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -120,7 +120,7 @@ WorkArea::~WorkArea()
|
|||||||
windowPool.FreeZonesOverlayWindow(m_window);
|
windowPool.FreeZonesOverlayWindow(m_window);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool WorkArea::Init(HINSTANCE hinstance, const FancyZonesDataTypes::DeviceIdData& uniqueId, const FancyZonesDataTypes::DeviceIdData& parentUniqueId)
|
bool WorkArea::Init(HINSTANCE hinstance, const FancyZonesDataTypes::WorkAreaId& uniqueId, const FancyZonesDataTypes::WorkAreaId& parentUniqueId)
|
||||||
{
|
{
|
||||||
m_uniqueId = uniqueId;
|
m_uniqueId = uniqueId;
|
||||||
InitializeZoneSets(parentUniqueId);
|
InitializeZoneSets(parentUniqueId);
|
||||||
@@ -378,13 +378,9 @@ void WorkArea::FlashZones() noexcept
|
|||||||
|
|
||||||
#pragma region private
|
#pragma region private
|
||||||
|
|
||||||
void WorkArea::InitializeZoneSets(const FancyZonesDataTypes::DeviceIdData& parentUniqueId) noexcept
|
void WorkArea::InitializeZoneSets(const FancyZonesDataTypes::WorkAreaId& parentUniqueId) noexcept
|
||||||
{
|
{
|
||||||
wil::unique_cotaskmem_string virtualDesktopId;
|
Logger::info(L"Initialize layout on {}", m_uniqueId.toString());
|
||||||
if (SUCCEEDED(StringFromCLSID(m_uniqueId.virtualDesktopId, &virtualDesktopId)))
|
|
||||||
{
|
|
||||||
Logger::debug(L"Initialize layout on the virtual desktop {}", virtualDesktopId.get());
|
|
||||||
}
|
|
||||||
|
|
||||||
bool isLayoutAlreadyApplied = AppliedLayouts::instance().IsLayoutApplied(m_uniqueId);
|
bool isLayoutAlreadyApplied = AppliedLayouts::instance().IsLayoutApplied(m_uniqueId);
|
||||||
if (!isLayoutAlreadyApplied)
|
if (!isLayoutAlreadyApplied)
|
||||||
|
|||||||
@@ -13,7 +13,7 @@ public:
|
|||||||
~WorkArea();
|
~WorkArea();
|
||||||
|
|
||||||
public:
|
public:
|
||||||
bool Init(HINSTANCE hinstance, const FancyZonesDataTypes::DeviceIdData& uniqueId, const FancyZonesDataTypes::DeviceIdData& parentUniqueId);
|
bool Init(HINSTANCE hinstance, const FancyZonesDataTypes::WorkAreaId& uniqueId, const FancyZonesDataTypes::WorkAreaId& parentUniqueId);
|
||||||
inline bool InitWorkAreaRect(HMONITOR monitor)
|
inline bool InitWorkAreaRect(HMONITOR monitor)
|
||||||
{
|
{
|
||||||
m_monitor = monitor;
|
m_monitor = monitor;
|
||||||
@@ -42,7 +42,7 @@ public:
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
FancyZonesDataTypes::DeviceIdData UniqueId() const noexcept { return { m_uniqueId }; }
|
FancyZonesDataTypes::WorkAreaId UniqueId() const noexcept { return { m_uniqueId }; }
|
||||||
IZoneSet* ZoneSet() const noexcept { return m_zoneSet.get(); }
|
IZoneSet* ZoneSet() const noexcept { return m_zoneSet.get(); }
|
||||||
|
|
||||||
ZoneIndexSet GetWindowZoneIndexes(HWND window) const noexcept;
|
ZoneIndexSet GetWindowZoneIndexes(HWND window) const noexcept;
|
||||||
@@ -72,7 +72,7 @@ protected:
|
|||||||
static LRESULT CALLBACK s_WndProc(HWND window, UINT message, WPARAM wparam, LPARAM lparam) noexcept;
|
static LRESULT CALLBACK s_WndProc(HWND window, UINT message, WPARAM wparam, LPARAM lparam) noexcept;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void InitializeZoneSets(const FancyZonesDataTypes::DeviceIdData& parentUniqueId) noexcept;
|
void InitializeZoneSets(const FancyZonesDataTypes::WorkAreaId& parentUniqueId) noexcept;
|
||||||
void CalculateZoneSet(OverlappingZonesAlgorithm overlappingAlgorithm) noexcept;
|
void CalculateZoneSet(OverlappingZonesAlgorithm overlappingAlgorithm) noexcept;
|
||||||
void UpdateActiveZoneSet(_In_opt_ IZoneSet* zoneSet) noexcept;
|
void UpdateActiveZoneSet(_In_opt_ IZoneSet* zoneSet) noexcept;
|
||||||
LRESULT WndProc(UINT message, WPARAM wparam, LPARAM lparam) noexcept;
|
LRESULT WndProc(UINT message, WPARAM wparam, LPARAM lparam) noexcept;
|
||||||
@@ -82,7 +82,7 @@ private:
|
|||||||
HMONITOR m_monitor{};
|
HMONITOR m_monitor{};
|
||||||
FancyZonesUtils::Rect m_workAreaRect{};
|
FancyZonesUtils::Rect m_workAreaRect{};
|
||||||
|
|
||||||
FancyZonesDataTypes::DeviceIdData m_uniqueId;
|
FancyZonesDataTypes::WorkAreaId m_uniqueId;
|
||||||
HWND m_window{}; // Hidden tool window used to represent current monitor desktop work area.
|
HWND m_window{}; // Hidden tool window used to represent current monitor desktop work area.
|
||||||
HWND m_windowMoveSize{};
|
HWND m_windowMoveSize{};
|
||||||
winrt::com_ptr<IZoneSet> m_zoneSet;
|
winrt::com_ptr<IZoneSet> m_zoneSet;
|
||||||
@@ -93,7 +93,7 @@ private:
|
|||||||
std::unique_ptr<ZonesOverlay> m_zonesOverlay;
|
std::unique_ptr<ZonesOverlay> m_zonesOverlay;
|
||||||
};
|
};
|
||||||
|
|
||||||
inline std::shared_ptr<WorkArea> MakeWorkArea(HINSTANCE hinstance, HMONITOR monitor, const FancyZonesDataTypes::DeviceIdData& uniqueId, const FancyZonesDataTypes::DeviceIdData& parentUniqueId) noexcept
|
inline std::shared_ptr<WorkArea> MakeWorkArea(HINSTANCE hinstance, HMONITOR monitor, const FancyZonesDataTypes::WorkAreaId& uniqueId, const FancyZonesDataTypes::WorkAreaId& parentUniqueId) noexcept
|
||||||
{
|
{
|
||||||
auto self = std::make_shared<WorkArea>(hinstance);
|
auto self = std::make_shared<WorkArea>(hinstance);
|
||||||
if (!self->InitWorkAreaRect(monitor))
|
if (!self->InitWorkAreaRect(monitor))
|
||||||
|
|||||||
@@ -16,63 +16,8 @@
|
|||||||
|
|
||||||
namespace FancyZonesUtils
|
namespace FancyZonesUtils
|
||||||
{
|
{
|
||||||
std::wstring TrimDeviceId(const std::wstring& deviceId)
|
|
||||||
{
|
|
||||||
// We're interested in the unique part between the first and last #'s
|
|
||||||
// Example input: \\?\DISPLAY#DELA026#5&10a58c63&0&UID16777488#{e6f07b5f-ee97-4a90-b076-33f57bf4eaa7}
|
|
||||||
// Example output: DELA026#5&10a58c63&0&UID16777488
|
|
||||||
static const std::wstring defaultDeviceId = L"FallbackDevice";
|
|
||||||
if (deviceId.empty())
|
|
||||||
{
|
|
||||||
return defaultDeviceId;
|
|
||||||
}
|
|
||||||
|
|
||||||
size_t start = deviceId.find(L'#');
|
|
||||||
size_t end = deviceId.rfind(L'#');
|
|
||||||
if (start != std::wstring::npos && end != std::wstring::npos && start != end)
|
|
||||||
{
|
|
||||||
size_t size = end - (start + 1);
|
|
||||||
return deviceId.substr(start + 1, size);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
return defaultDeviceId;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
typedef BOOL(WINAPI* GetDpiForMonitorInternalFunc)(HMONITOR, UINT, UINT*, UINT*);
|
typedef BOOL(WINAPI* GetDpiForMonitorInternalFunc)(HMONITOR, UINT, UINT*, UINT*);
|
||||||
|
|
||||||
std::wstring GetDisplayDeviceId(const std::wstring& device, std::unordered_map<std::wstring, DWORD>& displayDeviceIdxMap)
|
|
||||||
{
|
|
||||||
DISPLAY_DEVICE displayDevice{ .cb = sizeof(displayDevice) };
|
|
||||||
std::wstring deviceId;
|
|
||||||
while (EnumDisplayDevicesW(device.c_str(), displayDeviceIdxMap[device], &displayDevice, EDD_GET_DEVICE_INTERFACE_NAME))
|
|
||||||
{
|
|
||||||
++displayDeviceIdxMap[device];
|
|
||||||
|
|
||||||
Logger::info(L"Get display device: {}", displayDevice.DeviceID);
|
|
||||||
|
|
||||||
// Only take active monitors (presented as being "on" by the respective GDI view) and monitors that don't
|
|
||||||
// represent a pseudo device used to mirror application drawing.
|
|
||||||
if (WI_IsFlagSet(displayDevice.StateFlags, DISPLAY_DEVICE_ACTIVE) &&
|
|
||||||
WI_IsFlagClear(displayDevice.StateFlags, DISPLAY_DEVICE_MIRRORING_DRIVER))
|
|
||||||
{
|
|
||||||
deviceId = displayDevice.DeviceID;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (deviceId.empty())
|
|
||||||
{
|
|
||||||
Logger::info(L"Didn't find display device, set default");
|
|
||||||
deviceId = GetSystemMetrics(SM_REMOTESESSION) ?
|
|
||||||
L"\\\\?\\DISPLAY#REMOTEDISPLAY#" :
|
|
||||||
L"\\\\?\\DISPLAY#LOCALDISPLAY#";
|
|
||||||
}
|
|
||||||
|
|
||||||
return deviceId;
|
|
||||||
}
|
|
||||||
|
|
||||||
UINT GetDpiForMonitor(HMONITOR monitor) noexcept
|
UINT GetDpiForMonitor(HMONITOR monitor) noexcept
|
||||||
{
|
{
|
||||||
UINT dpi{};
|
UINT dpi{};
|
||||||
@@ -206,37 +151,6 @@ namespace FancyZonesUtils
|
|||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::wstring GenerateUniqueId(HMONITOR monitor, const std::wstring& deviceId, const std::wstring& virtualDesktopId)
|
|
||||||
{
|
|
||||||
MONITORINFOEXW mi;
|
|
||||||
mi.cbSize = sizeof(mi);
|
|
||||||
if (!virtualDesktopId.empty() && GetMonitorInfo(monitor, &mi))
|
|
||||||
{
|
|
||||||
Rect const monitorRect(mi.rcMonitor);
|
|
||||||
// Unique identifier format: <parsed-device-id>_<width>_<height>_<virtual-desktop-id>
|
|
||||||
return TrimDeviceId(deviceId) +
|
|
||||||
L'_' +
|
|
||||||
virtualDesktopId;
|
|
||||||
}
|
|
||||||
return {};
|
|
||||||
}
|
|
||||||
|
|
||||||
std::wstring GenerateUniqueIdAllMonitorsArea(const std::wstring& virtualDesktopId)
|
|
||||||
{
|
|
||||||
std::wstring result{ ZonedWindowProperties::MultiMonitorDeviceID };
|
|
||||||
|
|
||||||
RECT combinedResolution = GetAllMonitorsCombinedRect<&MONITORINFO::rcMonitor>();
|
|
||||||
|
|
||||||
result += L'_';
|
|
||||||
result += std::to_wstring(combinedResolution.right - combinedResolution.left);
|
|
||||||
result += L'_';
|
|
||||||
result += std::to_wstring(combinedResolution.bottom - combinedResolution.top);
|
|
||||||
result += L'_';
|
|
||||||
result += virtualDesktopId;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
size_t ChooseNextZoneByPosition(DWORD vkCode, RECT windowRect, const std::vector<RECT>& zoneRects) noexcept
|
size_t ChooseNextZoneByPosition(DWORD vkCode, RECT windowRect, const std::vector<RECT>& zoneRects) noexcept
|
||||||
{
|
{
|
||||||
using complex = std::complex<double>;
|
using complex = std::complex<double>;
|
||||||
|
|||||||
@@ -168,8 +168,6 @@ namespace FancyZonesUtils
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::wstring GetDisplayDeviceId(const std::wstring& device, std::unordered_map<std::wstring, DWORD>& displayDeviceIdxMap);
|
|
||||||
|
|
||||||
UINT GetDpiForMonitor(HMONITOR monitor) noexcept;
|
UINT GetDpiForMonitor(HMONITOR monitor) noexcept;
|
||||||
void OrderMonitors(std::vector<std::pair<HMONITOR, RECT>>& monitorInfo);
|
void OrderMonitors(std::vector<std::pair<HMONITOR, RECT>>& monitorInfo);
|
||||||
|
|
||||||
@@ -177,10 +175,6 @@ namespace FancyZonesUtils
|
|||||||
std::optional<GUID> GuidFromString(const std::wstring& str) noexcept;
|
std::optional<GUID> GuidFromString(const std::wstring& str) noexcept;
|
||||||
std::optional<std::wstring> GuidToString(const GUID& guid) noexcept;
|
std::optional<std::wstring> GuidToString(const GUID& guid) noexcept;
|
||||||
|
|
||||||
std::wstring GenerateUniqueId(HMONITOR monitor, const std::wstring& devideId, const std::wstring& virtualDesktopId);
|
|
||||||
std::wstring GenerateUniqueIdAllMonitorsArea(const std::wstring& virtualDesktopId);
|
|
||||||
std::wstring TrimDeviceId(const std::wstring& deviceId);
|
|
||||||
|
|
||||||
RECT PrepareRectForCycling(RECT windowRect, RECT workAreaRect, DWORD vkCode) noexcept;
|
RECT PrepareRectForCycling(RECT windowRect, RECT workAreaRect, DWORD vkCode) noexcept;
|
||||||
size_t ChooseNextZoneByPosition(DWORD vkCode, RECT windowRect, const std::vector<RECT>& zoneRects) noexcept;
|
size_t ChooseNextZoneByPosition(DWORD vkCode, RECT windowRect, const std::vector<RECT>& zoneRects) noexcept;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -33,7 +33,7 @@
|
|||||||
</ClCompile>
|
</ClCompile>
|
||||||
<Link>
|
<Link>
|
||||||
<OutputFile>$(OutDir)$(TargetName)$(TargetExt)</OutputFile>
|
<OutputFile>$(OutDir)$(TargetName)$(TargetExt)</OutputFile>
|
||||||
<AdditionalDependencies>gdiplus.lib;dwmapi.lib;shlwapi.lib;uxtheme.lib;shcore.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
<AdditionalDependencies>gdiplus.lib;dwmapi.lib;shlwapi.lib;uxtheme.lib;shcore.lib;wbemuuid.lib;comsuppw.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
||||||
</Link>
|
</Link>
|
||||||
</ItemDefinitionGroup>
|
</ItemDefinitionGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|||||||
@@ -102,22 +102,22 @@ namespace FancyZonesUnitTests
|
|||||||
Assert::AreEqual((size_t)2, AppZoneHistory::instance().GetFullAppZoneHistory().size());
|
Assert::AreEqual((size_t)2, AppZoneHistory::instance().GetFullAppZoneHistory().size());
|
||||||
|
|
||||||
{
|
{
|
||||||
FancyZonesDataTypes::DeviceIdData id{
|
FancyZonesDataTypes::WorkAreaId id{
|
||||||
.deviceName = L"monitor-1",
|
.monitorId = { .deviceId = { .id = L"monitor-1" } },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{72FA9FC0-26A6-4B37-A834-491C148DFC58}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{72FA9FC0-26A6-4B37-A834-491C148DFC58}").value()
|
||||||
};
|
};
|
||||||
Assert::IsTrue(AppZoneHistory::instance().GetZoneHistory(L"app-1", id).has_value());
|
Assert::IsTrue(AppZoneHistory::instance().GetZoneHistory(L"app-1", id).has_value());
|
||||||
}
|
}
|
||||||
{
|
{
|
||||||
FancyZonesDataTypes::DeviceIdData id{
|
FancyZonesDataTypes::WorkAreaId id{
|
||||||
.deviceName = L"monitor-2",
|
.monitorId = { .deviceId = { .id = L"monitor-2" } },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{72FA9FC0-26A6-4B37-A834-491C148DFC58}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{72FA9FC0-26A6-4B37-A834-491C148DFC58}").value()
|
||||||
};
|
};
|
||||||
Assert::IsTrue(AppZoneHistory::instance().GetZoneHistory(L"app-1", id).has_value());
|
Assert::IsTrue(AppZoneHistory::instance().GetZoneHistory(L"app-1", id).has_value());
|
||||||
}
|
}
|
||||||
{
|
{
|
||||||
FancyZonesDataTypes::DeviceIdData id{
|
FancyZonesDataTypes::WorkAreaId id{
|
||||||
.deviceName = L"monitor-1",
|
.monitorId = { .deviceId = { .id = L"monitor-1" } },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{72FA9FC0-26A6-4B37-A834-491C148DFC58}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{72FA9FC0-26A6-4B37-A834-491C148DFC58}").value()
|
||||||
};
|
};
|
||||||
Assert::IsTrue(AppZoneHistory::instance().GetZoneHistory(L"app-2", id).has_value());
|
Assert::IsTrue(AppZoneHistory::instance().GetZoneHistory(L"app-2", id).has_value());
|
||||||
@@ -197,8 +197,8 @@ namespace FancyZonesUnitTests
|
|||||||
Assert::AreEqual((size_t)1, AppZoneHistory::instance().GetFullAppZoneHistory().size());
|
Assert::AreEqual((size_t)1, AppZoneHistory::instance().GetFullAppZoneHistory().size());
|
||||||
|
|
||||||
{
|
{
|
||||||
FancyZonesDataTypes::DeviceIdData id{
|
FancyZonesDataTypes::WorkAreaId id{
|
||||||
.deviceName = L"monitor-1",
|
.monitorId = { .deviceId = { .id = L"monitor-1" } },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{72FA9FC0-26A6-4B37-A834-491C148DFC58}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{72FA9FC0-26A6-4B37-A834-491C148DFC58}").value()
|
||||||
};
|
};
|
||||||
Assert::IsTrue(AppZoneHistory::instance().GetZoneHistory(L"app-1", id).has_value());
|
Assert::IsTrue(AppZoneHistory::instance().GetZoneHistory(L"app-1", id).has_value());
|
||||||
@@ -208,103 +208,136 @@ namespace FancyZonesUnitTests
|
|||||||
TEST_METHOD (AppLastZoneInvalidWindow)
|
TEST_METHOD (AppLastZoneInvalidWindow)
|
||||||
{
|
{
|
||||||
const std::wstring zoneSetId = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
const std::wstring zoneSetId = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
||||||
const FancyZonesDataTypes::DeviceIdData deviceId{ L"DELA026#5&10a58c63&0&UID16777488_2194_1234_{39B25DD2-130D-4B5D-8851-4791D66B1539}" };
|
const FancyZonesDataTypes::WorkAreaId workAreaId{
|
||||||
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" } },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}").value()
|
||||||
|
};
|
||||||
const auto window = Mocks::Window();
|
const auto window = Mocks::Window();
|
||||||
|
|
||||||
Assert::IsTrue(std::vector<ZoneIndex>{} == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, deviceId, zoneSetId));
|
Assert::IsTrue(std::vector<ZoneIndex>{} == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, workAreaId, zoneSetId));
|
||||||
|
|
||||||
const int expectedZoneIndex = 1;
|
const int expectedZoneIndex = 1;
|
||||||
Assert::IsFalse(AppZoneHistory::instance().SetAppLastZones(window, deviceId, zoneSetId, { expectedZoneIndex }));
|
Assert::IsFalse(AppZoneHistory::instance().SetAppLastZones(window, workAreaId, zoneSetId, { expectedZoneIndex }));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD (AppLastZoneNullWindow)
|
TEST_METHOD (AppLastZoneNullWindow)
|
||||||
{
|
{
|
||||||
const std::wstring zoneSetId = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
const std::wstring zoneSetId = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
||||||
const FancyZonesDataTypes::DeviceIdData deviceId{ L"DELA026#5&10a58c63&0&UID16777488_2194_1234_{39B25DD2-130D-4B5D-8851-4791D66B1539}" };
|
const FancyZonesDataTypes::WorkAreaId workAreaId{
|
||||||
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" } },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}").value()
|
||||||
|
};
|
||||||
const auto window = nullptr;
|
const auto window = nullptr;
|
||||||
|
|
||||||
const int expectedZoneIndex = 1;
|
const int expectedZoneIndex = 1;
|
||||||
Assert::IsFalse(AppZoneHistory::instance().SetAppLastZones(window, deviceId, zoneSetId, { expectedZoneIndex }));
|
Assert::IsFalse(AppZoneHistory::instance().SetAppLastZones(window, workAreaId, zoneSetId, { expectedZoneIndex }));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD (AppLastdeviceIdTest)
|
TEST_METHOD (AppLastdeviceIdTest)
|
||||||
{
|
{
|
||||||
const std::wstring zoneSetId = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
const std::wstring zoneSetId = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
||||||
const FancyZonesDataTypes::DeviceIdData deviceId1{ L"DELA026#5&10a58c63&0&UID16777488_2194_1234_{39B25DD2-130D-4B5D-8851-4791D66B1539}" };
|
const FancyZonesDataTypes::WorkAreaId workAreaId1{
|
||||||
const FancyZonesDataTypes::DeviceIdData deviceId2{ L"DELA026#5&10a58c63&0&UID16777489_2194_1234_{39B25DD2-130D-4B5D-8851-4791D66B1539}" };
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" } },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}").value()
|
||||||
|
};
|
||||||
|
const FancyZonesDataTypes::WorkAreaId workAreaId2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"DELA027", .instanceId = L"5&10a58c63&0&UID16777489" } },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}").value()
|
||||||
|
};
|
||||||
const auto window = Mocks::WindowCreate(m_hInst);
|
const auto window = Mocks::WindowCreate(m_hInst);
|
||||||
|
|
||||||
const int expectedZoneIndex = 10;
|
const int expectedZoneIndex = 10;
|
||||||
Assert::IsTrue(AppZoneHistory::instance().SetAppLastZones(window, deviceId1, zoneSetId, { expectedZoneIndex }));
|
Assert::IsTrue(AppZoneHistory::instance().SetAppLastZones(window, workAreaId1, zoneSetId, { expectedZoneIndex }));
|
||||||
Assert::IsTrue(std::vector<ZoneIndex>{ expectedZoneIndex } == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, deviceId1, zoneSetId));
|
Assert::IsTrue(std::vector<ZoneIndex>{ expectedZoneIndex } == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, workAreaId1, zoneSetId));
|
||||||
Assert::IsTrue(std::vector<ZoneIndex>{} == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, deviceId2, zoneSetId));
|
Assert::IsTrue(std::vector<ZoneIndex>{} == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, workAreaId2, zoneSetId));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD (AppLastZoneSetIdTest)
|
TEST_METHOD (AppLastZoneSetIdTest)
|
||||||
{
|
{
|
||||||
const std::wstring zoneSetId1 = L"{B7A1F5A9-9DC2-4505-84AB-993253839093}";
|
const std::wstring zoneSetId1 = L"{B7A1F5A9-9DC2-4505-84AB-993253839093}";
|
||||||
const std::wstring zoneSetId2 = L"{B7A1F5A9-9DC2-4505-84AB-993253839094}";
|
const std::wstring zoneSetId2 = L"{B7A1F5A9-9DC2-4505-84AB-993253839094}";
|
||||||
const FancyZonesDataTypes::DeviceIdData deviceId{ L"DELA026#5&10a58c63&0&UID16777488_2194_1234_{39B25DD2-130D-4B5D-8851-4791D66B1539}" };
|
const FancyZonesDataTypes::WorkAreaId workAreaId{
|
||||||
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" } },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}").value()
|
||||||
|
};
|
||||||
const auto window = Mocks::WindowCreate(m_hInst);
|
const auto window = Mocks::WindowCreate(m_hInst);
|
||||||
|
|
||||||
const int expectedZoneIndex = 10;
|
const int expectedZoneIndex = 10;
|
||||||
Assert::IsTrue(AppZoneHistory::instance().SetAppLastZones(window, deviceId, zoneSetId1, { expectedZoneIndex }));
|
Assert::IsTrue(AppZoneHistory::instance().SetAppLastZones(window, workAreaId, zoneSetId1, { expectedZoneIndex }));
|
||||||
Assert::IsTrue(std::vector<ZoneIndex>{ expectedZoneIndex } == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, deviceId, zoneSetId1));
|
Assert::IsTrue(std::vector<ZoneIndex>{ expectedZoneIndex } == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, workAreaId, zoneSetId1));
|
||||||
Assert::IsTrue(std::vector<ZoneIndex>{} == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, deviceId, zoneSetId2));
|
Assert::IsTrue(std::vector<ZoneIndex>{} == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, workAreaId, zoneSetId2));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD (AppLastZoneRemoveWindow)
|
TEST_METHOD (AppLastZoneRemoveWindow)
|
||||||
{
|
{
|
||||||
const std::wstring zoneSetId = L"{B7A1F5A9-9DC2-4505-84AB-993253839093}";
|
const std::wstring zoneSetId = L"{B7A1F5A9-9DC2-4505-84AB-993253839093}";
|
||||||
const FancyZonesDataTypes::DeviceIdData deviceId{ L"DELA026#5&10a58c63&0&UID16777488_2194_1234_{39B25DD2-130D-4B5D-8851-4791D66B1539}" };
|
const FancyZonesDataTypes::WorkAreaId workAreaId{
|
||||||
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" } },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}").value()
|
||||||
|
};
|
||||||
const auto window = Mocks::WindowCreate(m_hInst);
|
const auto window = Mocks::WindowCreate(m_hInst);
|
||||||
|
|
||||||
Assert::IsTrue(AppZoneHistory::instance().SetAppLastZones(window, deviceId, zoneSetId, { 1 }));
|
Assert::IsTrue(AppZoneHistory::instance().SetAppLastZones(window, workAreaId, zoneSetId, { 1 }));
|
||||||
Assert::IsTrue(AppZoneHistory::instance().RemoveAppLastZone(window, deviceId, zoneSetId));
|
Assert::IsTrue(AppZoneHistory::instance().RemoveAppLastZone(window, workAreaId, zoneSetId));
|
||||||
Assert::IsTrue(std::vector<ZoneIndex>{} == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, deviceId, zoneSetId));
|
Assert::IsTrue(std::vector<ZoneIndex>{} == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, workAreaId, zoneSetId));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD (AppLastZoneRemoveUnknownWindow)
|
TEST_METHOD (AppLastZoneRemoveUnknownWindow)
|
||||||
{
|
{
|
||||||
const std::wstring zoneSetId = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
const std::wstring zoneSetId = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
||||||
const FancyZonesDataTypes::DeviceIdData deviceId{ L"DELA026#5&10a58c63&0&UID16777488_2194_1234_{39B25DD2-130D-4B5D-8851-4791D66B1539}" };
|
const FancyZonesDataTypes::WorkAreaId workAreaId{
|
||||||
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" } },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}").value()
|
||||||
|
};
|
||||||
const auto window = Mocks::WindowCreate(m_hInst);
|
const auto window = Mocks::WindowCreate(m_hInst);
|
||||||
|
|
||||||
Assert::IsFalse(AppZoneHistory::instance().RemoveAppLastZone(window, deviceId, zoneSetId));
|
Assert::IsFalse(AppZoneHistory::instance().RemoveAppLastZone(window, workAreaId, zoneSetId));
|
||||||
Assert::IsTrue(std::vector<ZoneIndex>{} == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, deviceId, zoneSetId));
|
Assert::IsTrue(std::vector<ZoneIndex>{} == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, workAreaId, zoneSetId));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD (AppLastZoneRemoveUnknownZoneSetId)
|
TEST_METHOD (AppLastZoneRemoveUnknownZoneSetId)
|
||||||
{
|
{
|
||||||
const std::wstring zoneSetIdToInsert = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
const std::wstring zoneSetIdToInsert = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
||||||
const std::wstring zoneSetIdToRemove = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F1}";
|
const std::wstring zoneSetIdToRemove = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F1}";
|
||||||
const FancyZonesDataTypes::DeviceIdData deviceId{ L"DELA026#5&10a58c63&0&UID16777488_2194_1234_{39B25DD2-130D-4B5D-8851-4791D66B1539}" };
|
const FancyZonesDataTypes::WorkAreaId workAreaId{
|
||||||
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" } },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}").value()
|
||||||
|
};
|
||||||
const auto window = Mocks::WindowCreate(m_hInst);
|
const auto window = Mocks::WindowCreate(m_hInst);
|
||||||
|
|
||||||
Assert::IsTrue(AppZoneHistory::instance().SetAppLastZones(window, deviceId, zoneSetIdToInsert, { 1 }));
|
Assert::IsTrue(AppZoneHistory::instance().SetAppLastZones(window, workAreaId, zoneSetIdToInsert, { 1 }));
|
||||||
Assert::IsFalse(AppZoneHistory::instance().RemoveAppLastZone(window, deviceId, zoneSetIdToRemove));
|
Assert::IsFalse(AppZoneHistory::instance().RemoveAppLastZone(window, workAreaId, zoneSetIdToRemove));
|
||||||
Assert::IsTrue(std::vector<ZoneIndex>{ 1 } == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, deviceId, zoneSetIdToInsert));
|
Assert::IsTrue(std::vector<ZoneIndex>{ 1 } == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, workAreaId, zoneSetIdToInsert));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD (AppLastZoneRemoveUnknownWindowId)
|
TEST_METHOD (AppLastZoneRemoveUnknownWindowId)
|
||||||
{
|
{
|
||||||
const std::wstring zoneSetId = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
const std::wstring zoneSetId = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
||||||
const FancyZonesDataTypes::DeviceIdData deviceIdToInsert{ L"DELA026#5&10a58c63&0&UID16777488_2194_1234_{39B25DD2-130D-4B5D-8851-4791D66B1539}" };
|
const FancyZonesDataTypes::WorkAreaId workAreaIdToInsert{
|
||||||
const FancyZonesDataTypes::DeviceIdData deviceIdToRemove{ L"DELA026#5&10a58c63&0&UID16777489_2194_1234_{39B25DD2-130D-4B5D-8851-4791D66B1539}" };
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" } },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}").value()
|
||||||
|
};
|
||||||
|
const FancyZonesDataTypes::WorkAreaId workAreaIdToRemove{
|
||||||
|
.monitorId = { .deviceId = { .id = L"DELA027", .instanceId = L"5&10a58c63&0&UID16777489" } },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}").value()
|
||||||
|
};
|
||||||
const auto window = Mocks::WindowCreate(m_hInst);
|
const auto window = Mocks::WindowCreate(m_hInst);
|
||||||
|
|
||||||
Assert::IsTrue(AppZoneHistory::instance().SetAppLastZones(window, deviceIdToInsert, zoneSetId, { 1 }));
|
Assert::IsTrue(AppZoneHistory::instance().SetAppLastZones(window, workAreaIdToInsert, zoneSetId, { 1 }));
|
||||||
Assert::IsFalse(AppZoneHistory::instance().RemoveAppLastZone(window, deviceIdToRemove, zoneSetId));
|
Assert::IsFalse(AppZoneHistory::instance().RemoveAppLastZone(window, workAreaIdToRemove, zoneSetId));
|
||||||
Assert::IsTrue(std::vector<ZoneIndex>{ 1 } == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, deviceIdToInsert, zoneSetId));
|
Assert::IsTrue(std::vector<ZoneIndex>{ 1 } == AppZoneHistory::instance().GetAppLastZoneIndexSet(window, workAreaIdToInsert, zoneSetId));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD (AppLastZoneRemoveNullWindow)
|
TEST_METHOD (AppLastZoneRemoveNullWindow)
|
||||||
{
|
{
|
||||||
const std::wstring zoneSetId = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
const std::wstring zoneSetId = L"{2FEC41DA-3A0B-4E31-9CE1-9473C65D99F2}";
|
||||||
const FancyZonesDataTypes::DeviceIdData deviceId{ L"DELA026#5&10a58c63&0&UID16777488_2194_1234_{39B25DD2-130D-4B5D-8851-4791D66B1539}" };
|
const FancyZonesDataTypes::WorkAreaId workAreaId{
|
||||||
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" } },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}").value()
|
||||||
|
};
|
||||||
const auto window = Mocks::WindowCreate(m_hInst);
|
const auto window = Mocks::WindowCreate(m_hInst);
|
||||||
|
|
||||||
Assert::IsFalse(AppZoneHistory::instance().RemoveAppLastZone(nullptr, deviceId, zoneSetId));
|
Assert::IsFalse(AppZoneHistory::instance().RemoveAppLastZone(nullptr, workAreaId, zoneSetId));
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@@ -23,6 +23,7 @@ namespace FancyZonesUnitTests
|
|||||||
{
|
{
|
||||||
std::filesystem::remove_all(AppliedLayouts::AppliedLayoutsFileName());
|
std::filesystem::remove_all(AppliedLayouts::AppliedLayoutsFileName());
|
||||||
std::filesystem::remove_all(PTSettingsHelper::get_module_save_folder_location(m_testFolder));
|
std::filesystem::remove_all(PTSettingsHelper::get_module_save_folder_location(m_testFolder));
|
||||||
|
AppliedLayouts::instance().LoadData(); // clean data
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD (AppliedLayoutsParse)
|
TEST_METHOD (AppliedLayoutsParse)
|
||||||
@@ -58,11 +59,12 @@ namespace FancyZonesUnitTests
|
|||||||
AppliedLayouts::instance().LoadData();
|
AppliedLayouts::instance().LoadData();
|
||||||
Assert::AreEqual((size_t)1, AppliedLayouts::instance().GetAppliedLayoutMap().size());
|
Assert::AreEqual((size_t)1, AppliedLayouts::instance().GetAppliedLayoutMap().size());
|
||||||
|
|
||||||
FancyZonesDataTypes::DeviceIdData id{
|
FancyZonesDataTypes::WorkAreaId id{
|
||||||
.deviceName = L"DELA026#5&10a58c63&0&UID16777488",
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value()
|
||||||
};
|
};
|
||||||
Assert::IsTrue(AppliedLayouts::instance().GetDeviceLayout(id).has_value());
|
Assert::IsTrue(AppliedLayouts::instance().GetDeviceLayout(id).has_value());
|
||||||
|
Assert::IsTrue(AppliedLayouts::instance().IsLayoutApplied(id));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD(AppliedLayoutsParseDataWithResolution)
|
TEST_METHOD(AppliedLayoutsParseDataWithResolution)
|
||||||
@@ -94,11 +96,12 @@ namespace FancyZonesUnitTests
|
|||||||
AppliedLayouts::instance().LoadData();
|
AppliedLayouts::instance().LoadData();
|
||||||
Assert::AreEqual((size_t)1, AppliedLayouts::instance().GetAppliedLayoutMap().size());
|
Assert::AreEqual((size_t)1, AppliedLayouts::instance().GetAppliedLayoutMap().size());
|
||||||
|
|
||||||
FancyZonesDataTypes::DeviceIdData id{
|
FancyZonesDataTypes::WorkAreaId id{
|
||||||
.deviceName = L"DELA026#5&10a58c63&0&UID16777488",
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value()
|
||||||
};
|
};
|
||||||
Assert::IsTrue(AppliedLayouts::instance().GetDeviceLayout(id).has_value());
|
Assert::IsTrue(AppliedLayouts::instance().GetDeviceLayout(id).has_value());
|
||||||
|
Assert::IsTrue(AppliedLayouts::instance().IsLayoutApplied(id));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD (AppliedLayoutsParseDataWithResolution2)
|
TEST_METHOD (AppliedLayoutsParseDataWithResolution2)
|
||||||
@@ -147,11 +150,12 @@ namespace FancyZonesUnitTests
|
|||||||
AppliedLayouts::instance().LoadData();
|
AppliedLayouts::instance().LoadData();
|
||||||
Assert::AreEqual((size_t)1, AppliedLayouts::instance().GetAppliedLayoutMap().size());
|
Assert::AreEqual((size_t)1, AppliedLayouts::instance().GetAppliedLayoutMap().size());
|
||||||
|
|
||||||
FancyZonesDataTypes::DeviceIdData id{
|
FancyZonesDataTypes::WorkAreaId id{
|
||||||
.deviceName = L"DELA026#5&10a58c63&0&UID16777488",
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value()
|
||||||
};
|
};
|
||||||
Assert::IsTrue(AppliedLayouts::instance().GetDeviceLayout(id).has_value());
|
Assert::IsTrue(AppliedLayouts::instance().GetDeviceLayout(id).has_value());
|
||||||
|
Assert::IsTrue(AppliedLayouts::instance().IsLayoutApplied(id));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD (AppliedLayoutsParseDataWithResolution3)
|
TEST_METHOD (AppliedLayoutsParseDataWithResolution3)
|
||||||
@@ -202,11 +206,12 @@ namespace FancyZonesUnitTests
|
|||||||
AppliedLayouts::instance().LoadData();
|
AppliedLayouts::instance().LoadData();
|
||||||
Assert::AreEqual((size_t)1, AppliedLayouts::instance().GetAppliedLayoutMap().size());
|
Assert::AreEqual((size_t)1, AppliedLayouts::instance().GetAppliedLayoutMap().size());
|
||||||
|
|
||||||
FancyZonesDataTypes::DeviceIdData id{
|
FancyZonesDataTypes::WorkAreaId id{
|
||||||
.deviceName = L"DELA026#5&10a58c63&0&UID16777488",
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value()
|
||||||
};
|
};
|
||||||
Assert::IsTrue(AppliedLayouts::instance().GetDeviceLayout(id).has_value());
|
Assert::IsTrue(AppliedLayouts::instance().GetDeviceLayout(id).has_value());
|
||||||
|
Assert::IsTrue(AppliedLayouts::instance().IsLayoutApplied(id));
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_METHOD (AppliedLayoutsParseEmpty)
|
TEST_METHOD (AppliedLayoutsParseEmpty)
|
||||||
@@ -262,8 +267,8 @@ namespace FancyZonesUnitTests
|
|||||||
AppliedLayouts::instance().LoadData();
|
AppliedLayouts::instance().LoadData();
|
||||||
Assert::AreEqual((size_t)1, AppliedLayouts::instance().GetAppliedLayoutMap().size());
|
Assert::AreEqual((size_t)1, AppliedLayouts::instance().GetAppliedLayoutMap().size());
|
||||||
|
|
||||||
FancyZonesDataTypes::DeviceIdData id{
|
FancyZonesDataTypes::WorkAreaId id{
|
||||||
.deviceName = L"VSC9636#5&37ac4db&0&UID160005",
|
.monitorId = { .deviceId = { .id = L"VSC9636", .instanceId = L"5&37ac4db&0&UID160005" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
||||||
};
|
};
|
||||||
Assert::IsTrue(AppliedLayouts::instance().GetDeviceLayout(id).has_value());
|
Assert::IsTrue(AppliedLayouts::instance().GetDeviceLayout(id).has_value());
|
||||||
@@ -295,12 +300,12 @@ namespace FancyZonesUnitTests
|
|||||||
|
|
||||||
TEST_METHOD (CloneDeviceInfo)
|
TEST_METHOD (CloneDeviceInfo)
|
||||||
{
|
{
|
||||||
FancyZonesDataTypes::DeviceIdData deviceSrc{
|
FancyZonesDataTypes::WorkAreaId deviceSrc{
|
||||||
.deviceName = L"Device1",
|
.monitorId = { .deviceId = { .id = L"Device1", .instanceId = L"" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
||||||
};
|
};
|
||||||
FancyZonesDataTypes::DeviceIdData deviceDst{
|
FancyZonesDataTypes::WorkAreaId deviceDst{
|
||||||
.deviceName = L"Device2",
|
.monitorId = { .deviceId = { .id = L"Device2", .instanceId = L"" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -323,12 +328,12 @@ namespace FancyZonesUnitTests
|
|||||||
|
|
||||||
TEST_METHOD (CloneDeviceInfoIntoUnknownDevice)
|
TEST_METHOD (CloneDeviceInfoIntoUnknownDevice)
|
||||||
{
|
{
|
||||||
FancyZonesDataTypes::DeviceIdData deviceSrc{
|
FancyZonesDataTypes::WorkAreaId deviceSrc{
|
||||||
.deviceName = L"Device1",
|
.monitorId = { .deviceId = { .id = L"Device1", .instanceId = L"" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
||||||
};
|
};
|
||||||
FancyZonesDataTypes::DeviceIdData deviceDst{
|
FancyZonesDataTypes::WorkAreaId deviceDst{
|
||||||
.deviceName = L"Device2",
|
.monitorId = { .deviceId = { .id = L"Device2", .instanceId = L"" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -350,12 +355,12 @@ namespace FancyZonesUnitTests
|
|||||||
|
|
||||||
TEST_METHOD (CloneDeviceInfoFromUnknownDevice)
|
TEST_METHOD (CloneDeviceInfoFromUnknownDevice)
|
||||||
{
|
{
|
||||||
FancyZonesDataTypes::DeviceIdData deviceSrc{
|
FancyZonesDataTypes::WorkAreaId deviceSrc{
|
||||||
.deviceName = L"Device1",
|
.monitorId = { .deviceId = { .id = L"Device1", .instanceId = L"" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
||||||
};
|
};
|
||||||
FancyZonesDataTypes::DeviceIdData deviceDst{
|
FancyZonesDataTypes::WorkAreaId deviceDst{
|
||||||
.deviceName = L"Device2",
|
.monitorId = { .deviceId = { .id = L"Device2", .instanceId = L"" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -370,12 +375,12 @@ namespace FancyZonesUnitTests
|
|||||||
|
|
||||||
TEST_METHOD (CloneDeviceInfoNullVirtualDesktopId)
|
TEST_METHOD (CloneDeviceInfoNullVirtualDesktopId)
|
||||||
{
|
{
|
||||||
FancyZonesDataTypes::DeviceIdData deviceSrc{
|
FancyZonesDataTypes::WorkAreaId deviceSrc{
|
||||||
.deviceName = L"Device1",
|
.monitorId = { .deviceId = { .id = L"Device1", .instanceId = L"" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = GUID_NULL
|
.virtualDesktopId = GUID_NULL
|
||||||
};
|
};
|
||||||
FancyZonesDataTypes::DeviceIdData deviceDst{
|
FancyZonesDataTypes::WorkAreaId deviceDst{
|
||||||
.deviceName = L"Device2",
|
.monitorId = { .deviceId = { .id = L"Device2", .instanceId = L"" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -399,8 +404,8 @@ namespace FancyZonesUnitTests
|
|||||||
TEST_METHOD (ApplyLayout)
|
TEST_METHOD (ApplyLayout)
|
||||||
{
|
{
|
||||||
// prepare
|
// prepare
|
||||||
FancyZonesDataTypes::DeviceIdData deviceId {
|
FancyZonesDataTypes::WorkAreaId deviceId {
|
||||||
.deviceName = L"DELA026#5&10a58c63&0&UID16777488",
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value()
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -430,8 +435,8 @@ namespace FancyZonesUnitTests
|
|||||||
TEST_METHOD (ApplyLayoutReplace)
|
TEST_METHOD (ApplyLayoutReplace)
|
||||||
{
|
{
|
||||||
// prepare
|
// prepare
|
||||||
FancyZonesDataTypes::DeviceIdData deviceId{
|
FancyZonesDataTypes::WorkAreaId deviceId{
|
||||||
.deviceName = L"DELA026#5&10a58c63&0&UID16777488",
|
.monitorId = { .deviceId = { .id = L"DELA026", .instanceId = L"5&10a58c63&0&UID16777488" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value()
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -482,8 +487,8 @@ namespace FancyZonesUnitTests
|
|||||||
|
|
||||||
TEST_METHOD (ApplyDefaultLayout)
|
TEST_METHOD (ApplyDefaultLayout)
|
||||||
{
|
{
|
||||||
FancyZonesDataTypes::DeviceIdData expected{
|
FancyZonesDataTypes::WorkAreaId expected{
|
||||||
.deviceName = L"Device",
|
.monitorId = { .deviceId = { .id = L"Device", .instanceId = L"" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{00000000-0000-0000-0000-000000000000}").value()
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -497,8 +502,8 @@ namespace FancyZonesUnitTests
|
|||||||
|
|
||||||
TEST_METHOD (ApplyDefaultLayoutWithNullVirtualDesktopId)
|
TEST_METHOD (ApplyDefaultLayoutWithNullVirtualDesktopId)
|
||||||
{
|
{
|
||||||
FancyZonesDataTypes::DeviceIdData expected{
|
FancyZonesDataTypes::WorkAreaId expected{
|
||||||
.deviceName = L"Device",
|
.monitorId = { .deviceId = { .id = L"Device", .instanceId = L"" }, .serialNumber = L"" },
|
||||||
.virtualDesktopId = GUID_NULL
|
.virtualDesktopId = GUID_NULL
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -509,5 +514,35 @@ namespace FancyZonesUnitTests
|
|||||||
|
|
||||||
Assert::IsFalse(actualMap.find(expected) == actualMap.end());
|
Assert::IsFalse(actualMap.find(expected) == actualMap.end());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (IsLayoutApplied)
|
||||||
|
{
|
||||||
|
// prepare
|
||||||
|
FancyZonesDataTypes::WorkAreaId id{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"serial-number" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
AppliedLayouts::instance().ApplyLayout(id, Layout{});
|
||||||
|
|
||||||
|
// test
|
||||||
|
Assert::IsTrue(AppliedLayouts::instance().IsLayoutApplied(id));
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (IsLayoutApplied2)
|
||||||
|
{
|
||||||
|
// prepare
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device-1", .instanceId = L"instance-id-1" }, .serialNumber = L"serial-number-1" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
AppliedLayouts::instance().ApplyLayout(id1, Layout{});
|
||||||
|
|
||||||
|
// test
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device-2", .instanceId = L"instance-id-2" }, .serialNumber = L"serial-number-2" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{F21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
Assert::IsFalse(AppliedLayouts::instance().IsLayoutApplied(id2));
|
||||||
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@@ -741,15 +741,9 @@ namespace FancyZonesUnitTests
|
|||||||
TEST_CLASS (DeviceInfoUnitTests)
|
TEST_CLASS (DeviceInfoUnitTests)
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
FancyZonesDataTypes::DeviceIdData m_defaultDeviceId{ .deviceName = L"AOC2460#4&fe3a015&0&UID65793", .virtualDesktopId = FancyZonesUtils::GuidFromString(L"{33A2B101-06E0-437B-A61E-CDBECF502907}").value() };
|
|
||||||
DeviceInfoJSON m_defaultDeviceInfo = DeviceInfoJSON{ BackwardsCompatibility::DeviceIdData::ParseDeviceId(L"AOC2460#4&fe3a015&0&UID65793_1920_1080_{33A2B101-06E0-437B-A61E-CDBECF502907}").value(), DeviceInfoData{ ZoneSetData{ L"{33A2B101-06E0-437B-A61E-CDBECF502906}", ZoneSetLayoutType::Custom }, true, 16, 3 } };
|
DeviceInfoJSON m_defaultDeviceInfo = DeviceInfoJSON{ BackwardsCompatibility::DeviceIdData::ParseDeviceId(L"AOC2460#4&fe3a015&0&UID65793_1920_1080_{33A2B101-06E0-437B-A61E-CDBECF502907}").value(), DeviceInfoData{ ZoneSetData{ L"{33A2B101-06E0-437B-A61E-CDBECF502906}", ZoneSetLayoutType::Custom }, true, 16, 3 } };
|
||||||
json::JsonObject m_defaultJson = json::JsonObject::Parse(L"{\"device-id\": \"AOC2460#4&fe3a015&0&UID65793_1920_1200_{39B25DD2-130D-4B5D-8851-4791D66B1539}\", \"active-zoneset\": {\"type\": \"custom\", \"uuid\": \"{33A2B101-06E0-437B-A61E-CDBECF502906}\"}, \"editor-show-spacing\": true, \"editor-spacing\": 16, \"editor-zone-count\": 3}");
|
json::JsonObject m_defaultJson = json::JsonObject::Parse(L"{\"device-id\": \"AOC2460#4&fe3a015&0&UID65793_1920_1200_{39B25DD2-130D-4B5D-8851-4791D66B1539}\", \"active-zoneset\": {\"type\": \"custom\", \"uuid\": \"{33A2B101-06E0-437B-A61E-CDBECF502906}\"}, \"editor-show-spacing\": true, \"editor-spacing\": 16, \"editor-zone-count\": 3}");
|
||||||
|
|
||||||
TEST_METHOD_INITIALIZE(Init)
|
|
||||||
{
|
|
||||||
CLSIDFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}", &m_defaultDeviceId.virtualDesktopId);
|
|
||||||
}
|
|
||||||
|
|
||||||
public:
|
public:
|
||||||
TEST_METHOD (FromJson)
|
TEST_METHOD (FromJson)
|
||||||
{
|
{
|
||||||
@@ -791,9 +785,7 @@ namespace FancyZonesUnitTests
|
|||||||
const std::wstring m_defaultCustomDeviceStr = L"{\"device-id\": \"AOC2460#4&fe3a015&0&UID65793_1920_1200_{39B25DD2-130D-4B5D-8851-4791D66B1539}\", \"active-zoneset\": {\"type\": \"custom\", \"uuid\": \"{33A2B101-06E0-437B-A61E-CDBECF502906}\"}, \"editor-show-spacing\": true, \"editor-spacing\": 16, \"editor-zone-count\": 3}";
|
const std::wstring m_defaultCustomDeviceStr = L"{\"device-id\": \"AOC2460#4&fe3a015&0&UID65793_1920_1200_{39B25DD2-130D-4B5D-8851-4791D66B1539}\", \"active-zoneset\": {\"type\": \"custom\", \"uuid\": \"{33A2B101-06E0-437B-A61E-CDBECF502906}\"}, \"editor-show-spacing\": true, \"editor-spacing\": 16, \"editor-zone-count\": 3}";
|
||||||
const std::wstring m_defaultCustomLayoutStr = L"{\"device-id\": \"AOC2460#4&fe3a015&0&UID65793_1920_1200_{39B25DD2-130D-4B5D-8851-4791D66B1539}\", \"applied-layout\": {\"type\": \"custom\", \"uuid\": \"{33A2B101-06E0-437B-A61E-CDBECF502906}\", \"show-spacing\": true, \"spacing\": 16, \"zone-count\": 3, \"sensitivity-radius\": 30}}";
|
const std::wstring m_defaultCustomLayoutStr = L"{\"device-id\": \"AOC2460#4&fe3a015&0&UID65793_1920_1200_{39B25DD2-130D-4B5D-8851-4791D66B1539}\", \"applied-layout\": {\"type\": \"custom\", \"uuid\": \"{33A2B101-06E0-437B-A61E-CDBECF502906}\", \"show-spacing\": true, \"spacing\": 16, \"zone-count\": 3, \"sensitivity-radius\": 30}}";
|
||||||
const json::JsonValue m_defaultCustomDeviceValue = json::JsonValue::Parse(m_defaultCustomDeviceStr);
|
const json::JsonValue m_defaultCustomDeviceValue = json::JsonValue::Parse(m_defaultCustomDeviceStr);
|
||||||
|
|
||||||
const FancyZonesDataTypes::DeviceIdData m_defaultDeviceId = FancyZonesDataTypes::DeviceIdData{ .deviceName = L"AOC2460#4&fe3a015&0&UID65793", .virtualDesktopId = FancyZonesUtils::GuidFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}").value() };
|
|
||||||
|
|
||||||
TEST_METHOD_INITIALIZE(Init)
|
TEST_METHOD_INITIALIZE(Init)
|
||||||
{
|
{
|
||||||
std::filesystem::remove_all(PTSettingsHelper::get_module_save_folder_location(m_moduleName));
|
std::filesystem::remove_all(PTSettingsHelper::get_module_save_folder_location(m_moduleName));
|
||||||
|
|||||||
@@ -37,7 +37,7 @@
|
|||||||
</ClCompile>
|
</ClCompile>
|
||||||
<Link>
|
<Link>
|
||||||
<AdditionalLibraryDirectories>$(VCInstallDir)UnitTest\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
|
<AdditionalLibraryDirectories>$(VCInstallDir)UnitTest\lib;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
|
||||||
<AdditionalDependencies>gdiplus.lib;dwmapi.lib;shlwapi.lib;uxtheme.lib;shcore.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
<AdditionalDependencies>gdiplus.lib;dwmapi.lib;shlwapi.lib;uxtheme.lib;shcore.lib;wbemuuid.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
||||||
</Link>
|
</Link>
|
||||||
</ItemDefinitionGroup>
|
</ItemDefinitionGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
@@ -55,6 +55,7 @@
|
|||||||
<ClCompile Include="Util.Spec.cpp" />
|
<ClCompile Include="Util.Spec.cpp" />
|
||||||
<ClCompile Include="Util.cpp" />
|
<ClCompile Include="Util.cpp" />
|
||||||
<ClCompile Include="WorkArea.Spec.cpp" />
|
<ClCompile Include="WorkArea.Spec.cpp" />
|
||||||
|
<ClCompile Include="WorkAreaIdTests.Spec.cpp" />
|
||||||
<ClCompile Include="Zone.Spec.cpp" />
|
<ClCompile Include="Zone.Spec.cpp" />
|
||||||
<ClCompile Include="ZoneSet.Spec.cpp" />
|
<ClCompile Include="ZoneSet.Spec.cpp" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|||||||
@@ -57,6 +57,9 @@
|
|||||||
<ClCompile Include="AppliedLayoutsTests.Spec.cpp">
|
<ClCompile Include="AppliedLayoutsTests.Spec.cpp">
|
||||||
<Filter>Source Files</Filter>
|
<Filter>Source Files</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
|
<ClCompile Include="WorkAreaIdTests.Spec.cpp">
|
||||||
|
<Filter>Source Files</Filter>
|
||||||
|
</ClCompile>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ClInclude Include="pch.h">
|
<ClInclude Include="pch.h">
|
||||||
|
|||||||
@@ -41,28 +41,6 @@ namespace FancyZonesUnitTests
|
|||||||
|
|
||||||
TEST_CLASS(UtilUnitTests)
|
TEST_CLASS(UtilUnitTests)
|
||||||
{
|
{
|
||||||
TEST_METHOD (TestTrimDeviceId)
|
|
||||||
{
|
|
||||||
// We're interested in the unique part between the first and last #'s
|
|
||||||
// Example input: \\?\DISPLAY#DELA026#5&10a58c63&0&UID16777488#{e6f07b5f-ee97-4a90-b076-33f57bf4eaa7}
|
|
||||||
// Example output: DELA026#5&10a58c63&0&UID16777488
|
|
||||||
const std::wstring input = L"\\\\?\\DISPLAY#DELA026#5&10a58c63&0&UID16777488#{e6f07b5f-ee97-4a90-b076-33f57bf4eaa7}";
|
|
||||||
const std::wstring actual = TrimDeviceId(input);
|
|
||||||
const std::wstring expected = L"DELA026#5&10a58c63&0&UID16777488";
|
|
||||||
Assert::AreEqual(expected, actual);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_METHOD(TestTrimInvalidDeviceId)
|
|
||||||
{
|
|
||||||
// We're interested in the unique part between the first and last #'s
|
|
||||||
// Example input: \\?\DISPLAY#DELA026#5&10a58c63&0&UID16777488#{e6f07b5f-ee97-4a90-b076-33f57bf4eaa7}
|
|
||||||
// Example output: DELA026#5&10a58c63&0&UID16777488
|
|
||||||
const std::wstring input = L"AnInvalidDeviceId";
|
|
||||||
const std::wstring actual = TrimDeviceId(input);
|
|
||||||
const std::wstring expected = L"FallbackDevice";
|
|
||||||
Assert::AreEqual(expected, actual);
|
|
||||||
}
|
|
||||||
|
|
||||||
TEST_METHOD(TestParseDeviceId01)
|
TEST_METHOD(TestParseDeviceId01)
|
||||||
{
|
{
|
||||||
const std::wstring input = L"AOC0001#5&37ac4db&0&UID160002_1536_960_{E0A2904E-889C-4532-95B1-28FE15C16F66}";
|
const std::wstring input = L"AOC0001#5&37ac4db&0&UID160002_1536_960_{E0A2904E-889C-4532-95B1-28FE15C16F66}";
|
||||||
|
|||||||
@@ -23,12 +23,14 @@ namespace FancyZonesUnitTests
|
|||||||
|
|
||||||
TEST_CLASS (WorkAreaCreationUnitTests)
|
TEST_CLASS (WorkAreaCreationUnitTests)
|
||||||
{
|
{
|
||||||
FancyZonesDataTypes::DeviceIdData m_uniqueId;
|
FancyZonesDataTypes::WorkAreaId m_uniqueId;
|
||||||
FancyZonesDataTypes::DeviceIdData m_emptyUniqueId;
|
FancyZonesDataTypes::WorkAreaId m_emptyUniqueId;
|
||||||
|
|
||||||
TEST_METHOD_INITIALIZE(Init)
|
TEST_METHOD_INITIALIZE(Init)
|
||||||
{
|
{
|
||||||
m_uniqueId.deviceName = L"DELA026#5&10a58c63&0&UID16777488";
|
m_uniqueId.monitorId.deviceId.id = L"DELA026";
|
||||||
|
m_uniqueId.monitorId.deviceId.instanceId = L"5&10a58c63&0&UID16777488";
|
||||||
|
m_uniqueId.monitorId.serialNumber = L"serial-number";
|
||||||
auto res = CLSIDFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}", &m_uniqueId.virtualDesktopId);
|
auto res = CLSIDFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}", &m_uniqueId.virtualDesktopId);
|
||||||
Assert::IsTrue(SUCCEEDED(res));
|
Assert::IsTrue(SUCCEEDED(res));
|
||||||
|
|
||||||
@@ -70,8 +72,10 @@ namespace FancyZonesUnitTests
|
|||||||
{
|
{
|
||||||
using namespace FancyZonesDataTypes;
|
using namespace FancyZonesDataTypes;
|
||||||
|
|
||||||
FancyZonesDataTypes::DeviceIdData parentUniqueId;
|
FancyZonesDataTypes::WorkAreaId parentUniqueId;
|
||||||
parentUniqueId.deviceName = L"DELA026#5&10a58c63&0&UID16777488";
|
parentUniqueId.monitorId.deviceId.id = L"DELA026";
|
||||||
|
parentUniqueId.monitorId.deviceId.instanceId = L"5&10a58c63&0&UID16777488";
|
||||||
|
parentUniqueId.monitorId.serialNumber = L"serial-number";
|
||||||
parentUniqueId.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value();
|
parentUniqueId.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{61FA9FC0-26A6-4B37-A834-491C148DFC57}").value();
|
||||||
|
|
||||||
Layout layout{
|
Layout layout{
|
||||||
@@ -104,15 +108,17 @@ namespace FancyZonesUnitTests
|
|||||||
|
|
||||||
TEST_CLASS (WorkAreaUnitTests)
|
TEST_CLASS (WorkAreaUnitTests)
|
||||||
{
|
{
|
||||||
FancyZonesDataTypes::DeviceIdData m_uniqueId;
|
FancyZonesDataTypes::WorkAreaId m_uniqueId;
|
||||||
FancyZonesDataTypes::DeviceIdData m_parentUniqueId; // default empty
|
FancyZonesDataTypes::WorkAreaId m_parentUniqueId; // default empty
|
||||||
|
|
||||||
HINSTANCE m_hInst{};
|
HINSTANCE m_hInst{};
|
||||||
HMONITOR m_monitor{};
|
HMONITOR m_monitor{};
|
||||||
|
|
||||||
TEST_METHOD_INITIALIZE(Init)
|
TEST_METHOD_INITIALIZE(Init)
|
||||||
{
|
{
|
||||||
m_uniqueId.deviceName = L"DELA026#5&10a58c63&0&UID16777488";
|
m_uniqueId.monitorId.deviceId.id = L"DELA026";
|
||||||
|
m_uniqueId.monitorId.deviceId.instanceId = L"5&10a58c63&0&UID16777488";
|
||||||
|
m_uniqueId.monitorId.serialNumber = L"serial-number";
|
||||||
CLSIDFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}", &m_uniqueId.virtualDesktopId);
|
CLSIDFromString(L"{39B25DD2-130D-4B5D-8851-4791D66B1539}", &m_uniqueId.virtualDesktopId);
|
||||||
|
|
||||||
AppZoneHistory::instance().LoadData();
|
AppZoneHistory::instance().LoadData();
|
||||||
|
|||||||
@@ -0,0 +1,212 @@
|
|||||||
|
#include "pch.h"
|
||||||
|
|
||||||
|
#include <FancyZonesLib/FancyZonesDataTypes.h>
|
||||||
|
#include <FancyZonesLib/util.h>
|
||||||
|
|
||||||
|
#include <FancyZonesTests/UnitTests/Util.h>
|
||||||
|
|
||||||
|
using namespace Microsoft::VisualStudio::CppUnitTestFramework;
|
||||||
|
|
||||||
|
namespace FancyZonesUnitTests
|
||||||
|
{
|
||||||
|
TEST_CLASS (WorkAreaIdComparison)
|
||||||
|
{
|
||||||
|
TEST_METHOD (MonitorHandleSame)
|
||||||
|
{
|
||||||
|
auto monitor = Mocks::Monitor();
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .monitor = monitor, .deviceId = { .id = L"device-1", .instanceId = L"instance-id-1" }, .serialNumber = L"serial-number-1" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .monitor = monitor, .deviceId = { .id = L"device-2", .instanceId = L"instance-id-2" }, .serialNumber = L"serial-number-2" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsTrue(id1 == id2);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (MonitorHandleDifferent)
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .monitor = Mocks::Monitor(), .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"serial-number" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .monitor = Mocks::Monitor(), .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"serial-number" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsFalse(id1 == id2);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (VirtualDesktopNull)
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"serial-number" },
|
||||||
|
.virtualDesktopId = GUID_NULL
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"serial-number" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsTrue(id1 == id2);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (VirtualDesktopDifferent)
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"serial-number" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{F21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"serial-number" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsFalse(id1 == id2);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (NoSerialNumber)
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"serial-number" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsFalse(id1 == id2);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (NoSerialNumber2)
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"serial-number" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsFalse(id1 == id2);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (DifferentSerialNumber)
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"serial-number" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id" }, .serialNumber = L"another-serial-number" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsFalse(id1 == id2);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (DefaultMonitorIdDifferentInstanceId)
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .deviceId = { .id = L"Default_Monitor", .instanceId = L"instance-id" }, .serialNumber = L"" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"Default_Monitor", .instanceId = L"another-instance-id" }, .serialNumber = L"" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsFalse(id1 == id2);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (DefaultMonitorIdSameInstanceId)
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .deviceId = { .id = L"Default_Monitor", .instanceId = L"instance-id" }, .serialNumber = L"" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"Default_Monitor", .instanceId = L"instance-id" }, .serialNumber = L"" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsTrue(id1 == id2);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (DifferentId)
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device-1", .instanceId = L"instance-id" }, .serialNumber = L"" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device-2", .instanceId = L"instance-id" }, .serialNumber = L"" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsFalse(id1 == id2);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (SameIdDifferentInstance)
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id-1" }, .serialNumber = L"" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device", .instanceId = L"instance-id-2" }, .serialNumber = L"" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsTrue(id1 == id2);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (SameIdDifferentSerialNumbers)
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device-1", .instanceId = L"instance-id-1" }, .serialNumber = L"serial-number-1" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device-1", .instanceId = L"instance-id-2" }, .serialNumber = L"serial-number-2" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsFalse(id1 == id2);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD (DifferentIdSameSerialNumbers)
|
||||||
|
{
|
||||||
|
FancyZonesDataTypes::WorkAreaId id1{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device-1", .instanceId = L"instance-id-1" }, .serialNumber = L"serial-number-1" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
FancyZonesDataTypes::WorkAreaId id2{
|
||||||
|
.monitorId = { .deviceId = { .id = L"device-2", .instanceId = L"instance-id-2" }, .serialNumber = L"serial-number-1" },
|
||||||
|
.virtualDesktopId = FancyZonesUtils::GuidFromString(L"{E21F6F29-76FD-4FC1-8970-17AB8AD64847}").value()
|
||||||
|
};
|
||||||
|
|
||||||
|
Assert::IsFalse(id1 == id2);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
@@ -13,6 +13,10 @@ namespace FancyZonesEditor.Utils
|
|||||||
{
|
{
|
||||||
public string MonitorName { get; set; }
|
public string MonitorName { get; set; }
|
||||||
|
|
||||||
|
public string MonitorInstanceId { get; set; }
|
||||||
|
|
||||||
|
public string MonitorSerialNumber { get; set; }
|
||||||
|
|
||||||
public Size MonitorSize { get; set; }
|
public Size MonitorSize { get; set; }
|
||||||
|
|
||||||
public string VirtualDesktopId { get; set; }
|
public string VirtualDesktopId { get; set; }
|
||||||
@@ -23,9 +27,11 @@ namespace FancyZonesEditor.Utils
|
|||||||
|
|
||||||
public int Dpi { get; set; }
|
public int Dpi { get; set; }
|
||||||
|
|
||||||
public Device(string monitorName, string virtualDesktopId, int dpi, Rect workArea, Size monitorSize)
|
public Device(string monitorName, string monitorInstanceId, string monitorSerialNumber, string virtualDesktopId, int dpi, Rect workArea, Size monitorSize)
|
||||||
{
|
{
|
||||||
MonitorName = monitorName;
|
MonitorName = monitorName;
|
||||||
|
MonitorInstanceId = monitorInstanceId;
|
||||||
|
MonitorSerialNumber = monitorSerialNumber;
|
||||||
VirtualDesktopId = virtualDesktopId;
|
VirtualDesktopId = virtualDesktopId;
|
||||||
Dpi = dpi;
|
Dpi = dpi;
|
||||||
WorkAreaRect = workArea;
|
WorkAreaRect = workArea;
|
||||||
@@ -48,6 +54,8 @@ namespace FancyZonesEditor.Utils
|
|||||||
var sb = new StringBuilder();
|
var sb = new StringBuilder();
|
||||||
|
|
||||||
sb.AppendFormat(CultureInfo.InvariantCulture, "MonitorName: {0}{1}", MonitorName, Environment.NewLine);
|
sb.AppendFormat(CultureInfo.InvariantCulture, "MonitorName: {0}{1}", MonitorName, Environment.NewLine);
|
||||||
|
sb.AppendFormat(CultureInfo.InvariantCulture, "Monitor InstanceId {0}{1}", MonitorInstanceId, Environment.NewLine);
|
||||||
|
sb.AppendFormat(CultureInfo.InvariantCulture, "Monitor Serial Number {0}{1}", MonitorSerialNumber, Environment.NewLine);
|
||||||
sb.AppendFormat(CultureInfo.InvariantCulture, "Virtual desktop: {0}{1}", VirtualDesktopId, Environment.NewLine);
|
sb.AppendFormat(CultureInfo.InvariantCulture, "Virtual desktop: {0}{1}", VirtualDesktopId, Environment.NewLine);
|
||||||
sb.AppendFormat(CultureInfo.InvariantCulture, "DPI: {0}{1}", Dpi, Environment.NewLine);
|
sb.AppendFormat(CultureInfo.InvariantCulture, "DPI: {0}{1}", Dpi, Environment.NewLine);
|
||||||
|
|
||||||
|
|||||||
@@ -41,10 +41,10 @@ namespace FancyZonesEditor.Models
|
|||||||
Window.Height = workArea.Height;
|
Window.Height = workArea.Height;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Monitor(string monitorName, string virtualDesktop, int dpi, Rect workArea, Size monitorSize)
|
public Monitor(string monitorName, string monitorInstanceId, string monitorSerialNumber, string virtualDesktop, int dpi, Rect workArea, Size monitorSize)
|
||||||
: this(workArea, monitorSize)
|
: this(workArea, monitorSize)
|
||||||
{
|
{
|
||||||
Device = new Device(monitorName, virtualDesktop, dpi, workArea, monitorSize);
|
Device = new Device(monitorName, monitorInstanceId, monitorSerialNumber, virtualDesktop, dpi, workArea, monitorSize);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void Scale(double scaleFactor)
|
public void Scale(double scaleFactor)
|
||||||
|
|||||||
@@ -77,6 +77,10 @@ namespace FancyZonesEditor.Utils
|
|||||||
{
|
{
|
||||||
public string Monitor { get; set; }
|
public string Monitor { get; set; }
|
||||||
|
|
||||||
|
public string MonitorInstanceId { get; set; }
|
||||||
|
|
||||||
|
public string MonitorSerialNumber { get; set; }
|
||||||
|
|
||||||
public string VirtualDesktop { get; set; }
|
public string VirtualDesktop { get; set; }
|
||||||
|
|
||||||
public int Dpi { get; set; }
|
public int Dpi { get; set; }
|
||||||
@@ -128,6 +132,10 @@ namespace FancyZonesEditor.Utils
|
|||||||
{
|
{
|
||||||
public string Monitor { get; set; }
|
public string Monitor { get; set; }
|
||||||
|
|
||||||
|
public string MonitorInstance { get; set; }
|
||||||
|
|
||||||
|
public string SerialNumber { get; set; }
|
||||||
|
|
||||||
public string VirtualDesktop { get; set; }
|
public string VirtualDesktop { get; set; }
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -309,6 +317,7 @@ namespace FancyZonesEditor.Utils
|
|||||||
if (!App.Overlay.SpanZonesAcrossMonitors)
|
if (!App.Overlay.SpanZonesAcrossMonitors)
|
||||||
{
|
{
|
||||||
string targetMonitorId = string.Empty;
|
string targetMonitorId = string.Empty;
|
||||||
|
string targetMonitorSerialNumber = string.Empty;
|
||||||
string targetVirtualDesktop = string.Empty;
|
string targetVirtualDesktop = string.Empty;
|
||||||
|
|
||||||
foreach (NativeMonitorData nativeData in editorParams.Monitors)
|
foreach (NativeMonitorData nativeData in editorParams.Monitors)
|
||||||
@@ -317,6 +326,7 @@ namespace FancyZonesEditor.Utils
|
|||||||
if (nativeData.IsSelected)
|
if (nativeData.IsSelected)
|
||||||
{
|
{
|
||||||
targetMonitorId = nativeData.Monitor;
|
targetMonitorId = nativeData.Monitor;
|
||||||
|
targetMonitorSerialNumber = nativeData.MonitorSerialNumber;
|
||||||
targetVirtualDesktop = nativeData.VirtualDesktop;
|
targetVirtualDesktop = nativeData.VirtualDesktop;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -324,6 +334,8 @@ namespace FancyZonesEditor.Utils
|
|||||||
|
|
||||||
var monitor = new Monitor(workArea, monitorSize);
|
var monitor = new Monitor(workArea, monitorSize);
|
||||||
monitor.Device.MonitorName = nativeData.Monitor;
|
monitor.Device.MonitorName = nativeData.Monitor;
|
||||||
|
monitor.Device.MonitorInstanceId = nativeData.MonitorInstanceId;
|
||||||
|
monitor.Device.MonitorSerialNumber = nativeData.MonitorSerialNumber;
|
||||||
monitor.Device.VirtualDesktopId = nativeData.VirtualDesktop;
|
monitor.Device.VirtualDesktopId = nativeData.VirtualDesktop;
|
||||||
monitor.Device.Dpi = nativeData.Dpi;
|
monitor.Device.Dpi = nativeData.Dpi;
|
||||||
|
|
||||||
@@ -335,7 +347,9 @@ namespace FancyZonesEditor.Utils
|
|||||||
for (int i = 0; i < monitors.Count; i++)
|
for (int i = 0; i < monitors.Count; i++)
|
||||||
{
|
{
|
||||||
var monitor = monitors[i];
|
var monitor = monitors[i];
|
||||||
if (monitor.Device.MonitorName == targetMonitorId && monitor.Device.VirtualDesktopId == targetVirtualDesktop)
|
if (monitor.Device.MonitorName == targetMonitorId &&
|
||||||
|
monitor.Device.MonitorSerialNumber == targetMonitorSerialNumber &&
|
||||||
|
monitor.Device.VirtualDesktopId == targetVirtualDesktop)
|
||||||
{
|
{
|
||||||
App.Overlay.CurrentDesktop = i;
|
App.Overlay.CurrentDesktop = i;
|
||||||
break;
|
break;
|
||||||
@@ -554,6 +568,8 @@ namespace FancyZonesEditor.Utils
|
|||||||
Device = new AppliedLayoutWrapper.DeviceIdWrapper
|
Device = new AppliedLayoutWrapper.DeviceIdWrapper
|
||||||
{
|
{
|
||||||
Monitor = monitor.Device.MonitorName,
|
Monitor = monitor.Device.MonitorName,
|
||||||
|
MonitorInstance = monitor.Device.MonitorInstanceId,
|
||||||
|
SerialNumber = monitor.Device.MonitorSerialNumber,
|
||||||
VirtualDesktop = monitor.Device.VirtualDesktopId,
|
VirtualDesktop = monitor.Device.VirtualDesktopId,
|
||||||
},
|
},
|
||||||
|
|
||||||
@@ -818,7 +834,10 @@ namespace FancyZonesEditor.Utils
|
|||||||
bool unused = true;
|
bool unused = true;
|
||||||
foreach (Monitor monitor in monitors)
|
foreach (Monitor monitor in monitors)
|
||||||
{
|
{
|
||||||
if (monitor.Device.MonitorName == layout.Device.Monitor && (monitor.Device.VirtualDesktopId == layout.Device.VirtualDesktop || layout.Device.VirtualDesktop == DefaultVirtualDesktopGuid))
|
if (monitor.Device.MonitorName == layout.Device.Monitor &&
|
||||||
|
monitor.Device.MonitorSerialNumber == layout.Device.SerialNumber &&
|
||||||
|
(monitor.Device.VirtualDesktopId == layout.Device.VirtualDesktop ||
|
||||||
|
layout.Device.VirtualDesktop == DefaultVirtualDesktopGuid))
|
||||||
{
|
{
|
||||||
var settings = new LayoutSettings
|
var settings = new LayoutSettings
|
||||||
{
|
{
|
||||||
|
|||||||
Reference in New Issue
Block a user