2012-03-18 160 views
6

我在开发可可用户界面时遇到了与gui /线程相关的问题。该应用程序是这样设计的:在非主线程中运行可可GUI

主线程(#1):解析参数加载插件等

GUI线程(#):启动GUI,处理事件等,其GUI线程。

Cocoa框架是非线程安全的,但强制执行一条规则,GUI必须在主线程上运行。断言用于检查这一点。为了尝试去解决这个问题,我自己实现了这个运行方法(代码如下) - http://cocoawithlove.com/2009/01/demystifying-nsapplication-by.html - guide。但我错过了一些东西。窗户打开,但保持空白(完全白色)。虽然如果我在主线程中进行调用,它可以很好地工作。

所以基本上我需要找出缺少的东西。

- (void)run 
{ 
    NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; 

    [self finishLaunching]; 

    shouldKeepRunning = YES; 
    do 
    { 
     [pool release]; 
     pool = [[NSAutoreleasePool alloc] init]; 

     NSEvent *event = 
      [self 
       nextEventMatchingMask:NSAnyEventMask 
       untilDate:[NSDate distantFuture] 
       inMode:NSDefaultRunLoopMode 
       dequeue:YES]; 

     [self sendEvent:event]; 
     [self updateWindows]; 
    } while (shouldKeepRunning); 

    [pool release]; 
} 

- (void)terminate:(id)sender 
{ 
    shouldKeepRunning = NO; 
} 
+0

看起来你应该扭转你正在使用你的线程的东西。为什么要打架? – 2012-03-18 20:48:26

+1

因为我宁愿不打架该程序的插件架构...但我想我必须承认这一个... – OCarlos 2012-03-18 22:46:41

回答

14

不要。这种方法将无法工作。即使您修复了当前的问题(该窗口未绘制),您仍会立即遇到另一个模糊不清的问题,以及另一个难题。 Cocoa期望GUI线程成为主线,故事结束。

+0

虽然想到了很多,但我想试试它...谢谢你的答复。 – OCarlos 2012-03-18 22:57:53

1

为什么不能解决问题?让主线程产生一个线程(让我们称之为应用程序线程),然后在产生GUI之前阻塞。应用程序线程将解析参数,加载插件等。初始化完成后,应用程序线程将发信号通知主线程继续并启动GUI。

1

除了更新GUI之外,在后台线程中执行所有操作。我看到你只有一行需要更新GUI。所以,做你正在做的方式,除非你在主线程中执行所有的图形用户界面的更新:

dispatch_async(dispatch_get_main_queue(),^
{ 
    [self updateWindows]; 
}); 

现在我不知道什么是updateWindows,我认为这不会创造竞争条件。