Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions src/modules/fancyzones/FancyZonesLib/Settings.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ namespace NonLocalizable
const wchar_t MouseMiddleClickSpanningMultipleZonesID[] = L"fancyzones_mouseMiddleClickSpanningMultipleZones";
const wchar_t OverrideSnapHotKeysID[] = L"fancyzones_overrideSnapHotkeys";
const wchar_t MoveWindowAcrossMonitorsID[] = L"fancyzones_moveWindowAcrossMonitors";
const wchar_t CycleThroughAllZonesID[] = L"fancyzones_cycleThroughAllZones";
const wchar_t MoveWindowsBasedOnPositionID[] = L"fancyzones_moveWindowsBasedOnPosition";
const wchar_t OverlappingZonesAlgorithmID[] = L"fancyzones_overlappingZonesAlgorithm";
const wchar_t DisplayOrWorkAreaChangeMoveWindowsID[] = L"fancyzones_displayOrWorkAreaChange_moveWindows";
Expand Down Expand Up @@ -111,6 +112,7 @@ void FancyZonesSettings::LoadSettings()
SetBoolFlag(values, NonLocalizable::MouseMiddleClickSpanningMultipleZonesID, SettingId::MouseMiddleClickSpanningMultipleZones, m_settings.mouseMiddleClickSpanningMultipleZones);
SetBoolFlag(values, NonLocalizable::OverrideSnapHotKeysID, SettingId::OverrideSnapHotkeys, m_settings.overrideSnapHotkeys);
SetBoolFlag(values, NonLocalizable::MoveWindowAcrossMonitorsID, SettingId::MoveWindowAcrossMonitors, m_settings.moveWindowAcrossMonitors);
SetBoolFlag(values, NonLocalizable::CycleThroughAllZonesID, SettingId::CycleThroughAllZones, m_settings.cycleThroughAllZones);
SetBoolFlag(values, NonLocalizable::MoveWindowsBasedOnPositionID, SettingId::MoveWindowsBasedOnPosition, m_settings.moveWindowsBasedOnPosition);
SetBoolFlag(values, NonLocalizable::DisplayOrWorkAreaChangeMoveWindowsID, SettingId::DisplayOrWorkAreaChangeMoveWindows, m_settings.displayOrWorkAreaChange_moveWindows);
SetBoolFlag(values, NonLocalizable::ZoneSetChangeMoveWindowsID, SettingId::ZoneSetChangeMoveWindows, m_settings.zoneSetChange_moveWindows);
Expand Down
1 change: 1 addition & 0 deletions src/modules/fancyzones/FancyZonesLib/Settings.h
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ struct Settings
bool zoneSetChange_moveWindows = false;
bool overrideSnapHotkeys = false;
bool moveWindowAcrossMonitors = false;
bool cycleThroughAllZones = true;
bool moveWindowsBasedOnPosition = false;
bool appLastZone_moveWindows = false;
bool openWindowOnActiveMonitor = false;
Expand Down
1 change: 1 addition & 0 deletions src/modules/fancyzones/FancyZonesLib/SettingsConstants.h
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ enum class SettingId
MouseMiddleClickSpanningMultipleZones,
OverrideSnapHotkeys,
MoveWindowAcrossMonitors,
CycleThroughAllZones,
MoveWindowsBasedOnPosition,
OverlappingZonesAlgorithm,
DisplayOrWorkAreaChangeMoveWindows,
Expand Down
29 changes: 23 additions & 6 deletions src/modules/fancyzones/FancyZonesLib/WindowKeyboardSnap.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -25,32 +25,46 @@ bool WindowKeyboardSnap::Snap(HWND window, RECT windowRect, HMONITOR monitor, DW
// clean previous extension data
m_extendData.Reset();

bool success = false;
bool cycle = FancyZonesSettings::settings().cycleThroughAllZones;

const auto& currentWorkArea = activeWorkAreas.at(monitor);
if (monitors.size() > 1 && FancyZonesSettings::settings().moveWindowAcrossMonitors)
{
// Multi monitor environment.
// First, try to stay on the same monitor
bool success = MoveByDirectionAndPosition(window, windowRect, vkCode, false, currentWorkArea.get());
success = MoveByDirectionAndPosition(window, windowRect, vkCode, false, currentWorkArea.get());
if (success)
{
return true;
}

// Try to snap on another monitor
success = SnapBasedOnPositionOnAnotherMonitor(window, windowRect, vkCode, monitor, activeWorkAreas, monitors);
success = SnapBasedOnPositionOnAnotherMonitor(window, windowRect, vkCode, cycle, monitor, activeWorkAreas, monitors);
if (success)
{
// Unsnap from previous work area
currentWorkArea->Unsnap(window);
}

return success;
}
else
{
// Single monitor environment, or combined multi-monitor environment.
return MoveByDirectionAndPosition(window, windowRect, vkCode, true, currentWorkArea.get());
success = MoveByDirectionAndPosition(window, windowRect, vkCode, cycle, currentWorkArea.get());
}

if (!success && (vkCode == VK_UP || vkCode == VK_DOWN))
{
WINDOWPLACEMENT placement{};
GetWindowPlacement(window, &placement);
if (vkCode == VK_UP)
placement.showCmd = SW_SHOWMAXIMIZED;
else if (vkCode == VK_DOWN)
placement.showCmd = SW_SHOWMINIMIZED;
success = SetWindowPlacement(window, &placement);
}

return success;
}

bool WindowKeyboardSnap::Extend(HWND window, RECT windowRect, HMONITOR monitor, DWORD vkCode, const std::unordered_map<HMONITOR, std::unique_ptr<WorkArea>>& activeWorkAreas)
Expand Down Expand Up @@ -133,7 +147,7 @@ bool WindowKeyboardSnap::SnapHotkeyBasedOnZoneNumber(HWND window, DWORD vkCode,
return false;
}

bool WindowKeyboardSnap::SnapBasedOnPositionOnAnotherMonitor(HWND window, RECT windowRect, DWORD vkCode, HMONITOR current, const std::unordered_map<HMONITOR, std::unique_ptr<WorkArea>>& activeWorkAreas, const std::vector<std::pair<HMONITOR, RECT>>& monitors)
bool WindowKeyboardSnap::SnapBasedOnPositionOnAnotherMonitor(HWND window, RECT windowRect, DWORD vkCode, bool cycle, HMONITOR current, const std::unordered_map<HMONITOR, std::unique_ptr<WorkArea>>& activeWorkAreas, const std::vector<std::pair<HMONITOR, RECT>>& monitors)
{
// Extract zones from all other monitors and target one of them
std::vector<RECT> zoneRects;
Expand Down Expand Up @@ -192,6 +206,9 @@ bool WindowKeyboardSnap::SnapBasedOnPositionOnAnotherMonitor(HWND window, RECT w
return snapped;
}

if (!cycle)
return false;

// We reached the end of all monitors.
// Try again, cycling on all monitors.
// First, add zones from the origin monitor to zoneRects
Expand Down
2 changes: 1 addition & 1 deletion src/modules/fancyzones/FancyZonesLib/WindowKeyboardSnap.h
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ class WindowKeyboardSnap

private:
bool SnapHotkeyBasedOnZoneNumber(HWND window, DWORD vkCode, HMONITOR monitor, const std::unordered_map<HMONITOR, std::unique_ptr<WorkArea>>& activeWorkAreas, const std::vector<HMONITOR>& monitors);
bool SnapBasedOnPositionOnAnotherMonitor(HWND window, RECT windowRect, DWORD vkCode, HMONITOR monitor, const std::unordered_map<HMONITOR, std::unique_ptr<WorkArea>>& activeWorkAreas, const std::vector<std::pair<HMONITOR, RECT>>& monitors);
bool SnapBasedOnPositionOnAnotherMonitor(HWND window, RECT windowRect, DWORD vkCode, bool cycle, HMONITOR monitor, const std::unordered_map<HMONITOR, std::unique_ptr<WorkArea>>& activeWorkAreas, const std::vector<std::pair<HMONITOR, RECT>>& monitors);

bool MoveByDirectionAndIndex(HWND window, DWORD vkCode, bool cycle, WorkArea* const workArea);
bool MoveByDirectionAndPosition(HWND window, RECT windowRect, DWORD vkCode, bool cycle, WorkArea* const workArea);
Expand Down
2 changes: 2 additions & 0 deletions src/modules/fancyzones/FancyZonesLib/trace.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@
#define MoveWindowsOnZoneSetChangeKey "MoveWindowsOnZoneSetChange"
#define OverrideSnapHotKeysKey "OverrideSnapHotKeys"
#define MoveWindowAcrossMonitorsKey "MoveWindowAcrossMonitors"
#define CycleThroughAllZonesKey "CycleThroughAllZones"
#define MoveWindowsBasedOnPositionKey "MoveWindowsBasedOnPosition"
#define MoveWindowsToLastZoneOnAppOpeningKey "MoveWindowsToLastZoneOnAppOpening"
#define OpenWindowOnActiveMonitorKey "OpenWindowOnActiveMonitor"
Expand Down Expand Up @@ -303,6 +304,7 @@ void Trace::SettingsTelemetry(const Settings& settings) noexcept
TraceLoggingBoolean(settings.zoneSetChange_moveWindows, MoveWindowsOnZoneSetChangeKey),
TraceLoggingBoolean(settings.overrideSnapHotkeys, OverrideSnapHotKeysKey),
TraceLoggingBoolean(settings.moveWindowAcrossMonitors, MoveWindowAcrossMonitorsKey),
TraceLoggingBoolean(settings.cycleThroughAllZones, CycleThroughAllZonesKey),
TraceLoggingBoolean(settings.moveWindowsBasedOnPosition, MoveWindowsBasedOnPositionKey),
TraceLoggingBoolean(settings.appLastZone_moveWindows, MoveWindowsToLastZoneOnAppOpeningKey),
TraceLoggingBoolean(settings.openWindowOnActiveMonitor, OpenWindowOnActiveMonitorKey),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ namespace FancyZonesUnitTests
Assert::AreEqual(expected.zoneSetChange_moveWindows, actual.zoneSetChange_moveWindows);
Assert::AreEqual(expected.overrideSnapHotkeys, actual.overrideSnapHotkeys);
Assert::AreEqual(expected.moveWindowAcrossMonitors, actual.moveWindowAcrossMonitors);
Assert::AreEqual(expected.cycleThroughAllZones, actual.cycleThroughAllZones);
Assert::AreEqual(expected.moveWindowsBasedOnPosition, actual.moveWindowsBasedOnPosition);
Assert::AreEqual(expected.appLastZone_moveWindows, actual.appLastZone_moveWindows);
Assert::AreEqual(expected.openWindowOnActiveMonitor, actual.openWindowOnActiveMonitor);
Expand Down Expand Up @@ -74,6 +75,7 @@ namespace FancyZonesUnitTests
values.add_property(L"fancyzones_zoneSetChange_moveWindows", m_defaultSettings.zoneSetChange_moveWindows);
values.add_property(L"fancyzones_overrideSnapHotkeys", m_defaultSettings.overrideSnapHotkeys);
values.add_property(L"fancyzones_moveWindowAcrossMonitors", m_defaultSettings.moveWindowAcrossMonitors);
values.add_property(L"fancyzones_cycleThroughAllZones", m_defaultSettings.cycleThroughAllZones);
values.add_property(L"fancyzones_moveWindowsBasedOnPosition", m_defaultSettings.moveWindowsBasedOnPosition);
values.add_property(L"fancyzones_appLastZone_moveWindows", m_defaultSettings.appLastZone_moveWindows);
values.add_property(L"fancyzones_openWindowOnActiveMonitor", m_defaultSettings.openWindowOnActiveMonitor);
Expand Down Expand Up @@ -117,6 +119,7 @@ namespace FancyZonesUnitTests
values.add_property(L"fancyzones_zoneSetChange_moveWindows", expected.zoneSetChange_moveWindows);
values.add_property(L"fancyzones_overrideSnapHotkeys", expected.overrideSnapHotkeys);
values.add_property(L"fancyzones_moveWindowAcrossMonitors", expected.moveWindowAcrossMonitors);
values.add_property(L"fancyzones_cycleThroughAllZones", expected.cycleThroughAllZones);
values.add_property(L"fancyzones_moveWindowsBasedOnPosition", expected.moveWindowsBasedOnPosition);
values.add_property(L"fancyzones_appLastZone_moveWindows", expected.appLastZone_moveWindows);
values.add_property(L"fancyzones_openWindowOnActiveMonitor", expected.openWindowOnActiveMonitor);
Expand Down
4 changes: 4 additions & 0 deletions src/settings-ui/Settings.UI.Library/FZConfigProperties.cs
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ public FZConfigProperties()
FancyzonesMouseSwitch = new BoolProperty();
FancyzonesMouseMiddleClickSpanningMultipleZones = new BoolProperty();
FancyzonesMoveWindowsAcrossMonitors = new BoolProperty();
FancyzonesCycleThroughAllZones = new BoolProperty();
FancyzonesMoveWindowsBasedOnPosition = new BoolProperty();
FancyzonesOverlappingZonesAlgorithm = new IntProperty();
FancyzonesDisplayOrWorkAreaChangeMoveWindows = new BoolProperty(ConfigDefaults.DefaultFancyzonesDisplayOrWorkAreaChangeMoveWindows);
Expand Down Expand Up @@ -72,6 +73,9 @@ public FZConfigProperties()
[JsonPropertyName("fancyzones_moveWindowAcrossMonitors")]
public BoolProperty FancyzonesMoveWindowsAcrossMonitors { get; set; }

[JsonPropertyName("fancyzones_cycleThroughAllZones")]
public BoolProperty FancyzonesCycleThroughAllZones { get; set; }

[JsonPropertyName("fancyzones_moveWindowsBasedOnPosition")]
public BoolProperty FancyzonesMoveWindowsBasedOnPosition { get; set; }

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,7 @@ public void OriginalFilesModificationTest(string version, string fileName)
Assert.AreEqual(originalSettings.Properties.FancyzonesMakeDraggedWindowTransparent.Value, viewModel.MakeDraggedWindowsTransparent);
Assert.AreEqual(originalSettings.Properties.FancyzonesMouseSwitch.Value, viewModel.MouseSwitch);
Assert.AreEqual(originalSettings.Properties.FancyzonesMoveWindowsAcrossMonitors.Value, viewModel.MoveWindowsAcrossMonitors);
Assert.AreEqual(originalSettings.Properties.FancyzonesCycleThroughAllZones.Value, viewModel.CycleThroughAllZones);
Assert.AreEqual(originalSettings.Properties.FancyzonesMoveWindowsBasedOnPosition.Value, viewModel.MoveWindowsBasedOnPosition);
Assert.AreEqual(originalSettings.Properties.FancyzonesOpenWindowOnActiveMonitor.Value, viewModel.OpenWindowOnActiveMonitor);
Assert.AreEqual(originalSettings.Properties.FancyzonesOverrideSnapHotkeys.Value, viewModel.OverrideSnapHotkeys);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -254,6 +254,12 @@
IsEnabled="{x:Bind ViewModel.SnapHotkeysCategoryEnabled, Mode=OneWay}">
<CheckBox x:Uid="FancyZones_MoveWindowsAcrossAllMonitorsCheckBoxControl" IsChecked="{x:Bind ViewModel.MoveWindowsAcrossMonitors, Mode=TwoWay}" />
</tkcontrols:SettingsCard>
<tkcontrols:SettingsCard
Name="FancyZonesCycleThroughAllZones"
ContentAlignment="Left"
IsEnabled="{x:Bind ViewModel.SnapHotkeysCategoryEnabled, Mode=OneWay}">
<CheckBox x:Uid="FancyZones_CycleThroughAllZonesCheckBoxControl" IsChecked="{x:Bind ViewModel.CycleThroughAllZones, Mode=TwoWay}" />
</tkcontrols:SettingsCard>
</tkcontrols:SettingsExpander.Items>
</tkcontrols:SettingsExpander>
</controls:SettingsGroup>
Expand Down
3 changes: 3 additions & 0 deletions src/settings-ui/Settings.UI/Strings/en-us/Resources.resw
Original file line number Diff line number Diff line change
Expand Up @@ -864,6 +864,9 @@ opera.exe</value>
<data name="FancyZones_MoveWindowsAcrossAllMonitorsCheckBoxControl.Content" xml:space="preserve">
<value>Move windows between zones across all monitors</value>
</data>
<data name="FancyZones_CycleThroughAllZonesCheckBoxControl.Content" xml:space="preserve">
<value>Cycle through all zones</value>
</data>
<data name="FancyZones_OverrideSnapHotkeys.Header" xml:space="preserve">
<value>Override Windows Snap</value>
</data>
Expand Down
20 changes: 20 additions & 0 deletions src/settings-ui/Settings.UI/ViewModels/FancyZonesViewModel.cs
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,7 @@ public FancyZonesViewModel(SettingsUtils settingsUtils, ISettingsRepository<Gene
_mouseMiddleButtonSpanningMultipleZones = Settings.Properties.FancyzonesMouseMiddleClickSpanningMultipleZones.Value;
_overrideSnapHotkeys = Settings.Properties.FancyzonesOverrideSnapHotkeys.Value;
_moveWindowsAcrossMonitors = Settings.Properties.FancyzonesMoveWindowsAcrossMonitors.Value;
_cycleThroughAllZones = Settings.Properties.FancyzonesCycleThroughAllZones.Value;
_moveWindowBehaviour = Settings.Properties.FancyzonesMoveWindowsBasedOnPosition.Value ? MoveWindowBehaviour.MoveWindowBasedOnPosition : MoveWindowBehaviour.MoveWindowBasedOnZoneIndex;
_overlappingZonesAlgorithm = (OverlappingZonesAlgorithm)Settings.Properties.FancyzonesOverlappingZonesAlgorithm.Value;
_displayOrWorkAreaChangeMoveWindows = Settings.Properties.FancyzonesDisplayOrWorkAreaChangeMoveWindows.Value;
Expand Down Expand Up @@ -155,6 +156,7 @@ public override Dictionary<string, HotkeySettings[]> GetAllHotkeySettings()
private bool _mouseMiddleButtonSpanningMultipleZones;
private bool _overrideSnapHotkeys;
private bool _moveWindowsAcrossMonitors;
private bool _cycleThroughAllZones;
private MoveWindowBehaviour _moveWindowBehaviour;
private OverlappingZonesAlgorithm _overlappingZonesAlgorithm;
private bool _displayOrWorkAreaChangeMoveWindows;
Expand Down Expand Up @@ -342,6 +344,24 @@ public bool MoveWindowsAcrossMonitors
}
}

public bool CycleThroughAllZones
{
get
{
return _cycleThroughAllZones;
}

set
{
if (value != _cycleThroughAllZones)
{
_cycleThroughAllZones = value;
Settings.Properties.FancyzonesCycleThroughAllZones.Value = value;
NotifyPropertyChanged();
}
}
}

public bool MoveWindowsBasedOnPosition
{
get
Expand Down