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
5 changes: 5 additions & 0 deletions Sources/TinyHand/Log.swift
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,11 @@ enum Log {
guard let data = line.data(using: .utf8) else {
return
}
// Keep the log small: once it passes 1 MB, start a fresh one.
if let size = (try? FileManager.default.attributesOfItem(atPath: url.path))?[.size] as? Int, size > 1_000_000 {
try? data.write(to: url)
return
}
if let handle = try? FileHandle(forWritingTo: url) {
handle.seekToEndOfFile()
handle.write(data)
Expand Down
18 changes: 17 additions & 1 deletion Sources/TinyHand/OverlayController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,9 @@ final class OverlayController {
private static let busyInterval: TimeInterval = 1.0 / 120.0
private static let idleInterval: TimeInterval = 1.0 / 20.0
private static let idleAfter: TimeInterval = 0.5
/// After this long without the mouse moving, stop the timer altogether. The idle monitors
/// wake it the moment the mouse moves, a button is pressed or a modifier changes.
private static let sleepAfter: TimeInterval = 3
private static let menuScanFast: TimeInterval = 0.05
private static let menuScanSlow: TimeInterval = 0.25
private var timerInterval: TimeInterval = 0
Expand Down Expand Up @@ -639,6 +642,9 @@ final class OverlayController {
let t = Timer(timeInterval: interval, repeats: true) { [weak self] _ in
self?.tick()
}
if interval == OverlayController.idleInterval {
t.tolerance = interval * 0.5 // let macOS batch idle wakeups
}
RunLoop.main.add(t, forMode: .common)
timer = t
timerInterval = interval
Expand All @@ -663,6 +669,13 @@ final class OverlayController {
if timerInterval == OverlayController.idleInterval {
if busy {
wake()
return
}
let asleep = Date().timeIntervalSince(stillSince) > OverlayController.sleepAfter
if asleep && !toolbar.revealed && downPoint == nil && !armView.isSettling {
timer?.invalidate()
timer = nil
timerInterval = 0
}
return
}
Expand Down Expand Up @@ -739,7 +752,10 @@ final class OverlayController {
let local = CGPoint(x: mouse.x - screen.frame.origin.x, y: mouse.y - screen.frame.origin.y)
armView.aim(cursor: local)
guard downPoint != nil else {
let busy = overDock || (!normalCursor && urgent) || CursorHider.isSettling
// Resting over the Dock kept the full-speed timer running for as long as the mouse sat
// there. Give up after a few still seconds; moving again wakes everything.
let lingering = Date().timeIntervalSince(stillSince) > OverlayController.sleepAfter
let busy = (!lingering && (overDock || (!normalCursor && urgent))) || CursorHider.isSettling
updatePace(busy: busy)
return
}
Expand Down