Skip to content
Merged
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
6 changes: 1 addition & 5 deletions Free Ruler/AppDelegate.swift
Original file line number Diff line number Diff line change
Expand Up @@ -525,7 +525,6 @@ class AppDelegate: NSObject, NSApplicationDelegate {

private func applyRulerWindowMode(showRulersIfNeeded: Bool = false) {
if rulerManager.hasRulers {
rulerManager.showAll()
updateMouseTickTimer()
return
}
Expand Down Expand Up @@ -745,8 +744,6 @@ class AppDelegate: NSObject, NSApplicationDelegate {
}

@IBAction func toggleGroupRulers(_ sender: Any) {
guard !rulerManager.hasRulers else { return }

prefs.groupRulers = !prefs.groupRulers
showGroupRulersHotkeyBezel(on: bezelScreen(for: sender))
}
Expand Down Expand Up @@ -1034,7 +1031,6 @@ class AppDelegate: NSObject, NSApplicationDelegate {
case kVK_ANSI_F:
toggleFloatRulers(sender)
case kVK_ANSI_G:
guard !rulerManager.hasRulers else { return true }
toggleGroupRulers(sender)
case kVK_ANSI_S:
toggleRulerShadow(sender)
Expand Down Expand Up @@ -1120,7 +1116,7 @@ extension AppDelegate: NSMenuItemValidation {
case #selector(closeKeyWindow(_:)):
return rulerManager.activeController != nil || NSApp.keyWindow?.isVisible == true
case #selector(toggleGroupRulers(_:)):
return !rulerManager.hasRulers
return true
case #selector(toggleHorizontalRuler(_:)):
if let controller = rulerManager.activeController {
let isVisible = controller.state.isWingVisible(.horizontal)
Expand Down
12 changes: 6 additions & 6 deletions Free Ruler/Base.lproj/MainMenu.xib
Original file line number Diff line number Diff line change
Expand Up @@ -218,16 +218,16 @@
</items>
</menu>
</menuItem>
<menuItem title="Float Rulers" keyEquivalent="f" id="GDK-AC-uC8">
<menuItem title="Group Rulers" keyEquivalent="g" id="7Ga-Fb-LLc">
<modifierMask key="keyEquivalentModifierMask"/>
<connections>
<action selector="toggleFloatRulers:" target="Voe-Tx-rLC" id="MFv-BV-ZRR"/>
<action selector="toggleGroupRulers:" target="Voe-Tx-rLC" id="0Dt-8h-7ed"/>
</connections>
</menuItem>
<menuItem title="Group Rulers" keyEquivalent="g" id="7Ga-Fb-LLc">
<menuItem title="Float Rulers" keyEquivalent="f" id="GDK-AC-uC8">
<modifierMask key="keyEquivalentModifierMask"/>
<connections>
<action selector="toggleGroupRulers:" target="Voe-Tx-rLC" id="0Dt-8h-7ed"/>
<action selector="toggleFloatRulers:" target="Voe-Tx-rLC" id="MFv-BV-ZRR"/>
</connections>
</menuItem>
<menuItem title="Show Ruler Shadow" keyEquivalent="s" id="a8D-hN-A59">
Expand All @@ -237,13 +237,13 @@
</connections>
</menuItem>
<menuItem isSeparatorItem="YES" id="hB3-LF-h0Y"/>
<menuItem title="Align Rulers at Mouse Location" keyEquivalent="o" id="iKV-uW-hwy">
<menuItem title="Align Ruler at Mouse Location" keyEquivalent="o" id="iKV-uW-hwy">
<modifierMask key="keyEquivalentModifierMask"/>
<connections>
<action selector="alignRulersAtMouseLocation:" target="Voe-Tx-rLC" id="sGx-h4-she"/>
</connections>
</menuItem>
<menuItem title="Reset Rulers" keyEquivalent="r" id="6ph-5N-O9R">
<menuItem title="Reset Ruler Position" keyEquivalent="r" id="6ph-5N-O9R">
<connections>
<action selector="resetRulerPositions:" target="Voe-Tx-rLC" id="fZ7-JH-EKI"/>
</connections>
Expand Down
83 changes: 83 additions & 0 deletions Free Ruler/GroupedRulerWindow.swift
Original file line number Diff line number Diff line change
Expand Up @@ -1096,6 +1096,9 @@ final class GroupedRulerController: NSWindowController, NSWindowDelegate, Notifi
let groupedWindow: GroupedRulerWindow
var state: RulerInstanceState
var onBecameActive: ((GroupedRulerController) -> Void)?
var onDragStarted: ((GroupedRulerController) -> Void)?
var onDragged: ((GroupedRulerController) -> Void)?
var onDragFinished: ((GroupedRulerController) -> Void)?
var onStateChanged: ((GroupedRulerController) -> Void)?

private var keyListener: Any?
Expand Down Expand Up @@ -1319,6 +1322,11 @@ final class GroupedRulerController: NSWindowController, NSWindowDelegate, Notifi
notifyStateChanged()
}

func move(to frame: NSRect) {
groupedWindow.setFrame(frame, display: false)
captureStateFromWindow()
}

func resetPosition() {
state.settings.zeroCorner = Prefs.defaultZeroCorner
state.layout = RulerLayoutState.defaults(
Expand Down Expand Up @@ -1489,6 +1497,7 @@ final class GroupedRulerController: NSWindowController, NSWindowDelegate, Notifi
)
)
captureStateFromWindow()
onDragged?(self)
mouseInteraction.windowDidMove(isLeftMouseButtonPressed: isLeftMouseButtonPressed())
}

Expand All @@ -1511,6 +1520,7 @@ final class GroupedRulerController: NSWindowController, NSWindowDelegate, Notifi

override func mouseDown(with event: NSEvent) {
mouseInteraction.mouseDown(with: event)
onDragStarted?(self)
}

override func mouseUp(with event: NSEvent) {
Expand All @@ -1521,6 +1531,7 @@ final class GroupedRulerController: NSWindowController, NSWindowDelegate, Notifi
if mouseInteraction.finishMouseDrag(with: event) {
syncRulerWindowFrames(persistAutosave: true)
captureStateFromWindow()
onDragFinished?(self)
}
}

Expand Down Expand Up @@ -1649,11 +1660,18 @@ extension GroupedRulerController {
final class RulerManager {
typealias ControllerFactory = (RulerInstanceState) -> GroupedRulerController

private struct GroupedDragState {
let draggedRulerID: UUID
let framesByRulerID: [UUID: NSRect]
}

private let controllerFactory: ControllerFactory
private(set) var controllers: [GroupedRulerController] = []
private(set) var activeRulerID: UUID?
var onActiveControllerChanged: ((GroupedRulerController?) -> Void)?
var onStateChanged: ((RulerManager) -> Void)?
private var groupedDragState: GroupedDragState?
private var isApplyingGroupedDrag = false

init(
initialStates: [RulerInstanceState] = [],
Expand Down Expand Up @@ -1770,6 +1788,59 @@ final class RulerManager {
notifyStateChanged()
}

func beginGroupedDrag(from controller: GroupedRulerController) {
guard prefs.groupRulers,
controllers.contains(where: { $0 === controller }) else {
groupedDragState = nil
return
}

groupedDragState = GroupedDragState(
draggedRulerID: controller.state.id,
framesByRulerID: Dictionary(
uniqueKeysWithValues: controllers
.filter(\.isVisible)
.map { ($0.state.id, $0.groupedWindow.frame) }
)
)
}

func syncGroupedDrag(from controller: GroupedRulerController) {
guard prefs.groupRulers,
!isApplyingGroupedDrag,
let groupedDragState = groupedDragState,
groupedDragState.draggedRulerID == controller.state.id,
let originalDraggedFrame = groupedDragState.framesByRulerID[controller.state.id] else {
return
}

let offset = NSSize(
width: controller.groupedWindow.frame.minX - originalDraggedFrame.minX,
height: controller.groupedWindow.frame.minY - originalDraggedFrame.minY
)
guard offset.width != 0 || offset.height != 0 else { return }

isApplyingGroupedDrag = true
defer {
isApplyingGroupedDrag = false
}

for otherController in controllers where otherController !== controller && otherController.isVisible {
guard var frame = groupedDragState.framesByRulerID[otherController.state.id] else { continue }

frame.origin.x += offset.width
frame.origin.y += offset.height
otherController.move(to: frame)
}

notifyStateChanged()
}

func finishGroupedDrag(from controller: GroupedRulerController) {
syncGroupedDrag(from: controller)
groupedDragState = nil
}

func controller(containing window: NSWindow?) -> GroupedRulerController? {
guard let window = window else { return nil }

Expand All @@ -1785,6 +1856,18 @@ final class RulerManager {
guard let controller = controller else { return }
self?.markActive(controller)
}
controller.onDragStarted = { [weak self, weak controller] _ in
guard let controller = controller else { return }
self?.beginGroupedDrag(from: controller)
}
controller.onDragged = { [weak self, weak controller] _ in
guard let controller = controller else { return }
self?.syncGroupedDrag(from: controller)
}
controller.onDragFinished = { [weak self, weak controller] _ in
guard let controller = controller else { return }
self?.finishGroupedDrag(from: controller)
}
controller.onStateChanged = { [weak self, weak controller] _ in
guard let controller = controller,
self?.activeRulerID == controller.state.id else { return }
Expand Down
8 changes: 4 additions & 4 deletions Free Ruler/de.lproj/MainMenu.strings
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,8 @@
/* Class = "NSMenuItem"; title = "Redo"; ObjectID = "6dh-zS-Vam"; */
"6dh-zS-Vam.title" = "Wiederholen";

/* Class = "NSMenuItem"; title = "Reset Rulers"; ObjectID = "6ph-5N-O9R"; */
"6ph-5N-O9R.title" = "Lineale zurücksetzen";
/* Class = "NSMenuItem"; title = "Reset Ruler Position"; ObjectID = "6ph-5N-O9R"; */
"6ph-5N-O9R.title" = "Linealposition zurücksetzen";

/* Class = "NSMenuItem"; title = "Group Rulers"; ObjectID = "7Ga-Fb-LLc"; */
"7Ga-Fb-LLc.title" = "Lineale gruppieren";
Expand Down Expand Up @@ -116,8 +116,8 @@
/* Class = "NSMenu"; title = "Services"; ObjectID = "hz9-B4-Xy5"; */
"hz9-B4-Xy5.title" = "Dienste";

/* Class = "NSMenuItem"; title = "Align Rulers at Mouse Location"; ObjectID = "iKV-uW-hwy"; */
"iKV-uW-hwy.title" = "Lineale an Zeigerposition ausrichten";
/* Class = "NSMenuItem"; title = "Align Ruler at Mouse Location"; ObjectID = "iKV-uW-hwy"; */
"iKV-uW-hwy.title" = "Lineal an Zeigerposition ausrichten";

/* Class = "NSMenuItem"; title = "Delete"; ObjectID = "pa3-QI-u2k"; */
"pa3-QI-u2k.title" = "Löschen";
Expand Down
8 changes: 4 additions & 4 deletions Free Ruler/es.lproj/MainMenu.strings
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,8 @@
/* Class = "NSMenuItem"; title = "Redo"; ObjectID = "6dh-zS-Vam"; */
"6dh-zS-Vam.title" = "Rehacer";

/* Class = "NSMenuItem"; title = "Reset Rulers"; ObjectID = "6ph-5N-O9R"; */
"6ph-5N-O9R.title" = "Restablecer reglas";
/* Class = "NSMenuItem"; title = "Reset Ruler Position"; ObjectID = "6ph-5N-O9R"; */
"6ph-5N-O9R.title" = "Restablecer posición de la regla";

/* Class = "NSMenuItem"; title = "Group Rulers"; ObjectID = "7Ga-Fb-LLc"; */
"7Ga-Fb-LLc.title" = "Agrupar reglas";
Expand Down Expand Up @@ -122,8 +122,8 @@
/* Class = "NSMenuItem"; title = "Unit"; ObjectID = "iDP-2z-irv"; */
"iDP-2z-irv.title" = "Unidad";

/* Class = "NSMenuItem"; title = "Align Rulers at Mouse Location"; ObjectID = "iKV-uW-hwy"; */
"iKV-uW-hwy.title" = "Alinear reglas con el ratón";
/* Class = "NSMenuItem"; title = "Align Ruler at Mouse Location"; ObjectID = "iKV-uW-hwy"; */
"iKV-uW-hwy.title" = "Alinear regla con el ratón";

/* Class = "NSMenuItem"; title = "Inches"; ObjectID = "lt1-Hj-2TR"; */
"lt1-Hj-2TR.title" = "Pulgadas";
Expand Down
8 changes: 4 additions & 4 deletions Free Ruler/fi.lproj/MainMenu.strings
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,8 @@
/* Class = "NSMenuItem"; title = "Redo"; ObjectID = "6dh-zS-Vam"; */
"6dh-zS-Vam.title" = "Tee sittenkin";

/* Class = "NSMenuItem"; title = "Reset Rulers"; ObjectID = "6ph-5N-O9R"; */
"6ph-5N-O9R.title" = "Nollaa viivaimet";
/* Class = "NSMenuItem"; title = "Reset Ruler Position"; ObjectID = "6ph-5N-O9R"; */
"6ph-5N-O9R.title" = "Nollaa viivaimen sijainti";

/* Class = "NSMenuItem"; title = "Group Rulers"; ObjectID = "7Ga-Fb-LLc"; */
"7Ga-Fb-LLc.title" = "Ryhmitä viivaimet";
Expand Down Expand Up @@ -116,8 +116,8 @@
/* Class = "NSMenu"; title = "Services"; ObjectID = "hz9-B4-Xy5"; */
"hz9-B4-Xy5.title" = "Palvelut";

/* Class = "NSMenuItem"; title = "Align Rulers at Mouse Location"; ObjectID = "iKV-uW-hwy"; */
"iKV-uW-hwy.title" = "Kohdista viivaimet hiiren sijaintiin";
/* Class = "NSMenuItem"; title = "Align Ruler at Mouse Location"; ObjectID = "iKV-uW-hwy"; */
"iKV-uW-hwy.title" = "Kohdista viivain hiiren sijaintiin";

/* Class = "NSMenuItem"; title = "Delete"; ObjectID = "pa3-QI-u2k"; */
"pa3-QI-u2k.title" = "Poista";
Expand Down
6 changes: 3 additions & 3 deletions Free Ruler/ja.lproj/MainMenu.strings
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,8 @@
/* Class = "NSMenuItem"; title = "Redo"; ObjectID = "6dh-zS-Vam"; */
"6dh-zS-Vam.title" = "やり直し";

/* Class = "NSMenuItem"; title = "Reset Rulers"; ObjectID = "6ph-5N-O9R"; */
"6ph-5N-O9R.title" = "定規をリセット";
/* Class = "NSMenuItem"; title = "Reset Ruler Position"; ObjectID = "6ph-5N-O9R"; */
"6ph-5N-O9R.title" = "定規の位置をリセット";

/* Class = "NSMenuItem"; title = "Group Rulers"; ObjectID = "7Ga-Fb-LLc"; */
"7Ga-Fb-LLc.title" = "定規をグループ化";
Expand Down Expand Up @@ -122,7 +122,7 @@
/* Class = "NSMenuItem"; title = "Unit"; ObjectID = "iDP-2z-irv"; */
"iDP-2z-irv.title" = "単位";

/* Class = "NSMenuItem"; title = "Align Rulers at Mouse Location"; ObjectID = "iKV-uW-hwy"; */
/* Class = "NSMenuItem"; title = "Align Ruler at Mouse Location"; ObjectID = "iKV-uW-hwy"; */
"iKV-uW-hwy.title" = "マウスの位置に定規を移動";

/* Class = "NSMenuItem"; title = "Inches"; ObjectID = "lt1-Hj-2TR"; */
Expand Down
6 changes: 3 additions & 3 deletions Free Ruler/zh-hans.lproj/MainMenu.strings
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,8 @@
/* Class = "NSMenuItem"; title = "Redo"; ObjectID = "6dh-zS-Vam"; */
"6dh-zS-Vam.title" = "重做";

/* Class = "NSMenuItem"; title = "Reset Rulers"; ObjectID = "6ph-5N-O9R"; */
"6ph-5N-O9R.title" = "重置尺子";
/* Class = "NSMenuItem"; title = "Reset Ruler Position"; ObjectID = "6ph-5N-O9R"; */
"6ph-5N-O9R.title" = "重置尺子位置";

/* Class = "NSMenuItem"; title = "Group Rulers"; ObjectID = "7Ga-Fb-LLc"; */
"7Ga-Fb-LLc.title" = "组合尺子";
Expand Down Expand Up @@ -116,7 +116,7 @@
/* Class = "NSMenu"; title = "Services"; ObjectID = "hz9-B4-Xy5"; */
"hz9-B4-Xy5.title" = "服务";

/* Class = "NSMenuItem"; title = "Align Rulers at Mouse Location"; ObjectID = "iKV-uW-hwy"; */
/* Class = "NSMenuItem"; title = "Align Ruler at Mouse Location"; ObjectID = "iKV-uW-hwy"; */
"iKV-uW-hwy.title" = "将尺子与鼠标位置对齐";

/* Class = "NSMenuItem"; title = "Delete"; ObjectID = "pa3-QI-u2k"; */
Expand Down
Loading