2

NSNotification はメイン スレッド以外のスレッドでセレクターを呼び出すため、その通知に応じて UIView やその他のインターフェイス要素に加えた変更は、反映されるまでに時間がかかることがよくあります。これは、メイン スレッドがビジー状態の場合に最も深刻です (私の場合はよくあります!)。

「performSelectorOnMainThread:」を呼び出すことで問題を解決できます。これは本当にベストプラクティスですか?

- (void) gotMovieSaveFinishNotication: (NSNotification *) not {
NSURL *exportMovieURL = (NSURL *) [not object];
//saving the composed video to the photos album
ALAssetsLibrary* library = [[[ALAssetsLibrary alloc] init] autorelease];

if(![library videoAtPathIsCompatibleWithSavedPhotosAlbum: exportMovieURL]) {
    NSLog(@"videoAtPathIsCompatibleWithSavedPhotosAlbum fails for: @",exportMovieURL);
    return;
}

[library writeVideoAtPathToSavedPhotosAlbum:exportMovieURL 
                            completionBlock:^(NSURL *assetURL, NSError *error)
 {
     [self performSelectorOnMainThread:@selector(setTintToNormal)
                            withObject: NULL
                         waitUntilDone: YES];

     if(error)
     {
         DLog(@"The video saving failed with the following error =============== %@",error);//notify of completion
     }
     else
     {
         DLog(@"The video is saved to the Photos Album successfully");

     }


 }];

}

4

2 に答える 2

3

NSNotificationCenter は、呼び出したのと同じスレッドで通知を送信しますpostNotification! したがって、それはメイン スレッドまたはバックグラウンド スレッドである可能性があります。

ところで、メイン以外のスレッドから UI を変更するべきではありません。完全に停止してください。速度の問題でさえありません。変更を行うべきではありません。物事が失敗する可能性があります。

あなたのソリューションは確かに実行可能ですが、少し異なる (そしておそらくより良い) 方法があります。情報については、このページを参照してください。

http://www.cocoanetics.com/2010/05/nsnotifications-and-background-threads/

要約すると、上記のリンクのアプローチは、カテゴリ内のいくつかの便利なヘルパー メソッドを介して、実際にメソッドを呼び出してメイン スレッドで通知を生成することにより、問題を処理します。役に立つかもしれません!現在の手法では、アプリで通知を受け取るたびperformSelectorOnMainThreadに多くの呼び出しが発生する可能性があるため、実際の通知受信メソッドから呼び出すソリューションよりも少し「きれい」に感じます。performSelectorOnMainThread

また、これは有用な情報です:

http://cocoadev.com/index.pl?NotificationsAcrossThreads

于 2011-03-13T20:34:26.953 に答える
2

はい。UIに関連するすべてのメソッドは、メインスレッドでのみ呼び出す必要があります。

あなたが持っている他のオプションは、GCDを使用してそれをメインキューに送信することです:

dispatch_async(dispatch_get_main_queue(), ^{
    // do some stuff on the main thread here...

    [self setTintToNormal];
});

また、waitUntilDone:NOを検討してください。可能な限り、ブロックしないでください。

于 2011-03-13T20:28:36.260 に答える