ios - 当主线程被阻塞时,MBProgressHUD 没有及时显示

标签 ios multithreading uikit cocos2d-x mbprogresshud

我正在开发一款使用 cocos2d-x 的游戏,我在 ipad 1 等旧设备上遇到了问题,在这些设备上加载大场景需要很长时间。 所以场景转换可能需要几秒钟,因此我尝试在加载新场景时在场景转换之间实现“忙碌”动画。 我在 IOS 上使用 MBProgressHUD 并在 android 上使用 ProgressDialog 实现了这一点。 我决定不想立即开始显示此动画,而是可以将动画安排在场景转换开始后 1-2 秒开始,这样在较新的设备上根本不会显示动画。 最初我做的是这样的:

- (void) showProgressDialog: (int) runWithoutDelay
    {
    [NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(showProgressDialogAfterDelay) object:nil];
    shouldShow = YES;
    if (runWithoutDelay){
        [self showProgressDialogAfterDelay];
    }
   else{
       [self performSelector:@selector(showProgressDialogAfterDelay) withObject:nil   afterDelay:delay];
       }
   }

- (void) showProgressDialogAfterDelay
  {
   if (shouldShow){
       isShown = YES;
       [progressHUD show:YES];
   }

}

如果我通过场景转换部分,我只会将 shouldShow 标志设置为 false 并且不会启动动画。 问题是,因为 cocos2d-x 场景转换有时是在 main\ui 线程中完成的,而不是在 2 秒后调用 show 方法,所以它需要 6-8 秒才能被调用,有时它甚至在我设置后被调用标记为假。 据我了解,这是因为 performSelector(我也尝试过的 NSTimer 也是如此)都通过将调用置于线程运行循环队列中而在同一线程上运行。 我需要像 performSelectorInBackground 这样需要延迟的东西,所以我尝试使用 dispatch_after (尽管我仍然没有弄清楚如何取消它,因为我需要在创建新计划时取消以前的计划)这看起来更准确根据Xcode 的日志,但即使日志说该方法在计划后恰好 2 秒被调用,该时间仍需要 5-8 秒才能显示,有时甚至根本不显示。 据我了解,如果我错了请纠正我,这是因为 MBProgressHUD 对 UI 的更改必须在主\UI 线程上发生,所以即使我在后台线程上调用 [ProgressHUD show:YES],UI 的实际更新是计划以某种方式在主线程上执行,并且由于它卡在 cocos2d-x 的东西上,它只会在那之后开始显示,当场景转换完成并且为时已晚。

有什么办法可以解决这个问题吗?我能否以某种方式安排它延迟开始但在我需要时立即显示?

我不明白的是,为什么如果我没有延迟地启动它,即使主线程忙于 cocos2d-x 处理,动画也能顺利运行而不会卡住。

最佳答案

我已经设法解决了这个问题!

  1. 创建一个普通方法,您将调用 progressHUD 并调用第二个

  2. 创建第二种方法,您可以在其中执行耗时的操作(加载 View )

  3. 在主线程上执行该方法

示例:

-(void)callHUD {

            [progressHUD show];

            dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
                [self performSelectorOnMainThread:@selector(loadView) withObject:nil waitUntilDone:YES];
                dispatch_async(dispatch_get_main_queue(), ^{
            [progressHUD dismiss];
    });
});
}

-(void)loadView {
    //Perform your segue or transition which needs to load
}

希望对您有所帮助。

关于ios - 当主线程被阻塞时,MBProgressHUD 没有及时显示,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25548625/

相关文章:

ios - 你如何在一个 UITextView (Xcode) 中使用两种字体?

iOS 运动检测 : Motion Detection Sensitivity Levels

java - 如果在 JVM 关闭过程中再次调用 System.exit() 会发生什么情况?

ios - 确定具有不同优先级的两个布局约束中的哪一个是确定它们影响的维度/ anchor 的值

ios - 如何获得像我的值一样随机化的 key ?

ios - iOS:没有有效的配置文件允许指定的权利

c# - c# - 如何在任何有异常的情况下向线程发出停止信号

python - 在 python 中稍后杀死线程

ios - 为多点触控继承 UIControl 的 endTracking

objective-c - Objective C 习语 - 属性、ivars 和 needsDisplay