Initial commit
This commit is contained in:
@@ -0,0 +1,127 @@
|
||||
// StatusMenuController.swift
|
||||
// GreenshotMac
|
||||
//
|
||||
// The menu bar item, equivalent to Greenshot's tray icon and context menu.
|
||||
|
||||
import AppKit
|
||||
|
||||
@MainActor
|
||||
final class StatusMenuController: NSObject, NSMenuDelegate {
|
||||
|
||||
private let statusItem = NSStatusBar.system.statusItem(withLength: NSStatusItem.variableLength)
|
||||
private var preferencesController: PreferencesWindowController?
|
||||
|
||||
override init() {
|
||||
super.init()
|
||||
if let button = statusItem.button {
|
||||
button.image = NSImage(systemSymbolName: "camera.viewfinder", accessibilityDescription: "GreenshotMac")
|
||||
button.image?.isTemplate = true
|
||||
button.toolTip = "GreenshotMac"
|
||||
}
|
||||
statusItem.menu = buildMenu()
|
||||
}
|
||||
|
||||
private func buildMenu() -> NSMenu {
|
||||
let menu = NSMenu()
|
||||
menu.delegate = self
|
||||
|
||||
menu.addItem(item(title: "Capture region",
|
||||
action: #selector(captureRegion),
|
||||
hotkey: HotkeyBindings.shared.spec(for: .region)))
|
||||
menu.addItem(item(title: "Capture window",
|
||||
action: #selector(captureWindow),
|
||||
hotkey: HotkeyBindings.shared.spec(for: .window)))
|
||||
menu.addItem(item(title: "Capture full screen",
|
||||
action: #selector(captureFullscreen),
|
||||
hotkey: HotkeyBindings.shared.spec(for: .fullscreen)))
|
||||
menu.addItem(item(title: "Capture last region",
|
||||
action: #selector(captureLastRegion),
|
||||
hotkey: HotkeyBindings.shared.spec(for: .lastRegion)))
|
||||
|
||||
menu.addItem(.separator())
|
||||
menu.addItem(item(title: "Open image from file…", action: #selector(openImageFile), hotkey: nil))
|
||||
menu.addItem(item(title: "Open last screenshot in Finder", action: #selector(revealLast), hotkey: nil))
|
||||
|
||||
menu.addItem(.separator())
|
||||
let destinationItem = NSMenuItem(title: "Default destination", action: nil, keyEquivalent: "")
|
||||
destinationItem.submenu = destinationMenu()
|
||||
menu.addItem(destinationItem)
|
||||
menu.addItem(item(title: "Preferences…", action: #selector(showPreferences), hotkey: nil))
|
||||
|
||||
menu.addItem(.separator())
|
||||
menu.addItem(item(title: "About GreenshotMac", action: #selector(showAbout), hotkey: nil))
|
||||
menu.addItem(item(title: "Quit GreenshotMac", action: #selector(quit), hotkey: nil))
|
||||
return menu
|
||||
}
|
||||
|
||||
private func destinationMenu() -> NSMenu {
|
||||
let menu = NSMenu()
|
||||
for destination in DestinationID.allCases {
|
||||
let menuItem = NSMenuItem(title: destination.title,
|
||||
action: #selector(selectDestination(_:)),
|
||||
keyEquivalent: "")
|
||||
menuItem.target = self
|
||||
menuItem.representedObject = destination.rawValue
|
||||
menuItem.state = Configuration.shared.defaultDestination == destination ? .on : .off
|
||||
menu.addItem(menuItem)
|
||||
}
|
||||
return menu
|
||||
}
|
||||
|
||||
private func item(title: String, action: Selector, hotkey: HotkeySpec?) -> NSMenuItem {
|
||||
let menuItem = NSMenuItem(title: title, action: action, keyEquivalent: "")
|
||||
menuItem.target = self
|
||||
if let hotkey, !hotkey.isEmpty {
|
||||
menuItem.toolTip = HotkeyManager.description(of: hotkey)
|
||||
}
|
||||
return menuItem
|
||||
}
|
||||
|
||||
func menuWillOpen(_ menu: NSMenu) {
|
||||
for menuItem in menu.items where menuItem.title == "Default destination" {
|
||||
menuItem.submenu = destinationMenu()
|
||||
}
|
||||
if let revealItem = menu.items.first(where: { $0.title == "Open last screenshot in Finder" }) {
|
||||
revealItem.isEnabled = Notifier.mostRecentSavedURL != nil
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - Actions
|
||||
|
||||
@objc private func captureRegion() { CaptureCoordinator.shared.captureRegion() }
|
||||
@objc private func captureWindow() { CaptureCoordinator.shared.captureWindow() }
|
||||
@objc private func captureFullscreen() { CaptureCoordinator.shared.captureFullscreen() }
|
||||
@objc private func captureLastRegion() { CaptureCoordinator.shared.captureLastRegion() }
|
||||
@objc private func openImageFile() { CaptureCoordinator.shared.openImageFile() }
|
||||
@objc private func revealLast() { Notifier.revealMostRecent() }
|
||||
|
||||
@objc private func selectDestination(_ sender: NSMenuItem) {
|
||||
guard let raw = sender.representedObject as? String,
|
||||
let destination = DestinationID(rawValue: raw) else { return }
|
||||
Configuration.shared.defaultDestination = destination
|
||||
}
|
||||
|
||||
@objc private func showPreferences() {
|
||||
if preferencesController == nil {
|
||||
preferencesController = PreferencesWindowController()
|
||||
}
|
||||
preferencesController?.showWindow(nil)
|
||||
preferencesController?.window?.makeKeyAndOrderFront(nil)
|
||||
NSApp.activate(ignoringOtherApps: true)
|
||||
}
|
||||
|
||||
@objc private func showAbout() {
|
||||
NSApp.activate(ignoringOtherApps: true)
|
||||
NSApp.orderFrontStandardAboutPanel(options: [
|
||||
.applicationName: "GreenshotMac",
|
||||
.credits: NSAttributedString(
|
||||
string: "A native macOS screenshot tool modelled on Greenshot for Windows.\n"
|
||||
+ "Licensed under the GNU General Public License v3.",
|
||||
attributes: [.font: NSFont.systemFont(ofSize: 11)])
|
||||
])
|
||||
}
|
||||
|
||||
@objc private func quit() {
|
||||
NSApp.terminate(nil)
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user