views:

52

answers:

2

Hey, I have a problem in Multithreading. To describe this, I have two threads. On main thread I have some logic And on another thread, I have a logic and some logic to UI which will update UI. What I want to do is that I want to call some method after the UI on another thread is updated. I think I am supposed to use NSOperationQueue or something. or background queue. but I have read the concurrency programming and threading guide and I still have no idea how to do it.

So how to do it so that I can call a method after a thread is finished? thanks!

+2  A: 

You should never touch the UI from any thread other than the main thread. Two easy ways of sending messsages between threads:

performSelector:

[someObject performSelectorOnMainThread:@selector(someSelector) withObject:nil waitUntilDone:NO];

Notifications:

NSNotification *notification = [NSNotification notificationWithName:@"myNotification" object:nil];
[[NSNotificationCenter defaultCenter] performSelectorOnMainThread:@selector(postNotification:) withObject:notification waitUntilDone:NO];

You can of course also use an NSOperationQueue and Key-Value-Observe the job's finished property, but unless you'd need it for other reasons it just adds unnecessary complexity.

eliego
NSNotifications are received on the same thread they were posted from, so the second example needs to use performSelectorOnMainThread: as well. (And one small typo @selector(postNotification) is missing a ':'.)
Vincent Gable
I'm pretty sure KVO runs on the same thread too, so you're down to performSelectorOnMainThread:
JeremyP
@Vincent Gable:You don't need a colon on the end of the selector. From the docs: The method should not have a significant return value and should take a single argument of type id, **or no arguments** . http://developer.apple.com/mac/library/documentation/Cocoa/Reference/Foundation/Classes/NSObject_Class/Reference/Reference.html#//apple_ref/doc/uid/20000050-CJBEHAEF
JeremyP
Vincent, you're right of course - just forgot to write out onMainThread. The missing colon was intentional though, as JeremyP says.
eliego
Sorry, I meant that '@selector(postNotification)' should be '@selector(postNotification:)', because -postNotification: and -postNotification are two different methods. The colon is part of the name.Running the code,'*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[NSNotificationCenter postNotification]: unrecognized selector sent to instance 0x6d13a70''
Vincent Gable
You're even righter, of course..
eliego
A: 

Here's the nicest way, if you're using iOS 4.0:

dispatch_async(dispatch_get_main_queue(), ^{
    // update the UI here...
});
jtbandes