cocos2dx-2.X前后台切换分析,基于android平台

前端之家收集整理的这篇文章主要介绍了cocos2dx-2.X前后台切换分析,基于android平台前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。

摘自网上的android生命周期图:


  1. cocos2dx-2.X后台切换分析,基于android平台:
  2. 1、从后台进入前台
  3. 项目的activity一般继承自Cocos2dxActivity,看过activity生命周期的
  4. 都知道onCreateonResume方法,这些函数activity生命周期中
  5. 最重要的函数,具体什么时候调用,可以查看相关资料。
  6.  
  7. //刚进入游戏和游戏从后台回到前台调用
  8. @Override
  9. protected void onResume() {
  10. super.onResume();
  11. Log.d(TAG,"onResume+++++++++++++++++++++++");
  12. Cocos2dxHelper.onResume();
  13. this.mGLSurfaceView.onResume(); --->>
  14. }
  15.  
  16. this.mGLSurfaceView.onResume(); 方法--->>
  17. @Override
  18. public void onResume() {
  19. super.onResume();
  20. this.setRenderMode(RENDERMODE_CONTINUOUSLY);
  21. //使用queueEvent方法:主要是从UI线程切换到OpenGL渲染线程
  22. this.queueEvent(new Runnable() {
  23. @Override
  24. public void run() {
  25. Cocos2dxGLSurfaceView.this.mCocos2dxRenderer.handleOnResume();
  26. }
  27. });
  28. }
  29.  
  30. ------>>>
  31. public void handleOnResume() {
  32. //private static native void nativeOnResume();
  33. //调用了一个native方法,在C++端实现
  34. Cocos2dxRenderer.nativeOnResume();
  35. }
  36. //C++端的实现在Java_org_cocos2dx_lib_Cocos2dxRenderer.cpp文件中:
  37. JNIEXPORT void JNICALL Java_org_cocos2dx_lib_Cocos2dxRenderer_nativeOnResume() {
  38. //做个标记(1)这里和我要在下面说的一点有关****
  39. if (CCDirector::sharedDirector()->getOpenGLView()) {
  40. CCApplication::sharedApplication()->applicationWillEnterForeground();
  41. }
  42. }
  43.  
  44. // this function will be called when the app is active again
  45. //进入前台,我们可以在这里做一些处理
  46. void AppDelegate::applicationWillEnterForeground()
  47. {
  48. CCDirector::sharedDirector()->startAnimation();
  49.  
  50. SimpleAudioEngine::sharedEngine()->resumeBackgroundMusic();
  51. }
  52.  
  53. 2 //从前台进入后台调用过程
  54. @Override
  55. protected void onPause() {
  56. super.onPause();
  57. Log.d(TAG,"onPause+++++++++++++++++++++++");
  58. Cocos2dxHelper.onPause();
  59. this.mGLSurfaceView.onPause();
  60. }
  61.  
  62. //this.mGLSurfaceView.onPause();--->>
  63. @Override
  64. public void onPause() {
  65. this.queueEvent(new Runnable() {
  66. @Override
  67. public void run() {
  68. Cocos2dxGLSurfaceView.this.mCocos2dxRenderer.handleOnPause();
  69. }
  70. });
  71. this.setRenderMode(RENDERMODE_WHEN_DIRTY);
  72. //super.onPause();
  73. }
  74.  
  75. ---->>>mCocos2dxRenderer.handleOnPause:
  76. public void handleOnPause() {
  77. Cocos2dxRenderer.nativeOnPause();
  78. }
  79. ----->>>native方法调用C++端的函数
  80. private static native void nativeOnPause();
  81.  
  82. //C++端的实现在Java_org_cocos2dx_lib_Cocos2dxRenderer.cpp文件中:
  83. JNIEXPORT void JNICALL Java_org_cocos2dx_lib_Cocos2dxRenderer_nativeOnPause() {
  84. //进入后台
  85. CCApplication::sharedApplication()->applicationDidEnterBackground();
  86.  
  87. CCNotificationCenter::sharedNotificationCenter()->postNotification(EVENT_COME_TO_BACKGROUND,NULL);
  88. }
  89.  
  90. // This function will be called when the app is inactive. When comes a phone call,it's be invoked too
  91. //进入后台,我们可以在这里做一些处理。
  92. void AppDelegate::applicationDidEnterBackground()
  93. {
  94. CCDirector::sharedDirector()->stopAnimation();
  95.  
  96. SimpleAudioEngine::sharedEngine()->pauseBackgroundMusic();
  97. }
  98.  
  99. 3、我的一点疑惑(已解决)
  100. activity生命周期中我们看到,在第一次进入游戏中时也会调用onResume方法,如果这样,那我们就不能
  101. 认为调用applicationWillEnterForeground方法的时机是从后台进入前台,如果这样我们在处理游戏从后台进入
  102. 前台时,就需要注意这个问题。其实,第一次进入游戏applicationWillEnterForeground方法是不会调用的,
  103. 我们可以不用管上面我说的那个问题。至于为什么,下面分析:
  104. 3.1、在activity中的onResume方法Cocos2dxRenderer类中的onSurfaceCreated方法中加入log日志,看下
  105. 两个地方的执行顺序:
  106. @Override
  107. //onSurfaceCreated在surface创建时调用,在这里调用nativeInit方法进行一些初始化。
  108. //具体整个过程,可以查看cocos2dx启动过程相关的资料。
  109. public void onSurfaceCreated(final GL10 pGL10,final EGLConfig pEGLConfig) {
  110. Log.d("","onSurfaceCreated+++++++++++");
  111. Cocos2dxRenderer.nativeInit(this.mScreenWidth,this.mScreenHeight);
  112. this.mLastTickInNanoSeconds = System.nanoTime();
  113. }
  114.  
  115. --->>>
  116. void Java_org_cocos2dx_lib_Cocos2dxRenderer_nativeInit(JNIEnv* env,jobject thiz,jint w,jint h)
  117. {
  118. if (!CCDirector::sharedDirector()->getOpenGLView())
  119. {
  120. //这里创建才创建CCEGLView,第二个标记(2)*****
  121. CCEGLView *view = CCEGLView::sharedOpenGLView();
  122. view->setFrameSize(w,h);
  123.  
  124. AppDelegate *pAppDelegate = new AppDelegate();
  125. CCApplication::sharedApplication()->run();
  126. }
  127. else
  128. {
  129. //其实这里我有一点疑问?就是这个分支什么时候会被执行,我试了很多次,都没有看到什么时候执行。
  130. //有待以后学习。
  131. ccGLInvalidateStateCache();
  132. CCShaderCache::sharedShaderCache()->reloadDefaultShaders();
  133. ccDrawInit();
  134. CCTextureCache::reloadAllTextures();
  135. CCNotificationCenter::sharedNotificationCenter()->postNotification(EVENT_COME_TO_FOREGROUND,NULL);
  136. CCDirector::sharedDirector()->setGLDefaultValues();
  137. }
  138. }
  139.  
  140. activity中的onResume方法Cocos2dxRenderer类中的onSurfaceCreated方法的执行顺序:
  141. 看下面的输出信息就可以清楚的知道,onResume方法先执行而onSurfaceCreated方法后执行
  142. 05-21 16:03:32.520: D/Cocos2dxActivity(7953): onResume+++++++++++++++++++++++
  143. 05-21 16:03:32.740: D/(7953): onSurfaceCreated+++++++++++
  144.  
  145. 还记的我们做过的(1)和(2)两个标记吗?
  146. 标记(1):看到这里大家应该明白了吧,这里对是否进入applicationWillEnterForeground函数
  147. 加了一个判断CCDirector::sharedDirector()->getOpenGLView()即CCEGLView是否存在,
  148. 按照上面的说明在 onSurfaceCreated -->> Java_org_cocos2dx_lib_Cocos2dxRenderer_nativeInit -->>
  149. --->> CCEGLView *view = CCEGLView::sharedOpenGLView() 即在nativeInit方法中才创建CCEGLView类的实例,
  150. 根据上面说的执行顺序,onResume方法onSurfaceCreated方法之前执行,就意味着在nativeInit方法之前执行,
  151. 同样意味着第一次进入游戏时,因为CCDirector::sharedDirector()->getOpenGLView()方法返回NULL,因为还没有
  152. 实例化,所以applicationWillEnterForeground方法并不会执行。而当游戏从后台切换到前台时,
  153. CCDirector::sharedDirector()->getOpenGLView()方法返回已经构造的实例变量,所以可以进入
  154. applicationWillEnterForeground函数
  155. JNIEXPORT void JNICALL Java_org_cocos2dx_lib_Cocos2dxRenderer_nativeOnResume() {
  156. //做个标记(1)这里和我要在下面说的一点有关****
  157. if (CCDirector::sharedDirector()->getOpenGLView()) {
  158. CCApplication::sharedApplication()->applicationWillEnterForeground();
  159. }
  160. }

猜你在找的Cocos2d-x相关文章