Thread safety for FanncyZonesData (#1281)

* FancyZones: make FancyZonesData thread-safe

* fixup: format affected sources

* fixup: clang-format case-style and format FancyZones.cpp

* fixup! add missing lock
This commit is contained in:
Andrey Nekrasov 2020-02-17 18:28:49 +03:00 committed by GitHub
parent cdf2f6b5b4
commit 1e6936a8c3
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
10 changed files with 1631 additions and 1533 deletions

View File

@ -20,6 +20,7 @@ AlwaysBreakTemplateDeclarations: Yes
BinPackArguments: false
BinPackParameters: false
BraceWrapping:
AfterCaseLabel: true
AfterClass: true
AfterControlStatement: true
AfterEnum: true
@ -28,7 +29,7 @@ BraceWrapping:
AfterObjCDeclaration: true
AfterStruct: true
AfterUnion: true
AfterExternBlock: false
AfterExternBlock: true
BeforeCatch: true
BeforeElse: true
IndentBraces: false
@ -90,4 +91,4 @@ SpacesInParentheses: false
SpacesInSquareBrackets: false
Standard: Cpp11
TabWidth: 4
UseTab: Never
UseTab: Never

View File

@ -47,28 +47,42 @@ public:
}
// IFancyZones
IFACEMETHODIMP_(void) Run() noexcept;
IFACEMETHODIMP_(void) Destroy() noexcept;
IFACEMETHODIMP_(void)
Run() noexcept;
IFACEMETHODIMP_(void)
Destroy() noexcept;
// IFancyZonesCallback
IFACEMETHODIMP_(bool) InMoveSize() noexcept
IFACEMETHODIMP_(bool)
InMoveSize() noexcept
{
std::shared_lock readLock(m_lock);
return m_inMoveSize;
}
IFACEMETHODIMP_(void) MoveSizeStart(HWND window, HMONITOR monitor, POINT const& ptScreen) noexcept;
IFACEMETHODIMP_(void) MoveSizeUpdate(HMONITOR monitor, POINT const& ptScreen) noexcept;
IFACEMETHODIMP_(void) MoveSizeEnd(HWND window, POINT const& ptScreen) noexcept;
IFACEMETHODIMP_(void) VirtualDesktopChanged() noexcept;
IFACEMETHODIMP_(void) VirtualDesktopInitialize() noexcept;
IFACEMETHODIMP_(void) WindowCreated(HWND window) noexcept;
IFACEMETHODIMP_(bool) OnKeyDown(PKBDLLHOOKSTRUCT info) noexcept;
IFACEMETHODIMP_(void) ToggleEditor() noexcept;
IFACEMETHODIMP_(void) SettingsChanged() noexcept;
IFACEMETHODIMP_(void)
MoveSizeStart(HWND window, HMONITOR monitor, POINT const& ptScreen) noexcept;
IFACEMETHODIMP_(void)
MoveSizeUpdate(HMONITOR monitor, POINT const& ptScreen) noexcept;
IFACEMETHODIMP_(void)
MoveSizeEnd(HWND window, POINT const& ptScreen) noexcept;
IFACEMETHODIMP_(void)
VirtualDesktopChanged() noexcept;
IFACEMETHODIMP_(void)
VirtualDesktopInitialize() noexcept;
IFACEMETHODIMP_(void)
WindowCreated(HWND window) noexcept;
IFACEMETHODIMP_(bool)
OnKeyDown(PKBDLLHOOKSTRUCT info) noexcept;
IFACEMETHODIMP_(void)
ToggleEditor() noexcept;
IFACEMETHODIMP_(void)
SettingsChanged() noexcept;
// IZoneWindowHost
IFACEMETHODIMP_(void) MoveWindowsOnActiveZoneSetChange() noexcept;
IFACEMETHODIMP_(COLORREF) GetZoneHighlightColor() noexcept
IFACEMETHODIMP_(void)
MoveWindowsOnActiveZoneSetChange() noexcept;
IFACEMETHODIMP_(COLORREF)
GetZoneHighlightColor() noexcept
{
// Skip the leading # and convert to long
const auto color = m_settings->GetSettings().zoneHightlightColor;
@ -78,7 +92,8 @@ public:
const auto nB = (tmp & 0xFF);
return RGB(nR, nG, nB);
}
IFACEMETHODIMP_(IZoneWindow*)GetParentZoneWindow(HMONITOR monitor) noexcept
IFACEMETHODIMP_(IZoneWindow*)
GetParentZoneWindow(HMONITOR monitor) noexcept
{
//NOTE: as public method it's unsafe without lock, but it's called from AddZoneWindow through making ZoneWindow that causes deadlock
//TODO: needs refactoring
@ -89,7 +104,8 @@ public:
}
return nullptr;
}
IFACEMETHODIMP_(int) GetZoneHighlightOpacity() noexcept
IFACEMETHODIMP_(int)
GetZoneHighlightOpacity() noexcept
{
return m_settings->GetSettings().zoneHighlightOpacity;
}
@ -176,7 +192,8 @@ UINT FancyZones::WM_PRIV_VDINIT = RegisterWindowMessage(L"{469818a8-00fa-4069-b8
UINT FancyZones::WM_PRIV_EDITOR = RegisterWindowMessage(L"{87543824-7080-4e91-9d9c-0404642fc7b6}");
// IFancyZones
IFACEMETHODIMP_(void) FancyZones::Run() noexcept
IFACEMETHODIMP_(void)
FancyZones::Run() noexcept
{
std::unique_lock writeLock(m_lock);
@ -212,7 +229,8 @@ IFACEMETHODIMP_(void) FancyZones::Run() noexcept
}
// IFancyZones
IFACEMETHODIMP_(void) FancyZones::Destroy() noexcept
IFACEMETHODIMP_(void)
FancyZones::Destroy() noexcept
{
std::unique_lock writeLock(m_lock);
m_zoneWindowMap.clear();
@ -234,7 +252,8 @@ IFACEMETHODIMP_(void) FancyZones::Destroy() noexcept
}
// IFancyZonesCallback
IFACEMETHODIMP_(void) FancyZones::MoveSizeStart(HWND window, HMONITOR monitor, POINT const& ptScreen) noexcept
IFACEMETHODIMP_(void)
FancyZones::MoveSizeStart(HWND window, HMONITOR monitor, POINT const& ptScreen) noexcept
{
if (IsInterestingWindow(window))
{
@ -244,14 +263,16 @@ IFACEMETHODIMP_(void) FancyZones::MoveSizeStart(HWND window, HMONITOR monitor, P
}
// IFancyZonesCallback
IFACEMETHODIMP_(void) FancyZones::MoveSizeUpdate(HMONITOR monitor, POINT const& ptScreen) noexcept
IFACEMETHODIMP_(void)
FancyZones::MoveSizeUpdate(HMONITOR monitor, POINT const& ptScreen) noexcept
{
std::unique_lock writeLock(m_lock);
MoveSizeUpdateInternal(monitor, ptScreen, writeLock);
}
// IFancyZonesCallback
IFACEMETHODIMP_(void) FancyZones::MoveSizeEnd(HWND window, POINT const& ptScreen) noexcept
IFACEMETHODIMP_(void)
FancyZones::MoveSizeEnd(HWND window, POINT const& ptScreen) noexcept
{
if (window == m_windowMoveSize || IsInterestingWindow(window))
{
@ -261,7 +282,8 @@ IFACEMETHODIMP_(void) FancyZones::MoveSizeEnd(HWND window, POINT const& ptScreen
}
// IFancyZonesCallback
IFACEMETHODIMP_(void) FancyZones::VirtualDesktopChanged() noexcept
IFACEMETHODIMP_(void)
FancyZones::VirtualDesktopChanged() noexcept
{
// VirtualDesktopChanged is called from another thread but results in new windows being created.
// Jump over to the UI thread to handle it.
@ -270,13 +292,15 @@ IFACEMETHODIMP_(void) FancyZones::VirtualDesktopChanged() noexcept
}
// IFancyZonesCallback
IFACEMETHODIMP_(void) FancyZones::VirtualDesktopInitialize() noexcept
IFACEMETHODIMP_(void)
FancyZones::VirtualDesktopInitialize() noexcept
{
PostMessage(m_window, WM_PRIV_VDINIT, 0, 0);
}
// IFancyZonesCallback
IFACEMETHODIMP_(void) FancyZones::WindowCreated(HWND window) noexcept
IFACEMETHODIMP_(void)
FancyZones::WindowCreated(HWND window) noexcept
{
if (m_settings->GetSettings().appLastZone_moveWindows && IsInterestingWindow(window))
{
@ -308,7 +332,8 @@ IFACEMETHODIMP_(void) FancyZones::WindowCreated(HWND window) noexcept
}
// IFancyZonesCallback
IFACEMETHODIMP_(bool) FancyZones::OnKeyDown(PKBDLLHOOKSTRUCT info) noexcept
IFACEMETHODIMP_(bool)
FancyZones::OnKeyDown(PKBDLLHOOKSTRUCT info) noexcept
{
// Return true to swallow the keyboard event
bool const shift = GetAsyncKeyState(VK_SHIFT) & 0x8000;
@ -430,9 +455,13 @@ void FancyZones::ToggleEditor() noexcept
std::to_wstring(width) + L"_" +
std::to_wstring(height);
const auto& deviceInfo = fancyZonesData.GetDeviceInfoMap().at(zoneWindow->UniqueId());
const auto deviceInfo = fancyZonesData.FindDeviceInfo(zoneWindow->UniqueId());
if (!deviceInfo.has_value())
{
return;
}
JSONHelpers::DeviceInfoJSON deviceInfoJson{ zoneWindow->UniqueId(), deviceInfo };
JSONHelpers::DeviceInfoJSON deviceInfoJson{ zoneWindow->UniqueId(), *deviceInfo };
fancyZonesData.SerializeDeviceInfoToTmpFile(deviceInfoJson, ZoneWindowUtils::GetActiveZoneSetTmpPath());
const std::wstring params =
@ -484,7 +513,8 @@ void FancyZones::SettingsChanged() noexcept
}
// IZoneWindowHost
IFACEMETHODIMP_(void) FancyZones::MoveWindowsOnActiveZoneSetChange() noexcept
IFACEMETHODIMP_(void)
FancyZones::MoveWindowsOnActiveZoneSetChange() noexcept
{
if (m_settings->GetSettings().zoneSetChange_moveWindows)
{
@ -566,7 +596,7 @@ void FancyZones::OnDisplayChange(DisplayChangeType changeType) noexcept
GUID currentVirtualDesktopId{};
if (SUCCEEDED(RegistryHelpers::GetCurrentVirtualDesktop(&currentVirtualDesktopId)))
{
std::unique_lock writeLock(m_lock);
std::unique_lock writeLock(m_lock);
m_currentVirtualDesktopId = currentVirtualDesktopId;
}
else

View File

@ -135,13 +135,10 @@ namespace JSONHelpers
jsonFilePath = result + L"\\" + std::wstring(FANCY_ZONES_DATA_FILE);
}
const std::wstring& FancyZonesData::GetPersistFancyZonesJSONPath() const
{
return jsonFilePath;
}
json::JsonObject FancyZonesData::GetPersistFancyZonesJSON()
{
std::scoped_lock lock{ dataLock };
std::wstring save_file_path = GetPersistFancyZonesJSONPath();
auto result = json::from_file(save_file_path);
@ -155,12 +152,27 @@ namespace JSONHelpers
}
}
std::optional<DeviceInfoData> FancyZonesData::FindDeviceInfo(const std::wstring& zoneWindowId) const
{
std::scoped_lock lock{ dataLock };
auto it = deviceInfoMap.find(zoneWindowId);
return it != end(deviceInfoMap) ? std::optional{ it->second } : std::nullopt;
}
std::optional<CustomZoneSetData> FancyZonesData::FindCustomZoneSet(const std::wstring& guuid) const
{
std::scoped_lock lock{ dataLock };
auto it = customZoneSetsMap.find(guuid);
return it != end(customZoneSetsMap) ? std::optional{ it->second } : std::nullopt;
}
void FancyZonesData::AddDevice(const std::wstring& deviceId)
{
std::scoped_lock lock{ dataLock };
if (!deviceInfoMap.contains(deviceId))
{
// Creates default entry in map when ZoneWindow is created
deviceInfoMap[deviceId] = DeviceInfoData{ ZoneSetData{ L"null", ZoneSetLayoutType::Blank } };
deviceInfoMap[deviceId] = DeviceInfoData{ ZoneSetData{ L"null", ZoneSetLayoutType::Blank } };
MigrateDeviceInfoFromRegistry(deviceId);
}
@ -168,6 +180,7 @@ namespace JSONHelpers
void FancyZonesData::CloneDeviceInfo(const std::wstring& source, const std::wstring& destination)
{
std::scoped_lock lock{ dataLock };
// Clone information from source device if destination device is uninitialized (Blank).
auto& destInfo = deviceInfoMap[destination];
if (destInfo.activeZoneSet.type == ZoneSetLayoutType::Blank)
@ -178,6 +191,7 @@ namespace JSONHelpers
int FancyZonesData::GetAppLastZoneIndex(HWND window, const std::wstring_view& deviceId, const std::wstring_view& zoneSetId) const
{
std::scoped_lock lock{ dataLock };
auto processPath = get_process_path(window);
if (!processPath.empty())
{
@ -188,7 +202,7 @@ namespace JSONHelpers
if (data.zoneSetUuid == zoneSetId && data.deviceId == deviceId)
{
return history->second.zoneIndex;
}
}
}
}
@ -197,6 +211,7 @@ namespace JSONHelpers
bool FancyZonesData::RemoveAppLastZone(HWND window, const std::wstring_view& deviceId, const std::wstring_view& zoneSetId)
{
std::scoped_lock lock{ dataLock };
auto processPath = get_process_path(window);
if (!processPath.empty())
{
@ -218,6 +233,7 @@ namespace JSONHelpers
bool FancyZonesData::SetAppLastZone(HWND window, const std::wstring& deviceId, const std::wstring& zoneSetId, int zoneIndex)
{
std::scoped_lock lock{ dataLock };
auto processPath = get_process_path(window);
if (processPath.empty())
{
@ -231,6 +247,7 @@ namespace JSONHelpers
void FancyZonesData::SetActiveZoneSet(const std::wstring& deviceId, const ZoneSetData& data)
{
std::scoped_lock lock{ dataLock };
auto it = deviceInfoMap.find(deviceId);
if (it != deviceInfoMap.end())
{
@ -240,12 +257,14 @@ namespace JSONHelpers
void FancyZonesData::SerializeDeviceInfoToTmpFile(const DeviceInfoJSON& deviceInfo, std::wstring_view tmpFilePath) const
{
std::scoped_lock lock{ dataLock };
json::JsonObject deviceInfoJson = DeviceInfoJSON::ToJson(deviceInfo);
json::to_file(tmpFilePath, deviceInfoJson);
}
void FancyZonesData::ParseDeviceInfoFromTmpFile(std::wstring_view tmpFilePath)
{
std::scoped_lock lock{ dataLock };
if (std::filesystem::exists(tmpFilePath))
{
if (auto zoneSetJson = json::from_file(tmpFilePath); zoneSetJson.has_value())
@ -266,6 +285,7 @@ namespace JSONHelpers
bool FancyZonesData::ParseCustomZoneSetFromTmpFile(std::wstring_view tmpFilePath)
{
std::scoped_lock lock{ dataLock };
bool res = true;
if (std::filesystem::exists(tmpFilePath))
{
@ -291,6 +311,7 @@ namespace JSONHelpers
bool FancyZonesData::ParseDeletedCustomZoneSetsFromTmpFile(std::wstring_view tmpFilePath)
{
std::scoped_lock lock{ dataLock };
bool res = true;
if (std::filesystem::exists(tmpFilePath))
{
@ -317,6 +338,7 @@ namespace JSONHelpers
bool FancyZonesData::ParseAppZoneHistory(const json::JsonObject& fancyZonesDataJSON)
{
std::scoped_lock lock{ dataLock };
try
{
auto appLastZones = fancyZonesDataJSON.GetNamedArray(L"app-zone-history");
@ -344,6 +366,7 @@ namespace JSONHelpers
json::JsonArray FancyZonesData::SerializeAppZoneHistory() const
{
std::scoped_lock lock{ dataLock };
json::JsonArray appHistoryArray;
for (const auto& [appPath, appZoneHistoryData] : appZoneHistoryMap)
@ -356,6 +379,7 @@ namespace JSONHelpers
bool FancyZonesData::ParseDeviceInfos(const json::JsonObject& fancyZonesDataJSON)
{
std::scoped_lock lock{ dataLock };
try
{
auto devices = fancyZonesDataJSON.GetNamedArray(L"devices");
@ -382,11 +406,13 @@ namespace JSONHelpers
json::JsonArray FancyZonesData::SerializeDeviceInfos() const
{
std::scoped_lock lock{ dataLock };
json::JsonArray DeviceInfosJSON{};
for (const auto& [deviceID, deviceData] : deviceInfoMap)
{
if (deviceData.activeZoneSet.type != ZoneSetLayoutType::Blank) {
if (deviceData.activeZoneSet.type != ZoneSetLayoutType::Blank)
{
DeviceInfosJSON.Append(DeviceInfoJSON::DeviceInfoJSON::ToJson(DeviceInfoJSON{ deviceID, deviceData }));
}
}
@ -396,6 +422,7 @@ namespace JSONHelpers
bool FancyZonesData::ParseCustomZoneSets(const json::JsonObject& fancyZonesDataJSON)
{
std::scoped_lock lock{ dataLock };
try
{
auto customZoneSets = fancyZonesDataJSON.GetNamedArray(L"custom-zone-sets");
@ -418,6 +445,7 @@ namespace JSONHelpers
json::JsonArray FancyZonesData::SerializeCustomZoneSets() const
{
std::scoped_lock lock{ dataLock };
json::JsonArray customZoneSetsJSON{};
for (const auto& [zoneSetId, zoneSetData] : customZoneSetsMap)
@ -430,6 +458,7 @@ namespace JSONHelpers
void FancyZonesData::CustomZoneSetsToJsonFile(std::wstring_view filePath) const
{
std::scoped_lock lock{ dataLock };
const auto& customZoneSetsJson = SerializeCustomZoneSets();
json::JsonObject root{};
root.SetNamedValue(L"custom-zone-sets", customZoneSetsJson);
@ -438,6 +467,7 @@ namespace JSONHelpers
void FancyZonesData::LoadFancyZonesData()
{
std::scoped_lock lock{ dataLock };
std::wstring jsonFilePath = GetPersistFancyZonesJSONPath();
if (!std::filesystem::exists(jsonFilePath))
@ -461,6 +491,7 @@ namespace JSONHelpers
void FancyZonesData::SaveFancyZonesData() const
{
std::scoped_lock lock{ dataLock };
json::JsonObject root{};
root.SetNamedValue(L"app-zone-history", SerializeAppZoneHistory());
@ -474,6 +505,7 @@ namespace JSONHelpers
{
std::wregex ex(L"^[0-9]{3,4}_[0-9]{3,4}$");
std::scoped_lock lock{ dataLock };
wchar_t key[256];
StringCchPrintf(key, ARRAYSIZE(key), L"%s", RegistryHelpers::REG_SETTINGS);
HKEY hkey;
@ -521,6 +553,7 @@ namespace JSONHelpers
void FancyZonesData::MigrateDeviceInfoFromRegistry(const std::wstring& deviceId)
{
std::scoped_lock lock{ dataLock };
wchar_t key[256];
StringCchPrintf(key, ARRAYSIZE(key), L"%s\\%s", RegistryHelpers::REG_SETTINGS, deviceId.c_str());
@ -546,6 +579,7 @@ namespace JSONHelpers
void FancyZonesData::MigrateCustomZoneSetsFromRegistry()
{
std::scoped_lock lock{ dataLock };
wchar_t key[256];
StringCchPrintf(key, ARRAYSIZE(key), L"%s\\%s", RegistryHelpers::REG_SETTINGS, L"Layouts");
HKEY hkey;
@ -574,8 +608,7 @@ namespace JSONHelpers
}
switch (zoneSetData.type)
{
case CustomLayoutType::Grid:
{
case CustomLayoutType::Grid: {
int j = 5;
GridLayoutInfo zoneSetInfo(GridLayoutInfo::Minimal{ .rows = data[j++], .columns = data[j++] });
@ -599,8 +632,7 @@ namespace JSONHelpers
zoneSetData.info = zoneSetInfo;
break;
}
case CustomLayoutType::Canvas:
{
case CustomLayoutType::Canvas: {
CanvasLayoutInfo info;
int j = 5;
@ -880,8 +912,7 @@ namespace JSONHelpers
result.SetNamedValue(L"name", json::value(customZoneSet.data.name));
switch (customZoneSet.data.type)
{
case CustomLayoutType::Canvas:
{
case CustomLayoutType::Canvas: {
result.SetNamedValue(L"type", json::value(L"canvas"));
CanvasLayoutInfo info = std::get<CanvasLayoutInfo>(customZoneSet.data.info);
@ -889,8 +920,7 @@ namespace JSONHelpers
break;
}
case CustomLayoutType::Grid:
{
case CustomLayoutType::Grid: {
result.SetNamedValue(L"type", json::value(L"grid"));
GridLayoutInfo gridInfo = std::get<GridLayoutInfo>(customZoneSet.data.info);

View File

@ -2,6 +2,7 @@
#include <common/settings_helpers.h>
#include <common/json.h>
#include <mutex>
#include <string>
#include <strsafe.h>
@ -159,12 +160,28 @@ namespace JSONHelpers
class FancyZonesData
{
mutable std::recursive_mutex dataLock;
public:
FancyZonesData();
const std::wstring& GetPersistFancyZonesJSONPath() const;
inline const std::wstring& GetPersistFancyZonesJSONPath() const
{
return jsonFilePath;
}
json::JsonObject GetPersistFancyZonesJSON();
std::optional<DeviceInfoData> FindDeviceInfo(const std::wstring& zoneWindowId) const;
std::optional<CustomZoneSetData> FindCustomZoneSet(const std::wstring& guuid) const;
inline const std::wstring GetActiveDeviceId() const
{
std::scoped_lock lock{ dataLock };
return activeDeviceId;
}
#if defined(UNIT_TESTS)
inline const std::unordered_map<std::wstring, DeviceInfoData>& GetDeviceInfoMap() const
{
return deviceInfoMap;
@ -180,13 +197,19 @@ namespace JSONHelpers
return appZoneHistoryMap;
}
inline const std::wstring GetActiveDeviceId() const
inline void clear_data()
{
return activeDeviceId;
appliedZoneSetsMap.clear();
appZoneHistoryMap.clear();
deviceInfoMap.clear();
customZoneSetsMap.clear();
activeDeviceId.clear();
}
#endif
void SetActiveDeviceId(const std::wstring& deviceId)
inline void SetActiveDeviceId(const std::wstring& deviceId)
{
std::scoped_lock lock{ dataLock };
activeDeviceId = deviceId;
}

View File

@ -497,13 +497,15 @@ bool ZoneSet::CalculateCustomLayout(Rect workArea, int spacing) noexcept
if (SUCCEEDED_LOG(StringFromCLSID(m_config.Id, &guuidStr)))
{
const std::wstring guuid = guuidStr.get();
const auto& customZoneSets = JSONHelpers::FancyZonesDataInstance().GetCustomZoneSetsMap();
if (!customZoneSets.contains(guuid))
const auto zoneSetSearchResult = JSONHelpers::FancyZonesDataInstance().FindCustomZoneSet(guuid);
if (!zoneSetSearchResult.has_value())
{
return false;
}
const auto& zoneSet = customZoneSets.at(guuid);
const auto& zoneSet = *zoneSetSearchResult;
if (zoneSet.type == JSONHelpers::CustomLayoutType::Canvas && std::holds_alternative<JSONHelpers::CanvasLayoutInfo>(zoneSet.info))
{
const auto& zoneSetInfo = std::get<JSONHelpers::CanvasLayoutInfo>(zoneSet.info);

View File

@ -280,14 +280,22 @@ public:
IFACEMETHODIMP MoveSizeUpdate(POINT const& ptScreen, bool dragEnabled) noexcept;
IFACEMETHODIMP MoveSizeEnd(HWND window, POINT const& ptScreen) noexcept;
IFACEMETHODIMP MoveSizeCancel() noexcept;
IFACEMETHODIMP_(bool) IsDragEnabled() noexcept { return m_dragEnabled; }
IFACEMETHODIMP_(void) MoveWindowIntoZoneByIndex(HWND window, int index) noexcept;
IFACEMETHODIMP_(void) MoveWindowIntoZoneByDirection(HWND window, DWORD vkCode) noexcept;
IFACEMETHODIMP_(void) CycleActiveZoneSet(DWORD vkCode) noexcept;
IFACEMETHODIMP_(std::wstring) UniqueId() noexcept { return { m_uniqueId }; }
IFACEMETHODIMP_(std::wstring) WorkAreaKey() noexcept { return { m_workArea }; }
IFACEMETHODIMP_(void) SaveWindowProcessToZoneIndex(HWND window) noexcept;
IFACEMETHODIMP_(IZoneSet*) ActiveZoneSet() noexcept { return m_activeZoneSet.get(); }
IFACEMETHODIMP_(bool)
IsDragEnabled() noexcept { return m_dragEnabled; }
IFACEMETHODIMP_(void)
MoveWindowIntoZoneByIndex(HWND window, int index) noexcept;
IFACEMETHODIMP_(void)
MoveWindowIntoZoneByDirection(HWND window, DWORD vkCode) noexcept;
IFACEMETHODIMP_(void)
CycleActiveZoneSet(DWORD vkCode) noexcept;
IFACEMETHODIMP_(std::wstring)
UniqueId() noexcept { return { m_uniqueId }; }
IFACEMETHODIMP_(std::wstring)
WorkAreaKey() noexcept { return { m_workArea }; }
IFACEMETHODIMP_(void)
SaveWindowProcessToZoneIndex(HWND window) noexcept;
IFACEMETHODIMP_(IZoneSet*)
ActiveZoneSet() noexcept { return m_activeZoneSet.get(); }
protected:
static LRESULT CALLBACK s_WndProc(HWND window, UINT message, WPARAM wparam, LPARAM lparam) noexcept;
@ -559,15 +567,21 @@ void ZoneWindow::InitializeZoneSets(MONITORINFO const& mi) noexcept
void ZoneWindow::CalculateZoneSet() noexcept
{
const auto& fancyZonesData = JSONHelpers::FancyZonesDataInstance();
const auto& deviceInfoMap = fancyZonesData.GetDeviceInfoMap();
const auto deviceInfoData = fancyZonesData.FindDeviceInfo(m_uniqueId);
const auto& activeDeviceId = fancyZonesData.GetActiveDeviceId();
const auto& activeZoneSet = deviceInfoMap.at(m_uniqueId).activeZoneSet;
if (!activeDeviceId.empty() && activeDeviceId != m_uniqueId)
{
return;
}
if (!deviceInfoData.has_value())
{
return;
}
const auto& activeZoneSet = deviceInfoData->activeZoneSet;
if (activeZoneSet.uuid.empty() || activeZoneSet.type == JSONHelpers::ZoneSetLayoutType::Blank)
{
return;
@ -585,9 +599,9 @@ void ZoneWindow::CalculateZoneSet() noexcept
monitorInfo.cbSize = sizeof(monitorInfo);
if (GetMonitorInfoW(m_monitor, &monitorInfo))
{
bool showSpacing = deviceInfoMap.at(m_uniqueId).showSpacing;
int spacing = showSpacing ? deviceInfoMap.at(m_uniqueId).spacing : 0;
int zoneCount = deviceInfoMap.at(m_uniqueId).zoneCount;
bool showSpacing = deviceInfoData->showSpacing;
int spacing = showSpacing ? deviceInfoData->spacing : 0;
int zoneCount = deviceInfoData->zoneCount;
zoneSet->CalculateZones(monitorInfo, zoneCount, spacing);
UpdateActiveZoneSet(zoneSet.get());
}

View File

@ -290,7 +290,7 @@ namespace FancyZonesUnitTests
m_fzCallback = fancyZones.as<IFancyZonesCallback>();
Assert::IsTrue(m_fzCallback != nullptr);
m_fancyZonesData = JSONHelpers::FancyZonesData();
m_fancyZonesData.clear_data();
}
TEST_METHOD_CLEANUP(Cleanup)

File diff suppressed because it is too large Load Diff

View File

@ -60,7 +60,7 @@
<Optimization>Disabled</Optimization>
<SDLCheck>true</SDLCheck>
<AdditionalIncludeDirectories>..\..\..\..\common\Telemetry;..\..\..\..\;..\..\..\..\..\deps\cpprestsdk\include;..\..\;$(VCInstallDir)UnitTest\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<PreprocessorDefinitions>_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PreprocessorDefinitions>UNIT_TESTS;_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<UseFullPaths>true</UseFullPaths>
<PrecompiledHeaderFile>pch.h</PrecompiledHeaderFile>
<LanguageStandard>stdcpplatest</LanguageStandard>
@ -81,7 +81,7 @@
<IntrinsicFunctions>true</IntrinsicFunctions>
<SDLCheck>true</SDLCheck>
<AdditionalIncludeDirectories>..\..\..\..\common\Telemetry;..\..\..\..\;..\..\..\..\..\deps\cpprestsdk\include;..\..\;$(VCInstallDir)UnitTest\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<PreprocessorDefinitions>NDEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PreprocessorDefinitions>UNIT_TESTS;NDEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<UseFullPaths>true</UseFullPaths>
<PrecompiledHeaderFile>pch.h</PrecompiledHeaderFile>
<LanguageStandard>stdcpplatest</LanguageStandard>

View File

@ -68,7 +68,7 @@ namespace FancyZonesUnitTests
GUID guid;
Assert::AreEqual(S_OK, CoCreateGuid(&guid));
return GuidString(guid);
return GuidString(guid);
}
TEST_METHOD_INITIALIZE(Init)
@ -89,7 +89,7 @@ namespace FancyZonesUnitTests
Assert::IsFalse(std::filesystem::exists(ZoneWindowUtils::GetAppliedZoneSetTmpPath()));
Assert::IsFalse(std::filesystem::exists(ZoneWindowUtils::GetCustomZoneSetsTmpPath()));
m_fancyZonesData = JSONHelpers::FancyZonesData();
m_fancyZonesData.clear_data();
}
TEST_METHOD_CLEANUP(Cleanup)
@ -622,7 +622,7 @@ namespace FancyZonesUnitTests
const auto processPath = get_process_path(window);
const auto deviceId = m_zoneWindow->UniqueId();
const auto zoneSetId = m_zoneWindow->ActiveZoneSet()->Id();
//fill app zone history map
Assert::IsTrue(m_fancyZonesData.SetAppLastZone(window, deviceId, GuidString(zoneSetId), 0));
Assert::AreEqual((size_t)1, m_fancyZonesData.GetAppZoneHistoryMap().size());