mirror of
https://github.com/MonitorControl/MonitorControl.git
synced 2026-05-16 06:05:52 -06:00
refactor
This commit is contained in:
parent
53e168c319
commit
79bd48166e
2 changed files with 223 additions and 287 deletions
|
|
@ -7,13 +7,13 @@
|
|||
objects = {
|
||||
|
||||
/* Begin PBXBuildFile section */
|
||||
2E3C2647A29DDCAA1F2D4E29 /* Pods_MonitorControl.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 65A9B356B917FAB6583F09A6 /* Pods_MonitorControl.framework */; };
|
||||
56754EAF1D9A4016007BCDC5 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 56754EAE1D9A4016007BCDC5 /* AppDelegate.swift */; };
|
||||
56754EB11D9A4016007BCDC5 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 56754EB01D9A4016007BCDC5 /* Assets.xcassets */; };
|
||||
56754EB41D9A4016007BCDC5 /* MainMenu.xib in Resources */ = {isa = PBXBuildFile; fileRef = 56754EB21D9A4016007BCDC5 /* MainMenu.xib */; };
|
||||
6C33119021C58BF600971151 /* README.md in Resources */ = {isa = PBXBuildFile; fileRef = 6C33118921C58BF500971151 /* README.md */; };
|
||||
6C33119221C58BF600971151 /* ddcctl.sh in Resources */ = {isa = PBXBuildFile; fileRef = 6C33118C21C58BF500971151 /* ddcctl.sh */; };
|
||||
6C33119521C58BF600971151 /* DDC.c in Sources */ = {isa = PBXBuildFile; fileRef = 6C33118F21C58BF600971151 /* DDC.c */; };
|
||||
9A19D3B73485870616B6D4E0 /* Pods_MonitorControl.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 398F482D5C8816B29F16AAEB /* Pods_MonitorControl.framework */; };
|
||||
F03A8DF21FFBAA6F0034DC27 /* Display.swift in Sources */ = {isa = PBXBuildFile; fileRef = F03A8DF11FFBAA6F0034DC27 /* Display.swift */; };
|
||||
F0445D3820023E710025AE82 /* MainPrefsViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = F0445D3720023E710025AE82 /* MainPrefsViewController.swift */; };
|
||||
F0445D3D200254FA0025AE82 /* KeysPrefsViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = F0445D3B200254FA0025AE82 /* KeysPrefsViewController.swift */; };
|
||||
|
|
@ -44,13 +44,13 @@
|
|||
|
||||
/* Begin PBXFileReference section */
|
||||
31E16D90527EBD3F8A12BE0B /* Pods-MonitorControl.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-MonitorControl.release.xcconfig"; path = "Pods/Target Support Files/Pods-MonitorControl/Pods-MonitorControl.release.xcconfig"; sourceTree = "<group>"; };
|
||||
398F482D5C8816B29F16AAEB /* Pods_MonitorControl.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_MonitorControl.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
42B61ABC1D7907131330228A /* Pods-MonitorControl.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-MonitorControl.debug.xcconfig"; path = "Pods/Target Support Files/Pods-MonitorControl/Pods-MonitorControl.debug.xcconfig"; sourceTree = "<group>"; };
|
||||
56754EAB1D9A4016007BCDC5 /* MonitorControl.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = MonitorControl.app; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
56754EAE1D9A4016007BCDC5 /* AppDelegate.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; lineEnding = 0; path = AppDelegate.swift; sourceTree = "<group>"; };
|
||||
56754EB01D9A4016007BCDC5 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = "<group>"; };
|
||||
56754EB31D9A4016007BCDC5 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = Base.lproj/MainMenu.xib; sourceTree = "<group>"; };
|
||||
56754EB51D9A4016007BCDC5 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
|
||||
65A9B356B917FAB6583F09A6 /* Pods_MonitorControl.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_MonitorControl.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
6C33118921C58BF500971151 /* README.md */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = net.daringfireball.markdown; path = README.md; sourceTree = "<group>"; };
|
||||
6C33118B21C58BF500971151 /* DDC.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DDC.h; sourceTree = "<group>"; };
|
||||
6C33118C21C58BF500971151 /* ddcctl.sh */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.script.sh; path = ddcctl.sh; sourceTree = "<group>"; };
|
||||
|
|
@ -77,17 +77,6 @@
|
|||
F091C9C31F6EB8720096FD65 /* fr */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.strings; lineEnding = 0; name = fr; path = fr.lproj/Localizable.strings; sourceTree = "<group>"; };
|
||||
F091C9C41F6EBA5A0096FD65 /* Bridging-Header.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "Bridging-Header.h"; sourceTree = "<group>"; };
|
||||
F0A987D61F77B290009B603D /* OSD.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; path = OSD.framework; sourceTree = "<group>"; };
|
||||
F0A987DA1F77B404009B603D /* en */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = en; path = en.lproj/MainMenu.strings; sourceTree = "<group>"; };
|
||||
F0A987DC1F77B404009B603D /* en */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = en; path = en.lproj/Localizable.strings; sourceTree = "<group>"; };
|
||||
F0A987DD1F77B404009B603D /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = "<group>"; };
|
||||
F0A987DF1F77B404009B603D /* SliderHandler.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SliderHandler.swift; sourceTree = "<group>"; };
|
||||
F0A987E11F77B404009B603D /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = Base.lproj/MainMenu.xib; sourceTree = "<group>"; };
|
||||
F0A987E21F77B404009B603D /* Utils.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Utils.swift; sourceTree = "<group>"; };
|
||||
F0A987E31F77B404009B603D /* fr */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = fr; path = fr.lproj/MainMenu.strings; sourceTree = "<group>"; };
|
||||
F0A987E41F77B404009B603D /* fr */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = fr; path = fr.lproj/Localizable.strings; sourceTree = "<group>"; };
|
||||
F0A987E51F77B404009B603D /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = "<group>"; };
|
||||
F0A987E61F77B404009B603D /* Bridging-Header.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "Bridging-Header.h"; sourceTree = "<group>"; };
|
||||
F0A987E71F77B404009B603D /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
|
||||
/* End PBXFileReference section */
|
||||
|
||||
/* Begin PBXFrameworksBuildPhase section */
|
||||
|
|
@ -96,7 +85,7 @@
|
|||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
F0A987E81F77B40E009B603D /* OSD.framework in Frameworks */,
|
||||
9A19D3B73485870616B6D4E0 /* Pods_MonitorControl.framework in Frameworks */,
|
||||
2E3C2647A29DDCAA1F2D4E29 /* Pods_MonitorControl.framework in Frameworks */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
|
|
@ -131,8 +120,8 @@
|
|||
55359E321E2737EC002671BC /* ddcctl */,
|
||||
F06792E8200A73460066C438 /* MonitorControlHelper */,
|
||||
56754EAC1D9A4016007BCDC5 /* Products */,
|
||||
F0A987D71F77B404009B603D /* Frameworks */,
|
||||
EFFC2F3E35BEC9ACFA754137 /* Pods */,
|
||||
8ABFD04A9742F18299723076 /* Frameworks */,
|
||||
);
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
|
|
@ -162,6 +151,14 @@
|
|||
path = MonitorControl;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
8ABFD04A9742F18299723076 /* Frameworks */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
65A9B356B917FAB6583F09A6 /* Pods_MonitorControl.framework */,
|
||||
);
|
||||
name = Frameworks;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
EFFC2F3E35BEC9ACFA754137 /* Pods */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
|
|
@ -201,39 +198,6 @@
|
|||
path = Objects;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
F0A987D71F77B404009B603D /* Frameworks */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
F0A987D81F77B404009B603D /* MonitorControl */,
|
||||
398F482D5C8816B29F16AAEB /* Pods_MonitorControl.framework */,
|
||||
);
|
||||
name = Frameworks;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
F0A987D81F77B404009B603D /* MonitorControl */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
F0A987D91F77B404009B603D /* MainMenu.strings */,
|
||||
F0A987DB1F77B404009B603D /* Localizable.strings */,
|
||||
F0A987DD1F77B404009B603D /* Assets.xcassets */,
|
||||
F0A987DE1F77B404009B603D /* Objects */,
|
||||
F0A987E01F77B404009B603D /* MainMenu.xib */,
|
||||
F0A987E21F77B404009B603D /* Utils.swift */,
|
||||
F0A987E51F77B404009B603D /* AppDelegate.swift */,
|
||||
F0A987E61F77B404009B603D /* Bridging-Header.h */,
|
||||
F0A987E71F77B404009B603D /* Info.plist */,
|
||||
);
|
||||
path = MonitorControl;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
F0A987DE1F77B404009B603D /* Objects */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
F0A987DF1F77B404009B603D /* SliderHandler.swift */,
|
||||
);
|
||||
path = Objects;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
/* End PBXGroup section */
|
||||
|
||||
/* Begin PBXNativeTarget section */
|
||||
|
|
@ -439,32 +403,6 @@
|
|||
name = Localizable.strings;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
F0A987D91F77B404009B603D /* MainMenu.strings */ = {
|
||||
isa = PBXVariantGroup;
|
||||
children = (
|
||||
F0A987DA1F77B404009B603D /* en */,
|
||||
F0A987E31F77B404009B603D /* fr */,
|
||||
);
|
||||
name = MainMenu.strings;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
F0A987DB1F77B404009B603D /* Localizable.strings */ = {
|
||||
isa = PBXVariantGroup;
|
||||
children = (
|
||||
F0A987DC1F77B404009B603D /* en */,
|
||||
F0A987E41F77B404009B603D /* fr */,
|
||||
);
|
||||
name = Localizable.strings;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
F0A987E01F77B404009B603D /* MainMenu.xib */ = {
|
||||
isa = PBXVariantGroup;
|
||||
children = (
|
||||
F0A987E11F77B404009B603D /* Base */,
|
||||
);
|
||||
name = MainMenu.xib;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
/* End PBXVariantGroup section */
|
||||
|
||||
/* Begin XCBuildConfiguration section */
|
||||
|
|
|
|||
|
|
@ -16,133 +16,129 @@ var app: AppDelegate! = nil
|
|||
let prefs = UserDefaults.standard
|
||||
|
||||
@NSApplicationMain
|
||||
class AppDelegate: NSObject, NSApplicationDelegate, MediaKeyTapDelegate {
|
||||
|
||||
class AppDelegate: NSObject, NSApplicationDelegate {
|
||||
|
||||
@IBOutlet weak var statusMenu: NSMenu!
|
||||
@IBOutlet weak var window: NSWindow!
|
||||
|
||||
|
||||
let statusItem = NSStatusBar.system.statusItem(withLength: NSStatusItem.variableLength)
|
||||
|
||||
|
||||
var monitorItems: [NSMenuItem] = []
|
||||
var displays: [Display] = []
|
||||
|
||||
let step = 100/16
|
||||
|
||||
var mediaKeyTap: MediaKeyTap?
|
||||
var prefsController: NSWindowController?
|
||||
|
||||
var keysListenedFor: [MediaKey] = [.brightnessUp, .brightnessDown, .mute, .volumeUp, .volumeDown]
|
||||
|
||||
|
||||
let step = 100/16
|
||||
|
||||
var mediaKeyTap: MediaKeyTap?
|
||||
var prefsController: NSWindowController?
|
||||
|
||||
var keysListenedFor: [MediaKey] = [.brightnessUp, .brightnessDown, .mute, .volumeUp, .volumeDown]
|
||||
|
||||
func applicationDidFinishLaunching(_ aNotification: Notification) {
|
||||
app = self
|
||||
|
||||
let listenFor = prefs.integer(forKey: Utils.PrefKeys.listenFor.rawValue)
|
||||
if listenFor == Utils.ListenForKeys.brightnessOnlyKeys.rawValue {
|
||||
keysListenedFor.removeSubrange(2...4)
|
||||
} else if listenFor == Utils.ListenForKeys.volumeOnlyKeys.rawValue {
|
||||
keysListenedFor.removeSubrange(0...1)
|
||||
}
|
||||
|
||||
mediaKeyTap = MediaKeyTap.init(delegate: self, for: keysListenedFor, observeBuiltIn: false)
|
||||
let storyboard: NSStoryboard = NSStoryboard.init(name: "Main", bundle: Bundle.main)
|
||||
let views = [
|
||||
storyboard.instantiateController(withIdentifier: "MainPrefsVC"),
|
||||
storyboard.instantiateController(withIdentifier: "KeysPrefsVC"),
|
||||
storyboard.instantiateController(withIdentifier: "DisplayPrefsVC")
|
||||
]
|
||||
prefsController = MASPreferencesWindowController(viewControllers: views, title: NSLocalizedString("Preferences", comment: "Shown in Preferences window"))
|
||||
|
||||
NotificationCenter.default.addObserver(self, selector: #selector(handleListenForChanged), name: NSNotification.Name.init(Utils.PrefKeys.listenFor.rawValue), object: nil)
|
||||
NotificationCenter.default.addObserver(self, selector: #selector(handleShowContrastChanged), name: NSNotification.Name.init(Utils.PrefKeys.showContrast.rawValue), object: nil)
|
||||
|
||||
statusItem.image = NSImage.init(named: "status")
|
||||
|
||||
let listenFor = prefs.integer(forKey: Utils.PrefKeys.listenFor.rawValue)
|
||||
if listenFor == Utils.ListenForKeys.brightnessOnlyKeys.rawValue {
|
||||
keysListenedFor.removeSubrange(2...4)
|
||||
} else if listenFor == Utils.ListenForKeys.volumeOnlyKeys.rawValue {
|
||||
keysListenedFor.removeSubrange(0...1)
|
||||
}
|
||||
|
||||
mediaKeyTap = MediaKeyTap.init(delegate: self, for: keysListenedFor, observeBuiltIn: false)
|
||||
let storyboard: NSStoryboard = NSStoryboard.init(name: "Main", bundle: Bundle.main)
|
||||
let views = [
|
||||
storyboard.instantiateController(withIdentifier: "MainPrefsVC"),
|
||||
storyboard.instantiateController(withIdentifier: "KeysPrefsVC"),
|
||||
storyboard.instantiateController(withIdentifier: "DisplayPrefsVC")
|
||||
]
|
||||
prefsController = MASPreferencesWindowController(viewControllers: views, title: NSLocalizedString("Preferences", comment: "Shown in Preferences window"))
|
||||
|
||||
NotificationCenter.default.addObserver(self, selector: #selector(handleListenForChanged), name: NSNotification.Name.init(Utils.PrefKeys.listenFor.rawValue), object: nil)
|
||||
NotificationCenter.default.addObserver(self, selector: #selector(handleShowContrastChanged), name: NSNotification.Name.init(Utils.PrefKeys.showContrast.rawValue), object: nil)
|
||||
|
||||
statusItem.image = NSImage.init(named: "status")
|
||||
statusItem.menu = statusMenu
|
||||
|
||||
setDefaultPrefs()
|
||||
|
||||
|
||||
setDefaultPrefs()
|
||||
|
||||
Utils.acquirePrivileges()
|
||||
|
||||
|
||||
CGDisplayRegisterReconfigurationCallback({_, _, _ in app.updateDisplays()}, nil)
|
||||
updateDisplays()
|
||||
|
||||
mediaKeyTap?.start()
|
||||
|
||||
mediaKeyTap?.start()
|
||||
}
|
||||
|
||||
func applicationWillTerminate(_ aNotification: Notification) {
|
||||
}
|
||||
|
||||
@IBAction func quitClicked(_ sender: AnyObject) {
|
||||
NSApplication.shared.terminate(self)
|
||||
}
|
||||
|
||||
@IBAction func prefsClicked(_ sender: AnyObject) {
|
||||
if let prefsController = prefsController {
|
||||
prefsController.showWindow(sender)
|
||||
NSApp.activate(ignoringOtherApps: true)
|
||||
prefsController.window?.makeKeyAndOrderFront(sender)
|
||||
}
|
||||
}
|
||||
|
||||
/// Set the default prefs of the app
|
||||
func setDefaultPrefs() {
|
||||
let prefs = UserDefaults.standard
|
||||
if !prefs.bool(forKey: Utils.PrefKeys.appAlreadyLaunched.rawValue) {
|
||||
prefs.set(true, forKey: Utils.PrefKeys.appAlreadyLaunched.rawValue)
|
||||
|
||||
prefs.set(false, forKey: Utils.PrefKeys.startAtLogin.rawValue)
|
||||
|
||||
prefs.set(false, forKey: Utils.PrefKeys.showContrast.rawValue)
|
||||
prefs.set(false, forKey: Utils.PrefKeys.lowerContrast.rawValue)
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - Menu
|
||||
|
||||
func clearDisplays() {
|
||||
if statusMenu.items.count > 2 {
|
||||
var items: [NSMenuItem] = []
|
||||
for i in 0..<statusMenu.items.count - 2 {
|
||||
items.append(statusMenu.items[i])
|
||||
}
|
||||
|
||||
for item in items {
|
||||
statusMenu.removeItem(item)
|
||||
}
|
||||
}
|
||||
|
||||
monitorItems = []
|
||||
displays = []
|
||||
}
|
||||
|
||||
|
||||
@IBAction func quitClicked(_ sender: AnyObject) {
|
||||
NSApplication.shared.terminate(self)
|
||||
}
|
||||
|
||||
@IBAction func prefsClicked(_ sender: AnyObject) {
|
||||
if let prefsController = prefsController {
|
||||
prefsController.showWindow(sender)
|
||||
NSApp.activate(ignoringOtherApps: true)
|
||||
prefsController.window?.makeKeyAndOrderFront(sender)
|
||||
}
|
||||
}
|
||||
|
||||
/// Set the default prefs of the app
|
||||
func setDefaultPrefs() {
|
||||
let prefs = UserDefaults.standard
|
||||
if !prefs.bool(forKey: Utils.PrefKeys.appAlreadyLaunched.rawValue) {
|
||||
prefs.set(true, forKey: Utils.PrefKeys.appAlreadyLaunched.rawValue)
|
||||
|
||||
prefs.set(false, forKey: Utils.PrefKeys.startAtLogin.rawValue)
|
||||
|
||||
prefs.set(false, forKey: Utils.PrefKeys.showContrast.rawValue)
|
||||
prefs.set(false, forKey: Utils.PrefKeys.lowerContrast.rawValue)
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - Menu
|
||||
func clearDisplays() {
|
||||
if statusMenu.items.count > 2 {
|
||||
var items: [NSMenuItem] = []
|
||||
for i in 0..<statusMenu.items.count - 2 {
|
||||
items.append(statusMenu.items[i])
|
||||
}
|
||||
|
||||
for item in items {
|
||||
statusMenu.removeItem(item)
|
||||
}
|
||||
}
|
||||
|
||||
monitorItems = []
|
||||
displays = []
|
||||
}
|
||||
|
||||
func updateDisplays() {
|
||||
clearDisplays()
|
||||
|
||||
var filteredScreens = NSScreen.screens.filter { screen -> Bool in
|
||||
if let id = screen.deviceDescription[NSDeviceDescriptionKey.init("NSScreenNumber")] as? CGDirectDisplayID {
|
||||
// Is Built In Screen (e.g. MBP/iMac Screen)
|
||||
if CGDisplayIsBuiltin(id) != 0 {
|
||||
return false
|
||||
}
|
||||
|
||||
// Does screen support EDID ?
|
||||
var edid = EDID()
|
||||
if !EDIDTest(id, &edid) {
|
||||
return false
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
if filteredScreens.count == 1 {
|
||||
self.addScreenToMenu(screen: filteredScreens[0], asSubMenu: false)
|
||||
} else {
|
||||
for screen in filteredScreens {
|
||||
self.addScreenToMenu(screen: screen, asSubMenu: true)
|
||||
}
|
||||
}
|
||||
|
||||
clearDisplays()
|
||||
|
||||
var filteredScreens = NSScreen.screens.filter { screen -> Bool in
|
||||
if let id = screen.deviceDescription[NSDeviceDescriptionKey.init("NSScreenNumber")] as? CGDirectDisplayID {
|
||||
// Is Built In Screen (e.g. MBP/iMac Screen)
|
||||
if CGDisplayIsBuiltin(id) != 0 {
|
||||
return false
|
||||
}
|
||||
|
||||
// Does screen support EDID ?
|
||||
var edid = EDID()
|
||||
if !EDIDTest(id, &edid) {
|
||||
return false
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
if filteredScreens.count == 1 {
|
||||
self.addScreenToMenu(screen: filteredScreens[0], asSubMenu: false)
|
||||
} else {
|
||||
for screen in filteredScreens {
|
||||
self.addScreenToMenu(screen: screen, asSubMenu: true)
|
||||
}
|
||||
}
|
||||
|
||||
if filteredScreens.count == 0 {
|
||||
// If no DDC capable display was detected
|
||||
let item = NSMenuItem()
|
||||
|
|
@ -152,103 +148,105 @@ class AppDelegate: NSObject, NSApplicationDelegate, MediaKeyTapDelegate {
|
|||
statusMenu.insertItem(item, at: 0)
|
||||
}
|
||||
}
|
||||
|
||||
/// Add a screen to the menu
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - screen: The screen to add
|
||||
/// - asSubMenu: Display in a sub menu or directly in menu
|
||||
private func addScreenToMenu(screen: NSScreen, asSubMenu: Bool) {
|
||||
if let id = screen.deviceDescription[NSDeviceDescriptionKey.init("NSScreenNumber")] as? CGDirectDisplayID {
|
||||
|
||||
var edid = EDID()
|
||||
if EDIDTest(id, &edid) {
|
||||
let name = Utils.getDisplayName(forEdid: edid)
|
||||
let serial = Utils.getDisplaySerial(forEdid: edid)
|
||||
|
||||
let display = Display.init(id, name: name, serial: serial)
|
||||
|
||||
let monitorSubMenu: NSMenu = asSubMenu ? NSMenu() : statusMenu
|
||||
let volumeSliderHandler = Utils.addSliderMenuItem(toMenu: monitorSubMenu,
|
||||
forDisplay: display,
|
||||
command: AUDIO_SPEAKER_VOLUME,
|
||||
title: NSLocalizedString("Volume", comment: "Shown in menu"))
|
||||
let brightnessSliderHandler = Utils.addSliderMenuItem(toMenu: monitorSubMenu,
|
||||
forDisplay: display,
|
||||
command: BRIGHTNESS,
|
||||
title: NSLocalizedString("Brightness", comment: "Shown in menu"))
|
||||
if prefs.bool(forKey: Utils.PrefKeys.showContrast.rawValue) {
|
||||
let contrastSliderHandler = Utils.addSliderMenuItem(toMenu: monitorSubMenu,
|
||||
forDisplay: display,
|
||||
command: CONTRAST,
|
||||
title: NSLocalizedString("Contrast", comment: "Shown in menu"))
|
||||
display.contrastSliderHandler = contrastSliderHandler
|
||||
}
|
||||
|
||||
display.volumeSliderHandler = volumeSliderHandler
|
||||
display.brightnessSliderHandler = brightnessSliderHandler
|
||||
displays.append(display)
|
||||
|
||||
let monitorMenuItem = NSMenuItem()
|
||||
monitorMenuItem.title = "\(name)"
|
||||
if asSubMenu {
|
||||
monitorMenuItem.submenu = monitorSubMenu
|
||||
}
|
||||
|
||||
monitorItems.append(monitorMenuItem)
|
||||
statusMenu.insertItem(monitorMenuItem, at: 0)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - Media Key Tap delegate
|
||||
|
||||
func handle(mediaKey: MediaKey, event: KeyEvent?) {
|
||||
guard let currentDisplay = Utils.getCurrentDisplay(from: displays) else { return }
|
||||
let allDisplays = prefs.bool(forKey: Utils.PrefKeys.allScreens.rawValue) ? displays : [currentDisplay]
|
||||
for display in allDisplays {
|
||||
if (prefs.object(forKey: "\(display.identifier)-state") as? Bool) ?? true {
|
||||
switch mediaKey {
|
||||
case .brightnessUp:
|
||||
let value = display.calcNewValue(for: BRIGHTNESS, withRel: +step)
|
||||
display.setBrightness(to: value)
|
||||
case .brightnessDown:
|
||||
let value = currentDisplay.calcNewValue(for: BRIGHTNESS, withRel: -step)
|
||||
display.setBrightness(to: value)
|
||||
case .mute:
|
||||
display.mute()
|
||||
case .volumeUp:
|
||||
let value = display.calcNewValue(for: AUDIO_SPEAKER_VOLUME, withRel: +step)
|
||||
display.setVolume(to: value)
|
||||
case .volumeDown:
|
||||
let value = display.calcNewValue(for: AUDIO_SPEAKER_VOLUME, withRel: -step)
|
||||
display.setVolume(to: value)
|
||||
default:
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// MARK: - Prefs notification
|
||||
|
||||
@objc func handleListenForChanged() {
|
||||
let listenFor = prefs.integer(forKey: Utils.PrefKeys.listenFor.rawValue)
|
||||
keysListenedFor = [.brightnessUp, .brightnessDown, .mute, .volumeUp, .volumeDown]
|
||||
if listenFor == Utils.ListenForKeys.brightnessOnlyKeys.rawValue {
|
||||
keysListenedFor.removeSubrange(2...4)
|
||||
} else if listenFor == Utils.ListenForKeys.volumeOnlyKeys.rawValue {
|
||||
keysListenedFor.removeSubrange(0...1)
|
||||
}
|
||||
|
||||
mediaKeyTap?.stop()
|
||||
mediaKeyTap = MediaKeyTap.init(delegate: self, for: keysListenedFor, observeBuiltIn: false)
|
||||
mediaKeyTap?.start()
|
||||
}
|
||||
|
||||
@objc func handleShowContrastChanged() {
|
||||
self.updateDisplays()
|
||||
}
|
||||
|
||||
|
||||
/// Add a screen to the menu
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - screen: The screen to add
|
||||
/// - asSubMenu: Display in a sub menu or directly in menu
|
||||
private func addScreenToMenu(screen: NSScreen, asSubMenu: Bool) {
|
||||
if let id = screen.deviceDescription[NSDeviceDescriptionKey.init("NSScreenNumber")] as? CGDirectDisplayID {
|
||||
|
||||
var edid = EDID()
|
||||
if EDIDTest(id, &edid) {
|
||||
let name = Utils.getDisplayName(forEdid: edid)
|
||||
let serial = Utils.getDisplaySerial(forEdid: edid)
|
||||
|
||||
let display = Display.init(id, name: name, serial: serial)
|
||||
|
||||
let monitorSubMenu: NSMenu = asSubMenu ? NSMenu() : statusMenu
|
||||
let volumeSliderHandler = Utils.addSliderMenuItem(toMenu: monitorSubMenu,
|
||||
forDisplay: display,
|
||||
command: AUDIO_SPEAKER_VOLUME,
|
||||
title: NSLocalizedString("Volume", comment: "Shown in menu"))
|
||||
let brightnessSliderHandler = Utils.addSliderMenuItem(toMenu: monitorSubMenu,
|
||||
forDisplay: display,
|
||||
command: BRIGHTNESS,
|
||||
title: NSLocalizedString("Brightness", comment: "Shown in menu"))
|
||||
if prefs.bool(forKey: Utils.PrefKeys.showContrast.rawValue) {
|
||||
let contrastSliderHandler = Utils.addSliderMenuItem(toMenu: monitorSubMenu,
|
||||
forDisplay: display,
|
||||
command: CONTRAST,
|
||||
title: NSLocalizedString("Contrast", comment: "Shown in menu"))
|
||||
display.contrastSliderHandler = contrastSliderHandler
|
||||
}
|
||||
|
||||
display.volumeSliderHandler = volumeSliderHandler
|
||||
display.brightnessSliderHandler = brightnessSliderHandler
|
||||
displays.append(display)
|
||||
|
||||
let monitorMenuItem = NSMenuItem()
|
||||
monitorMenuItem.title = "\(name)"
|
||||
if asSubMenu {
|
||||
monitorMenuItem.submenu = monitorSubMenu
|
||||
}
|
||||
|
||||
monitorItems.append(monitorMenuItem)
|
||||
statusMenu.insertItem(monitorMenuItem, at: 0)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// MARK: - Media Key Tap delegate
|
||||
extension AppDelegate: MediaKeyTapDelegate {
|
||||
|
||||
func handle(mediaKey: MediaKey, event: KeyEvent?) {
|
||||
guard let currentDisplay = Utils.getCurrentDisplay(from: displays) else { return }
|
||||
let allDisplays = prefs.bool(forKey: Utils.PrefKeys.allScreens.rawValue) ? displays : [currentDisplay]
|
||||
for display in allDisplays {
|
||||
if (prefs.object(forKey: "\(display.identifier)-state") as? Bool) ?? true {
|
||||
switch mediaKey {
|
||||
case .brightnessUp:
|
||||
let value = display.calcNewValue(for: BRIGHTNESS, withRel: +step)
|
||||
display.setBrightness(to: value)
|
||||
case .brightnessDown:
|
||||
let value = currentDisplay.calcNewValue(for: BRIGHTNESS, withRel: -step)
|
||||
display.setBrightness(to: value)
|
||||
case .mute:
|
||||
display.mute()
|
||||
case .volumeUp:
|
||||
let value = display.calcNewValue(for: AUDIO_SPEAKER_VOLUME, withRel: +step)
|
||||
display.setVolume(to: value)
|
||||
case .volumeDown:
|
||||
let value = display.calcNewValue(for: AUDIO_SPEAKER_VOLUME, withRel: -step)
|
||||
display.setVolume(to: value)
|
||||
default:
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// MARK: - Prefs notification
|
||||
|
||||
@objc func handleListenForChanged() {
|
||||
let listenFor = prefs.integer(forKey: Utils.PrefKeys.listenFor.rawValue)
|
||||
keysListenedFor = [.brightnessUp, .brightnessDown, .mute, .volumeUp, .volumeDown]
|
||||
if listenFor == Utils.ListenForKeys.brightnessOnlyKeys.rawValue {
|
||||
keysListenedFor.removeSubrange(2...4)
|
||||
} else if listenFor == Utils.ListenForKeys.volumeOnlyKeys.rawValue {
|
||||
keysListenedFor.removeSubrange(0...1)
|
||||
}
|
||||
|
||||
mediaKeyTap?.stop()
|
||||
mediaKeyTap = MediaKeyTap.init(delegate: self, for: keysListenedFor, observeBuiltIn: false)
|
||||
mediaKeyTap?.start()
|
||||
}
|
||||
|
||||
@objc func handleShowContrastChanged() {
|
||||
self.updateDisplays()
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue