CGEventTapを使用してキーボードイベントタップの監視を停止する正しい方法は何ですか?
特定のキーの出力を変換するシンプルなバックグラウンドアプリを構築しています。CGEventTapに関するこのすばらしい投稿のおかげで、キー変換を有効にすることができました。残念ながら、私はアプリを殺さずにそれを止めることができないようです。
ユーザーがチェックボックスを切り替えて機能をオンまたはオフにすると、次のメソッドが呼び出されます。トグルオンはすぐに発生します。トグルオフは、有効になるまでに1分以上かかる場合があります。ログを見ると、「無効。タップの変換を停止してください」と表示されます。が検出されました。しかし、キー変換は継続します。理由がわかりません。
- (void)watchEventTap
{
@autoreleasepool
{
CFRunLoopSourceRef runLoopSource = NULL;
CFMachPortRef eventTap = CGEventTapCreate(kCGHIDEventTap, kCGHeadInsertEventTap, kCGEventTapOptionDefault, CGEventMaskBit(kCGEventKeyUp) | CGEventMaskBit(kCGEventKeyDown) | CGEventMaskBit(NX_SYSDEFINED), myCGEventCallback, NULL);
runLoopSource = CFMachPortCreateRunLoopSource(kCFAllocatorDefault, eventTap, 0);
if (!eventTap)
{
NSLog(@"Couldn't create event tap!");
exit(1);
}
if (self.shortcutEnabled) // User default toggled ON
{
NSLog(@"Enabled. Convert taps.");
CFRunLoopAddSource(CFRunLoopGetCurrent(), runLoopSource, kCFRunLoopCommonModes);
CGEventTapEnable(eventTap, true);
// CFRunLoopRun(); // This blocks rest of app from executing
}
else // User default toggled OFF
{
NSLog(@"Disabled. Stop converting taps.");
CFRunLoopRemoveSource(CFRunLoopGetCurrent(), runLoopSource, kCFRunLoopCommonModes);
CGEventTapEnable(eventTap, false);
// Clean up the event tap and source after ourselves.
CFMachPortInvalidate(eventTap);
CFRunLoopSourceInvalidate(runLoopSource);
CFRelease(eventTap);
CFRelease(runLoopSource);
eventTap = NULL;
runLoopSource = NULL;
}
}
// exit(0); // This blocks rest of app from executing
}
提案をありがとう。私はMacOSXアプリを新しく構築しているので、知らないことをしている場合はご容赦ください。