Cocos2dx 多线程

摘要:
首先想到的是cocos2d-x是否有自己的方法。Cocos2d-x附带了第三方插件pthread。在Cocos2dxplatformhird_Partywin32pthread中可以找到。例如下面的代码显示了简单的线程启动方法:头文件:[cpp]viewplaincopy#ifndef_LOADING_SCENE_H__#define_LOADING_SCENE_H__#Include“cocos2d.H”#Include“pthread/phread.H”classLoadingScene:publiccocos2d::CCScene{public:virtualcoolity();CREATE_FUNC;intstart(); 无效更新;私有:pthread_tpid;staticvoid*updateInfo//注意,线程函数必须是静态的};Cpp文件[Cpp]viewplaincopy#include“LoadingScene.h”#include使用namespacecopies2d“pthread/phread.h”;boolLoadingScene::init(){this-˃scheduleUpdate();start();returntrue;}VoidLoadingScene::update{//可以在此处重新绘制UI}void*LoadingScene::updateInfo{//可在此处加载资源returnNULL;}IntLoadingScene::start(){pthread_create;//启动新线程return0;}第二,我们可以在新打开的线程中加载Plist。可以在新的螺纹中执行钳子等操作。这不是cocos2d所支持的,而是opengl的标准。无论您在Android或Windows上使用opengl,这一原则都适用。发现CCSpriteFrameCache::addSpriteFramesWithFile方法可以传入Texture2D参数。

多-threaded负荷plist特征。获取知识的必要性:

1.多线程开启:pthread

2.怎样在线程中载入plist


一.多线程开启

当我们想在程序中开多线程中。第一想到的是cocos2d-x有没有自带方法。幸运的是我们找到了CCThread,不幸却发现里面什么都没有。

cocos2d-x自带了一个第三方插件--pthread,在cocos2dxplatform hird_partywin32pthread能够找到。既然是自带的,必须它的理由。想在VS中应用这个插件须要两个步骤:

1.须要右键project--属性--配置属性--链接器--输入--编缉右側的附加依赖项--在当中加入pthreadVCE2.lib,例如以下图所看到的:

Cocos2dx 多线程第1张

2..须要右键project--属性--配置属性--C/C++--常规--编缉右側的附加包括文件夹--加入新行--找到pthread文件夹所在位置。例如以下图所看到的:

Cocos2dx 多线程第2张


然后我们就能够应用这个插件在程序中开启新线程。简单线程开启方法例如以下代码所看到的:

头文件:

  1. #ifndef _LOADING_SCENE_H__  
  2. #define _LOADING_SCENE_H__  
  3.   
  4. #include "cocos2d.h"  
  5. #include "pthread/pthread.h"  
  6. class LoadingScene : public cocos2d::CCScene{  
  7. public:  
  8.     virtual bool init();  
  9.     CREATE_FUNC(LoadingScene);  
  10.     int start();    
  11.     void update(float dt);  
  12. private:  
  13.     pthread_t pid;  
  14.     static void* updateInfo(void* args); //注意线程函数必须是静态的  
  15. };  


cpp文件
  1. #include "LoadingScene.h"  
  2. #include "pthread/pthread.h"  
  3.   
  4. using namespace cocos2d;  
  5. bool LoadingScene::init(){  
  6.     this->scheduleUpdate();  
  7.     start();  
  8.     return true;  
  9. }  
  10. void LoadingScene::update(float dt){  
  11.            //能够在这里重绘UI  
  12. }  
  13. void* LoadingScene::updateInfo(void* args){  
  14.       //能够在这里载入资源  
  15.     return NULL;  
  16. }  
  17. int LoadingScene::start(){  
  18.     pthread_create(&pid,NULL,updateInfo,NULL); //开启新线程  
  19.     return 0;  
  20. }  



二 载入Plist

我们能够在新开的线程中。载入资源,设置一个静态变量bool,在新线程中。当载入全然部资源后,设置bool值为真。在主线程中Update中,检測bool值,为假,能够重绘UI(比如,显示载入图片,或者模拟载入进度),为真,则载入目标场景。相关代码例如以下:

  1. void* LoadingScene::updateInfo(void* args){  
  2.      CCSpriteFrameCache *cache = CCSpriteFrameCache::sharedSpriteFrameCache();  
  3.      cache->addSpriteFramesWithFile("BattleIcons.plist");  
  4.      cache->addSpriteFramesWithFile("ArcherAnim.plist");  
  5.      cache->addSpriteFramesWithFile("DeathReaperAnim.plist");  
  6.      loadComplete = true;  //状态值设为真,表示载入完毕  
  7.      return NULL;  
  8. }  


成功载入且执行后,你会发现新场景中全部精灵都不显示(类似于黑屏了)。为什么呢?

由于我们在载入plist文件时,addSpriteFramesWithFile方法里会帮我们创建plist相应Png图的Texture2D,并将其载入进缓存中。但是这里就遇到了一个OpenGl规范的问题:不能在新开的线程中。创建texture,texture必须在主线程创建.通俗点,就是全部的opengl api都必须在主线程中调用;其他的操作,比方文件,内存。plist等,能够在新线程中做,这个不是cocos2d不支持,是opengl的标准,无论你是在android,还是windows上使用opengl,都是这个原理。

所以不能在新线程中创建Texture2D,导致纹理都不显示。那么该怎么办?让我们看看CCSpriteFrameCache源代码。发现CCSpriteFrameCache::addSpriteFramesWithFile(const char *pszPlist, CCTexture2D *pobTexture)方法,是能够传入Texture2D參数的。

是的。我们找到了解决方法:

相关代码例如以下:

  1. int LoadingScene::start(){  
  2.     CCTexture2D *texture = CCTextureCache::sharedTextureCache()->addImage("BattleIcons.png"); //在这里(主线程中)载入plist相应的Png图片进纹理缓存  
  3.     CCTexture2D *texture2 = CCTextureCache::sharedTextureCache()->addImage("ArcherAnim.png"); //以这样的方法载入的纹理,其Key值就是文件path值,即比如  
  4. texture2的key值就是ArcherAnim.png  
  5.     CCTexture2D *texture3 = CCTextureCache::sharedTextureCache()->addImage("DeathReaperAnim.png");  
  6.     pthread_create(&pid,NULL,updateInfo,NULL); //开启新线程  
  7.     return 0;  
  8. }  
  9. void* LoadingScene::updateInfo(void* args){  
  10.     CCSpriteFrameCache *cache = CCSpriteFrameCache::sharedSpriteFrameCache();  
  11.     CCTextureCache* teCache = CCTextureCache::sharedTextureCache();     
  12.     CCTexture2D* texture1 = teCache->textureForKey("BattleIcons.png"); //从纹理缓存中取出Texure2D,并将其当參数传入addSpriteFramesWithFile方法中  
  13.     cache->addSpriteFramesWithFile("BattleIcons.plist",texture1);  
  14.     CCTexture2D* texture2 = teCache->textureForKey("ArcherAnim.png");  
  15.     cache->addSpriteFramesWithFile("ArcherAnim.plist",texture2);  
  16.     CCTexture2D* texture3 = teCache->textureForKey("DeathReaperAnim.png");  
  17.     cache->addSpriteFramesWithFile("DeathReaperAnim.plist",texture3);  
  18.     loadComplete = true;  
  19.     return NULL;  
  20. }  


解决。这是不是违背OpenGl产品规格,不要创建一个新的线程Texture2D。


免责声明:文章转载自《Cocos2dx 多线程》仅用于学习参考。如对内容有疑问,请及时联系本站处理。

上篇微信小程序tabBar如何设置spark常用参数下篇

宿迁高防,2C2G15M,22元/月;香港BGP,2C5G5M,25元/月 雨云优惠码:MjYwNzM=

相关文章

Python 多线程库总结

多线程库总结基于线程的并行性threading模块下面是一些基础函数,函数包括: 函数 threading.active_count() threading.current_thread() threading.get_ident() threading.enumerate() threading.main_thread() threading.se...

perl多线程使用

原文来自:博客园(华夏35度)http://www.cnblogs.com/zhangchaoyang 作者:Orisun <<=========================threads===========================>> #!/usr/bin/perl use threads ('yield',...

AS3多线程快速入门(二):图像处理[译]

原文链接:http://esdot.ca/site/2012/intro-to-as3-workers-part-2-image-processing 在《AS3多线程快速入门》系列教程的第一部分中,我们研究了AS3 Worker的基本原理,包括多种通信方式,还展示了一个简单例子:Hello World Worker。 在这篇文章里,我将更进一步,向你展...

多线程和CPU的关系

什么是CPU (1)         Central  Progressing  Unit 中央处理器,是一块超大规模的集成电路,是一台计算机的运算核心和控制核心。 (2)         CPU包括 运算器,高速缓冲存储器,总线。 (3)         它的工作,主要是解释计算机中的指令,和处理计算机软件中的数据。它在计算机中起着最重要的作用,构成了系...

python中多进程multiprocessing、多线程threading、线程池threadpool

浅显点理解:进程就是一个程序,里面的线程就是用来干活的,,,进程大,线程小 一、多线程threading 简单的单线程和多线程运行:一个参数时,后面要加逗号 步骤:for循环,相当于多个线程——t=threading.Thread(target=函数名,args=(参数,))——t.start()——while threading.active_coun...

CL.exe

CL.exe  CL.exe 是控制 Microsoft C 和 C++ 编译器与链接器的 32 位工具。编译器产生通用对象文件格式 (COFF) 对象 (.obj) 文件。链接器产生可运行文件 (.exe) 或动态链接库文件 (DLL)。 注意,全部编译器选项都区分大写和小写。 若要编译但不链接,请使用 /c。 使用 NMAKE...