I am writing a small macOS app in which the app intercept all the keyboard events and nullify them.I use CGEventType to achieve this goal, but CGEventType does not include the power button on macbook. When I press the power button, the app is unable to intercept. So I wonder if there is a way to include the power button too. Big thanks in acvance.
this is code I have:
private func startKeyboardMonitoring() {
let eventMask = (1 << CGEventType.keyDown.rawValue) | (1 << CGEventType.keyUp.rawValue) | (1 << CGEventType.flagsChanged.rawValue)
guard let eventTap = CGEvent.tapCreate(
tap: .cgSessionEventTap,
place: .headInsertEventTap,
options: .defaultTap,
eventsOfInterest: CGEventMask(eventMask),
callback: { (proxy, type, event, refcon) -> Unmanaged? in
let keyCallback = Unmanaged.fromOpaque(refcon!).takeUnretainedValue()
return keyCallback.keyboardCallback(proxy: proxy, type: type, event: event)
},
userInfo: Unmanaged.passUnretained(self).toOpaque()
) else {
print(“Failed to create keyboard event tap”)
return
}
self.keyboardEventTap = eventTap
let runLoopSource = CFMachPortCreateRunLoopSource(kCFAllocatorDefault, eventTap, 0)
CFRunLoopAddSource(CFRunLoopGetCurrent(), runLoopSource, .commonModes)
CGEvent.tapEnable(tap: eventTap, enable: true)
}
private func keyboardCallback(proxy: CGEventTapProxy, type: CGEventType, event: CGEvent) -> Unmanaged<CGEvent>? {
let keyCode = event.getIntegerValueField(.keyboardEventKeycode)
let flags = event.flags
let isKeyComboPressed = keyCode == stopMonitoringKeyCombo.keyCode && flags.contains(stopMonitoringKeyCombo.flags)
if isKeyComboPressed && !lastKeyComboState {
DispatchQueue.main.async {
self.isMonitoring.toggle()
}
}
lastKeyComboState = isKeyComboPressed
return (isMonitoring && !isKeyComboPressed) ? nil : Unmanaged.passRetained(event)
}