停止 NSApplication 主事件循环
Stopping the NSApplication main event loop
我有一个包含以下单个 .m
文件的应用程序:
#import <Cocoa/Cocoa.h>
int main(int argc, char* argv[]) {
[[[NSThread alloc] initWithBlock: ^{
sleep(2);
dispatch_async(dispatch_get_main_queue(), ^{
NSLog(@"Stop");
[[NSApplication sharedApplication] stop:nil];
});
}] start];
[[NSApplication sharedApplication] run];
NSLog(@"Run finished");
return 0;
}
根据 the developer documentation, stop
should stop the main loop (run
), but it doesn't (at least not on OS X 10.12 and 10.13). There's also terminate
,但这会过早退出程序。我还尝试设置一个实现 applicationShouldTerminate
的 NSApplicationDelegate
,但这从未被调用过。
如何确保 运行 主循环(干净地)退出?
注意: 共享应用程序主循环是必需的,因为 UI 其他地方正在进行工作。更具体地说,这给 Go WDE UI 库带来了问题,它使用 Cocoa 为 Go 应用程序提供 window。
[C]alling this method from a timer or run-loop observer routine would not stop the run loop because they do not result in the posting of an NSEvent object.
分派到主队列的块的相似之处在于它不post一个事件。您可以在调用 -stop:
.
后尝试 posting 一个 NSEventTypeApplicationDefined
事件
进一步调查后,似乎 UI 循环 stop
请求仅在 UI 事件后处理(所以不是就在主循环事件之后)。因此,它可以响应 UI 事件,但不像我在示例中那样在线程中工作。
在 stop
请求后触发 UI 事件(例如,程序化调整大小对我有用)会导致循环结束。
我有一个包含以下单个 .m
文件的应用程序:
#import <Cocoa/Cocoa.h>
int main(int argc, char* argv[]) {
[[[NSThread alloc] initWithBlock: ^{
sleep(2);
dispatch_async(dispatch_get_main_queue(), ^{
NSLog(@"Stop");
[[NSApplication sharedApplication] stop:nil];
});
}] start];
[[NSApplication sharedApplication] run];
NSLog(@"Run finished");
return 0;
}
根据 the developer documentation, stop
should stop the main loop (run
), but it doesn't (at least not on OS X 10.12 and 10.13). There's also terminate
,但这会过早退出程序。我还尝试设置一个实现 applicationShouldTerminate
的 NSApplicationDelegate
,但这从未被调用过。
如何确保 运行 主循环(干净地)退出?
注意: 共享应用程序主循环是必需的,因为 UI 其他地方正在进行工作。更具体地说,这给 Go WDE UI 库带来了问题,它使用 Cocoa 为 Go 应用程序提供 window。
[C]alling this method from a timer or run-loop observer routine would not stop the run loop because they do not result in the posting of an NSEvent object.
分派到主队列的块的相似之处在于它不post一个事件。您可以在调用 -stop:
.
NSEventTypeApplicationDefined
事件
进一步调查后,似乎 UI 循环 stop
请求仅在 UI 事件后处理(所以不是就在主循环事件之后)。因此,它可以响应 UI 事件,但不像我在示例中那样在线程中工作。
在 stop
请求后触发 UI 事件(例如,程序化调整大小对我有用)会导致循环结束。