• cocos2dx源码分析(1)


    1 class CC_DLL CCCopying
    2 {
    3 public:
    4     virtual CCObject* copyWithZone(CCZone* pZone);
    5 };
    class CC_DLL CCZone
    {
    public:
        CCZone(CCObject *pObject = NULL);
    
    public:
        CCObject *m_pCopyObject;
    };

    CCCopying 类是最简单的一个类了。

    只有一个构造函数,用CCZone初始化一个CCobject

    只是相当于一个接口的作用。

    再看看CCZone类的定义

    只有一个CCObject* m_pCopyObject;

    主要用来保存CCObject对象的。

    可以看看CCZone的构造函数

    1 CCZone::CCZone(CCObject *pObject)
    2 {
    3     m_pCopyObject = pObject;
    4 }

    可以看到,只是保存了CCObject的对象,CCZone中人是为了CCObject子类之间拷贝作用的。

    比如CCAction::copyWithZone(CCZone *pZone) 的实现,代码如下:

    CCObject* CCAction::copyWithZone(CCZone *pZone)
    {
        CCZone *pNewZone = NULL;
        CCAction *pRet = NULL;
        if (pZone && pZone->m_pCopyObject)
        {
            pRet = (CCAction*)(pZone->m_pCopyObject);//这一句,可以看到,CCZone只是方便拷贝使用的。
        }
        else
        {
            pRet = new CCAction();
            pNewZone = new CCZone(pRet);
        }
        //copy member data
        pRet->m_nTag = m_nTag;
        CC_SAFE_DELETE(pNewZone);
        return pRet;
    }

    CCObject继承自CCopying,CCObject有两个功能。提供了引用计数,主要用来进行内存管理的。又分为手动内存管理和自动内存管理。

    看下CCObject类的定义

     1 class CC_DLL CCObject : public CCCopying
     2 {
     3 public:
     4 
     5     //这两个是支持lua等脚本语言用的,可以先不用管
     6     unsigned int        m_uID;        .
     7     int                 m_nLuaID;    
     8 protected:
     9     unsigned int        m_uReference;        //对象的引用计数的
    10     unsigned int        m_uAutoReleaseCount;//自动内存管理的
    11 public:
    12     CCObject(void);
    13     virtual ~CCObject(void);
    14     void release(void);                        // 自减1 , m_uReference == 0时,delete this,销毁自己
    15     void retain(void);                        // 自增1 , m_uReference++ ; 
    16     CCObject* autorelease(void);            // 自动内存管理的。CCPoolManager::sharedPoolManager()->addObject(this);CCPoolManager是个内存池管理的
    17     CCObject* copy(void);                    // CCObject的拷贝机制,内存就一句代码  return copyWithZone(0); ,可见,是调用了copyWithZone
    18     bool isSingleReference(void) const;        // 判断是不是单个引用 
    19     unsigned int retainCount(void) const;    // 返回引用数
    20     virtual bool isEqual(const CCObject* pObject); //判断两个对象是否是同一个对象
    21 
    22     virtual void acceptVisitor(CCDataVisitor &visitor);
    23     virtual void update(float dt) {CC_UNUSED_PARAM(dt);};    
    24     friend class CCAutoreleasePool;            // 把CCAutoreleasePool设为CCObject的友元类,是为了方便CCAutoreleasePool访问CCObject中的成员进而进行内存管理
    25 };

    相应的CCObject实现代码如下,可以参照上面的注释进行理解

     1 CCObject* CCCopying::copyWithZone(CCZone *pZone)
     2 {
     3     CC_UNUSED_PARAM(pZone);
     4     CCAssert(0, "not implement");
     5     return 0;
     6 }
     7 
     8 CCObject::CCObject(void)
     9 : m_nLuaID(0)
    10 , m_uReference(1) // when the object is created, the reference count of it is 1
    11 , m_uAutoReleaseCount(0)
    12 {
    13     static unsigned int uObjectCount = 0;
    14 
    15     m_uID = ++uObjectCount;
    16 }
    17 
    18 CCObject::~CCObject(void)
    19 {
    20     // if the object is managed, we should remove it
    21     // from pool manager
    22     if (m_uAutoReleaseCount > 0)
    23     {
    24         CCPoolManager::sharedPoolManager()->removeObject(this);
    25     }
    26 
    27     // if the object is referenced by Lua engine, remove it
    28     if (m_nLuaID)
    29     {
    30         CCScriptEngineManager::sharedManager()->getScriptEngine()->removeScriptObjectByCCObject(this);
    31     }
    32     else
    33     {
    34         CCScriptEngineProtocol* pEngine = CCScriptEngineManager::sharedManager()->getScriptEngine();
    35         if (pEngine != NULL && pEngine->getScriptType() == kScriptTypeJavascript)
    36         {
    37             pEngine->removeScriptObjectByCCObject(this);
    38         }
    39     }
    40 }
    41 
    42 CCObject* CCObject::copy()
    43 {
    44     return copyWithZone(0);
    45 }
    46 
    47 void CCObject::release(void)
    48 {
    49     CCAssert(m_uReference > 0, "reference count should greater than 0");
    50     --m_uReference;
    51 
    52     if (m_uReference == 0)
    53     {
    54         delete this;
    55     }
    56 }
    57 
    58 void CCObject::retain(void)
    59 {
    60     CCAssert(m_uReference > 0, "reference count should greater than 0");
    61 
    62     ++m_uReference;
    63 }
    64 
    65 CCObject* CCObject::autorelease(void)
    66 {
    67     CCPoolManager::sharedPoolManager()->addObject(this);
    68     return this;
    69 }
    70 
    71 bool CCObject::isSingleReference(void) const
    72 {
    73     return m_uReference == 1;
    74 }
    75 
    76 unsigned int CCObject::retainCount(void) const
    77 {
    78     return m_uReference;
    79 }
    80 
    81 bool CCObject::isEqual(const CCObject *pObject)
    82 {
    83     return this == pObject;
    84 }
    85 
    86 void CCObject::acceptVisitor(CCDataVisitor &visitor)
    87 {
    88     visitor.visitObject(this);
    89 }

    另外介绍3个宏,分别是NS_CC_BEGIN ,NS_CC_END ,USING_NS_CC     

    定义分别如下

    #define NS_CC_BEGIN namespace cocos2d {
    #define NS_CC_END }

    #define USING_NS_CC     using namespace cocos2d

    通过定义可以得知,前面两个宏的其实就是用来进行命名空间的声明的。

    namespace cocos2d{

    // here your code

    }

    第3个宏,是在使用 using namespace cocos2d 时可以用USING_NS_CC  代替,个人觉得完全没有必要,直接写觉得更好。

     今天就写到这,写的不完善,还请见谅

    
    
    
    
    
    
    
    
    
    
    
  • 相关阅读:
    ajax请求
    easyui相关问题
    linux解压命令
    angular2 中文学习资料整理
    在angular2服务中注入服务
    Angular 2模板语法
    登录,注册流程(基于token的身份验证)
    Node Js与JavaScript的区别及nodejs优缺点。
    yarn包管理网站
    浅谈Cookie,Session,WebStorage区别,应用场景
  • 原文地址:https://www.cnblogs.com/start1225/p/3525331.html
Copyright © 2020-2023  润新知