顾名思义,removeFromParent就是把自己从父亲那里移除,removeAllChildren就是移除自己所有的孩子,这些方法的具体实现都在基类Node里面,通过查看代码也很容易看到怎么实现的。

现在主要看下他们两个的调用顺序

示例代码如下:

比如自定义一个类Layer,

#ifndef _MAINMENU_H1_
#define _MAINMENU_H1_ #include "cocos2d.h"
using namespace cocos2d;
using namespace std;
class Layer1 : public Layer
{
public:
Layer1(); virtual ~Layer1(); bool init(); virtual bool onTouchBegan(Touch *pTouch, Event *pEvent);
virtual void onTouchMoved(Touch *pTouch, Event *pEvent);
virtual void onTouchEnded(Touch *pTouch, Event *pEvent);
virtual void onTouchCancelled(Touch *pTouch, Event *pEvent); string haha; CREATE_FUNC(Layer1); }; #endif
#include "Layer1.h"

Layer1::Layer1()
{ }
Layer1::~Layer1()
{ printf("析构函数"); } bool Layer1::init()
{
// this->setTouchEnabled(true); auto listen = EventListenerTouchOneByOne::create();
listen->onTouchBegan = CC_CALLBACK_2(Layer1::onTouchBegan, this);
listen->onTouchMoved = CC_CALLBACK_2(Layer1::onTouchMoved, this);
listen->onTouchEnded = CC_CALLBACK_2(Layer1::onTouchEnded, this);
listen->onTouchCancelled = CC_CALLBACK_2(Layer1::onTouchCancelled, this);
// listen->setSwallowTouches(true);
Director::getInstance()->getEventDispatcher()->addEventListenerWithSceneGraphPriority(listen, this); return true;
} bool Layer1::onTouchBegan(Touch *touch, Event * pEvent)
{
printf("Layer1 began\n"); this->removeFromParent();
this->removeAllChildren(); // for(int i=0;i<100000;i++){
// printf("char=%s",haha.c_str());
// } return true;
} void Layer1::onTouchEnded(Touch *touch, Event * pEvent)
{
printf("Layer1 end\n");
} void Layer1::onTouchCancelled(Touch *touch, Event *pEvent)
{
printf("Layer1 cancel\n");
} void Layer1::onTouchMoved(Touch *touch, Event *pEvent)
{
printf("Layer1 Move\n");
}
AppDelegate
auto scene = Scene::create();
auto layer1=Layer1::create();
scene->addChild(layer1);
director->runWithScene(scene);

当点击界面的时候,会报错,看标红的地方,很容易理解什么原因 removeFromParent之后,Layer1实例已经释放了,在调用就会报错(但是在cocos2d-iphone中,他们的顺序是无关紧要的,都可以正确运行,通过调试得知,当调用RemoveFromPanrent的时候,dealloac没有马上调用,而c++中的析构函数会立即调用,我猜想原因可能就在这里吧),然后把顺序反过来,果然正确执行.

下面再看下一个问题,移除Layer1实例的时候,能否只调用removeFromParent,而不调用removeAllChildren().这个可以通过析构函数来判断,新建一个Layer2的类

#ifndef _MAINMENU_H222_
#define _MAINMENU_H222_ #include "cocos2d.h"
using namespace cocos2d; class Layer2 : public Layer
{
public:
Layer2(); virtual ~Layer2(); bool init(); virtual bool onTouchBegan(Touch *pTouch, Event *pEvent);
virtual void onTouchMoved(Touch *pTouch, Event *pEvent);
virtual void onTouchEnded(Touch *pTouch, Event *pEvent);
virtual void onTouchCancelled(Touch *pTouch, Event *pEvent); CREATE_FUNC(Layer2); }; #endif
#include "Layer2.h"

Layer2::Layer2()
{
} Layer2::~Layer2(){
printf("Layer2析构函数");
} bool Layer2::init()
{
//this->setTouchEnabled(true); auto listen = EventListenerTouchOneByOne::create();
listen->onTouchBegan = CC_CALLBACK_2(Layer2::onTouchBegan, this);
listen->onTouchMoved = CC_CALLBACK_2(Layer2::onTouchMoved, this);
listen->onTouchEnded = CC_CALLBACK_2(Layer2::onTouchEnded, this);
listen->onTouchCancelled = CC_CALLBACK_2(Layer2::onTouchCancelled, this);
// listen->setSwallowTouches(true);
Director::getInstance()->getEventDispatcher()->addEventListenerWithSceneGraphPriority(listen, this); return true;
} bool Layer2::onTouchBegan(Touch *touch, Event * pEvent)
{
printf("Layer2 began\n"); return true;
} void Layer2::onTouchEnded(Touch *touch, Event * pEvent)
{
printf("Layer2 end\n");
// pEvent->stopPropagation();
} void Layer2::onTouchCancelled(Touch *touch, Event *pEvent)
{
printf("Layer2 cancel\n");
} void Layer2::onTouchMoved(Touch *touch, Event *pEvent)
{
printf("Layer2 Move\n");
pEvent->stopPropagation();
}

Layer1修改,去掉

this->removeAllChildren();这一行代码

Appdelegate

   auto scene = Scene::create();
// scene->addChild(MainMenu::create()); auto layer1=Layer1::create(); //int fff=layer1->getReferenceCount(); auto layer2=Layer2::create();
layer1->addChild(layer2);
scene->addChild(layer1);
// layer2->retain(); // run
director->runWithScene(scene);

通过运行发现,Layer2会执行析构函数,那么Layer2是在什么位置被删除的呢,通过看removeFromParent的源码发现,并没有发现删除Layer2的代码,

而在removeAllChildren()中很容易发现是

_children.clear();但是removeFromParent中并没有这个代码,最后通过分析找到了地方,原来Layer的基类Node有一个_children的Vector数组,当

Node释放的时候,他的属性_children也会释放,然后这个属性会调用析构函数,在析构函数里面调用了clear()方法,如下代码

/** Destructor */

~Vector<T>()

{

CCLOGINFO("In the destructor of Vector.");

clear();

},

,从而使Layer1的孩子Layer2也释放。

所以分析得知,要移除某个cocos2d类的实例,在保证没有内存泄露的情况下(内存泄露的话,两个方法都调也不行),调用 removeFromParent就可删除自身,无需调用removeAllChildren(),如果两个类都想调用,那么先调用removeAllChildren,在调用removeFromParent。

cocos2dx3.0 removeFromParent和removeAllChildren含义的更多相关文章

  1. Cocos2d-X3.0 刨根问底(七)----- 事件机制Event源码分析

    这一章,我们来分析Cocos2d-x 事件机制相关的源码, 根据Cocos2d-x的工程目录,我们可以找到所有关于事件的源码都存在放在下图所示的目录中. 从这个event_dispatcher目录中的 ...

  2. linux中shell变量$#,$@,$0,$1,$2的含义解释

    linux中shell变量$#,$@,$0,$1,$2的含义解释: 变量说明: $$ Shell本身的PID(ProcessID) $! Shell最后运行的后台Process的PID $? 最后运行 ...

  3. Cocos2dx-3.0版本 从开发环境搭建(Win32)到项目移植Android平台过程详解

    作为重量级的跨平台开发的游戏引擎,Cocos2d-x在现今的手游开发领域占有重要地位.那么问题来了,作为Cocos2dx的学习者,它的可移植特性我们就需要掌握,要不然总觉得少一门技能.然而这个时候各种 ...

  4. Cocos2d-X3.0 刨根问底(八)----- 场景(Scene)、层(Layer)相关源码分析

    本章节我们重点分析Cocos2d-x3.0与 场景.层相关的源码.这部分源码集中在 libcocos2d –> layers_scenes_transitions_nodes目录下面 我先发个截 ...

  5. Cocos2d-X3.0 刨根问底(一)----- 概览

    罗嗦几句,本系列文章记录了小鱼(本人)自学Cocos2D-X的整个过程,主要从分析Cocos2D-x的源码方式来学习Cocos2d-x这样一个优秀的游戏引擎架构,本着不但要知其然还要知其所以然的学习态 ...

  6. Mac下cocos2dx-3.0打包Android时,提示&quot;SimpleAudioEngine.h&quot;not found的解决方法

    前段时间触控公布cocos2dx-3.0,在升级之后试过之后,在最初的不习惯之后,感觉比之前的好用了不少,在下之前一直是用xCode模板创建,这回算是一口气升到顶了. 之后再一次编程时须要用到Sima ...

  7. cocos2d-x3.0+Eclipse配置说明

    假如我们已经装了JavaJDK.Cygwin,也解压了2013-08-27之后最新的AndroidSDK,其实最新的AndroidSDK已经集成了eclipse,eclipse里面已经配置好了Andr ...

  8. linux中shell变量$#,$@,$0,$1,$2的含义解释

    linux中shell变量$#,$@,$0,$1,$2的含义解释 linux中shell变量$#,$@,$0,$1,$2的含义解释:  变量说明:  $$  Shell本身的PID(ProcessID ...

  9. Cocos2d-x3.0游戏实例之《别救我》第二篇——创建物理世界

    这篇我要给大家介绍两个知识点: 1. 创建游戏物理世界 2. 没了(小若:我噗) 害怕了?不用操心.这太简单了~! 笨木头花心贡献.啥?花心?不呢.是用心~ 转载请注明,原文地址:http://www ...

随机推荐

  1. IT公司100题-26-左旋转字符串

    问题描述: 给定字符串和左旋的字符数,写程序实现字符串的左旋操作.例如对于字符串”12345678″, 左旋转4个字符后,变成”56781234″.要求时间复杂度为O(n),空间复杂度O(1).   ...

  2. Python学习笔记-字符串

    Python之使用字符串 1.所有的标准序列操作(索引,分片,乘法,判断成员资格,求长度,取最小值,最大值)对字符串同样适用.但是字符串都是不可变的. 2.字符串格式化使用字符串格式化操作符即%. f ...

  3. web前端基础篇⑥

    LESS.①是一种拓展技术,基于css.②包含变量.混合.函数.运算.③简化css代码.降低维护成本④目前用的解析器(koala) 变量(值可变)@变量名:值步骤:①建立文件夹②建html和less两 ...

  4. Get IP Address in Android 4.0+

    在android2.3以下的系统中,可以使用如下的代码来获取Android系统的本地IP地址: [java]  private String getLocalIPAddress() throws So ...

  5. C语言实现双向循环链表

    #include <stdio.h> #include <stdlib.h> #include <string.h> struct list_head { stru ...

  6. php 判断复选框checkbox是否被选中

    php 判断复选框checkbox是否被选中   复选框checkbox在php表单提交中经常被使用到,本文章通过实例向大家介绍php如何判断复选框checkbox中的值是否被选中,需要的朋友可以参考 ...

  7. js限制文本框只能输入整数或者带小数点[转]

    这篇文章是关于js限制文本框只能输入整数或者带小数点的内容,以下就是该内容的详细介绍. 做表单验证的时候是否会碰到验证某个输入框内只能填写数字呢,仅允许输入整数数字或者带小数点的数字.下面这段代码也许 ...

  8. linux内核分析——扒开系统调用的三层皮

    万子惠 + 原创作品转载请注明出处 + <Linux内核分析>MOOC课程http://mooc.study.163.com/course/USTC-1000029000 实验部分 选择2 ...

  9. 黑马程序员:Java编程_集合

    =========== ASP.Net+Android+IOS开发..Net培训.期待与您交流!=========== 面向对象语言对事物的体现都是以对象的形式,所以为了方便对多个对象的操作,就对对象 ...

  10. canvas实现类似弹窗广告效果

    先看看下面的效果图,想想使用canvas是怎样实现的? 如下图: 这个就不详细描述了,看代码就会了. <!doctype html> <html lang="en" ...