Cocos2d x 使用c++;在Xcode中
我是cocos2dx的新开发人员。我正在开发一款游戏,其中我使用的是通过物理编辑器加载的box2d实体。游戏中有20多个实体在使用,我正在为与它们相连的单独精灵制作单独的身体,类似的身体在其他关卡中使用,游戏中有50个关卡,对于每个关卡,我制作了单独的类,并再次制作b2body加载功能,所有的代码都正常工作,但我只想做一个通用函数来加载类中的实体,这样我就可以在所有级别使用相同的b2body加载函数。而且我必须在触摸精灵时销毁特定的实体和精灵Cocos2d x 使用c++;在Xcode中,cocos2d-x,Cocos2d X,我是cocos2dx的新开发人员。我正在开发一款游戏,其中我使用的是通过物理编辑器加载的box2d实体。游戏中有20多个实体在使用,我正在为与它们相连的单独精灵制作单独的身体,类似的身体在其他关卡中使用,游戏中有50个关卡,对于每个关卡,我制作了单独的类,并再次制作b2body加载功能,所有的代码都正常工作,但我只想做一个通用函数来加载类中的实体,这样我就可以在所有级别使用相同的b2body加载函数。而且我必须在触摸精灵时销毁特定的实体和精灵 //Sprites: rect_sprite1=CC
//Sprites:
rect_sprite1=CCSprite::create("rect1.png");
rect_sprite1->setScaleX(rX);
rect_sprite1->setScaleY(rY);
this->addChild(rect_sprite1,1);
rect_sprite2=CCSprite::create("rect2.png");
rect_sprite2->setScaleX(rX);
rect_sprite2->setScaleY(rY);
this->addChild(rect_sprite2,1);
rect_sprite3=CCSprite::create("circle.png");
rect_sprite3->setScale(rZ);
this->addChild(rect_sprite3,1);
GB2ShapeCache::sharedGB2ShapeCache()->addShapesWithFile("obs.plist");
//body loading function
void Level1::addNewSpriteWithCoords()
{
CCSize winSize = CCDirector::sharedDirector()->getWinSize();
b2BodyDef bodyDef1;
bodyDef1.type=b2_dynamicBody;
bodyDef1.position.Set((winSize.width*0.38)/PTM_RATIO,(winSize.height*0.4) /PTM_RATIO);
bodyDef1.userData = rect_sprite1;
body1 = (MyPhysicsBody*)world->CreateBody(&bodyDef1);
body1->setTypeFlag(7);
// add the fixture definitions to the body
GB2ShapeCache *sc1 = GB2ShapeCache::sharedGB2ShapeCache();
sc1->addFixturesToBody(body1,"rect1", rect_sprite1);
rect_sprite1->setAnchorPoint(sc1->anchorPointForShape("rect1"));
b2BodyDef bodyDef2;
bodyDef2.type=b2_dynamicBody;
bodyDef2.position.Set((winSize.width*0.62)/PTM_RATIO,
(winSize.height*0.4)/PTM_RATIO);
bodyDef2.userData = rect_sprite2;
body2 = (MyPhysicsBody*)world->CreateBody(&bodyDef2);
body2->setTypeFlag(7);
// add the fixture definitions to the body
GB2ShapeCache *sc2 = GB2ShapeCache::sharedGB2ShapeCache();
sc2->addFixturesToBody(body2,"rect2", rect_sprite2);
rect_sprite2->setAnchorPoint(sc2->anchorPointForShape("rect2"));
b2BodyDef bodyDef3;
bodyDef3.type=b2_dynamicBody;
bodyDef3.position.Set((winSize.width*0.5)/PTM_RATIO, (winSize.height*0.23)/PTM_RATIO);
bodyDef3.userData = rect_sprite3;
body3 = (MyPhysicsBody*)world->CreateBody(&bodyDef3);
body3->setTypeFlag(7);
// add the fixture definitions to the body
GB2ShapeCache *sc3 = GB2ShapeCache::sharedGB2ShapeCache();
sc3->addFixturesToBody(body3,"circle", rect_sprite3);
rect_sprite3->setAnchorPoint(sc3->anchorPointForShape("circle"));
}
void Level1::ccTouchesBegan(cocos2d::CCSet* touches, cocos2d::CCEvent* event)
{
if(box->containsPoint(touchPoint))
{
this->removeChild(((CCSprite*)rect),true);
if(((CCSprite*)rect)==rect_sprite1)
{
rect_sprite1=NULL;
world->DestroyBody(body1);
Utils::setCount(Utils::getCount()-1);
}
if(((CCSprite*)rect)==rect_sprite2)
{
rect_sprite2=NULL;
world->DestroyBody(body2);
Utils::setCount(Utils::getCount()-1);
}
if(((CCSprite*)rect)==rect_sprite3)
{
rect_sprite3=NULL;
world->DestroyBody(body3);
Utils::setCount(Utils::getCount()-1);
}
}
同样地,我也在为其他级别做准备。
如果有人知道,请提出建议。谢谢这似乎更像是“我应该使用什么设计模式?”而不是加载代码的特定问题
通常,当我想要创建需要物理实体的“实体”时,我会使用包含Box2D实体作为其成员之一的基类。基类是实体(已分配给它)的容器,负责在实体被销毁时销毁实体(将其从Box2D世界中删除)
派生类可以从Box2D形状缓存加载主体。最好通过一个例子来说明这一点。我正在做一个游戏,游戏中有一群形状各异的小行星围绕太阳旋转。以下是屏幕截图:
基类Entity包含实体,并在实体被销毁时将其销毁:
class Entity : public HasFlags
{
public:
enum
{
DEFAULT_ENTITY_ID = -1,
};
private:
uint32 _ID;
// Every entity has one "main" body which it
// controls in some way. Or not.
b2Body* _body;
// Every entity has a scale size from 1 to 100.
// This maps on to the meters size of 0.1 to 10
// in the physics engine.
uint32 _scale;
protected:
void SetScale(uint32 value)
{
assert(value >= 1);
assert(value <= 100);
_scale = value;
}
public:
void SetBody(b2Body* body)
{
assert(_body == NULL);
if(_body != NULL)
{
CCLOG("BODY SHOULD BE NULL BEFORE ASSIGNING");
_body->GetWorld()->DestroyBody(_body);
_body = NULL;
}
_body = body;
if(body != NULL)
{
_body->SetUserData(this);
for (b2Fixture* f = _body->GetFixtureList(); f; f = f->GetNext())
{
f->SetUserData(this);
}
}
}
inline void SetID(uint32 ID)
{
_ID = ID;
}
inline uint32 GetID() const
{
return _ID;
}
virtual string ToString(bool updateDescription = false)
{
string descr = "ID: ";
descr += _ID;
descr += "Flags: ";
if(IsFlagSet(HF_IS_GRAPH_SENSOR))
descr += "IS_FLAG_SENSOR ";
return descr;
}
Entity() :
_ID(DEFAULT_ENTITY_ID),
_body(NULL),
_scale(1)
{
}
Entity(uint32 flags, uint32 scale) :
HasFlags(flags),
_ID(DEFAULT_ENTITY_ID),
_body(NULL),
_scale(scale)
{
}
virtual void Update()
{
}
virtual void UpdateDisplay()
{
}
virtual ~Entity()
{
if(_body != NULL)
{
_body->GetWorld()->DestroyBody(_body);
}
}
inline static float32 ScaleToMeters(uint32 scale)
{
return 0.1*scale;
}
inline Body* GetBody()
{
return _body;
}
inline const Body* GetBody() const
{
return _body;
}
inline uint32 GetScale()
{
return _scale;
}
inline float32 GetSizeMeters()
{
return ScaleToMeters(_scale);
}
};
类实体:公共标志
{
公众:
枚举
{
默认的实体ID=-1,
};
私人:
uint32_ID;
//每个实体都有一个“主体”,它可以
//以某种方式控制。或者不控制。
b2Body*_body;
//每个实体的比例大小为1到100。
//这将映射到0.1到10的米大小
//在物理引擎中。
uint32_标度;
受保护的:
无效设置刻度(uint32值)
{
断言(值>=1);
断言(值GetWorld()->DestroyBody(_body);
_body=NULL;
}
_身体=身体;
if(body!=NULL)
{
_body->SetUserData(此);
对于(b2Fixture*f=_body->GetFixtureList();f;f=f->GetNext())
{
f->SetUserData(本文件);
}
}
}
内联无效集合ID(uint32 ID)
{
_ID=ID;
}
内联uint32 GetID()常量
{
返回_ID;
}
虚拟字符串到字符串(bool updateDescription=false)
{
字符串descr=“ID:”;
descr+=\u ID;
descr+=“标志:”;
if(IsFlagSet(高频是图形传感器))
descr+=“IS_标志_传感器”;
返回描述;
}
实体():
_ID(默认实体ID),
_正文(空),
_比额表(1)
{
}
实体(uint32标志、uint32比例):
有旗(旗),,
_ID(默认实体ID),
_正文(空),
_比例尺(比例尺)
{
}
虚拟空间更新()
{
}
虚拟void UpdateDisplay()
{
}
虚拟实体()
{
如果(_body!=NULL)
{
_body->GetWorld()->DestroyBody(_body);
}
}
内联静态浮式32标度计(uint32标度)
{
返回0.1*刻度;
}
内联Body*GetBody()
{
返回体;
}
内联常量Body*GetBody()常量
{
返回体;
}
内联uint32 GetScale()
{
返回量表;
}
内联float32 GetSizeMeters()
{
返回标度计(_标度);
}
};
小行星类本身负责从形状缓存加载几个不同的“小行星”形状中的一个。但是,所有小行星都有使其在屏幕中心移动的共同逻辑。它们连接了一个绳接头,更新(…)功能为其添加了一些“旋转”,以便它们围绕中心旋转:
class Asteroid : public Entity
{
private:
b2Fixture* _hull;
Vec2 _anchor;
CCSprite* _sprite;
float32 _targetRadius;
public:
// Some getters to help us out.
b2Fixture& GetHullFixture() const { return *_hull; }
float32 GetTargetRadius() { return _targetRadius; }
CCSprite* GetSprite() { return _sprite; }
void UpdateDisplay()
{
// Update the sprite position and orientation.
CCPoint pixel = Viewport::Instance().Convert(GetBody()->GetPosition());
_sprite->setPosition(pixel);
_sprite->setRotation(-CC_RADIANS_TO_DEGREES(GetBody()->GetAngle()));
}
virtual void Update()
{
Body* body = GetBody();
Vec2 vRadius = body->GetPosition();
Vec2 vTangent = vRadius.Skew();
vTangent.Normalize();
vRadius.Normalize();
// If it is not moving...give it some spin.
if(fabs(vTangent.Dot(body->GetLinearVelocity())) < 1)
{
body->SetLinearDamping(0.001);
body->ApplyForceToCenter(body->GetMass()*1.5*vTangent);
body->ApplyForce(vRadius,body->GetMass()*0.05*vRadius);
}
else
{
body->SetLinearDamping(0.05);
}
}
~Asteroid()
{
}
Asteroid() :
Entity(HF_CAN_MOVE | HF_UPDATE_PRIO_5,50)
{
}
bool Create(b2World& world, const string& shapeName,const Vec2& position, float32 targetRadius)
{
_targetRadius = targetRadius;
_anchor = position;
string str = shapeName;
str += ".png";
_sprite = CCSprite::createWithSpriteFrameName(str.c_str());
_sprite->setTag((int)this);
_sprite->setAnchorPoint(ccp(0.5,0.5));
// _sprite->setVisible(false);
b2BodyDef bodyDef;
bodyDef.position = position;
bodyDef.type = b2_dynamicBody;
Body* body = world.CreateBody(&bodyDef);
assert(body != NULL);
// Add the polygons to the body.
Box2DShapeCache::instance().addFixturesToBody(body, shapeName, GetSizeMeters());
SetBody(body);
return true;
}
};
class小行星:公共实体
{
私人:
B2U船体;
Vec2锚;
CCSprite*_sprite;
浮动32 _targetRadius;
公众:
//有人来帮我们。
b2Fixture&GetHullFixture()常量{return*\u hull;}
float32 getargetradius(){return\u targetRadius;}
CCSprite*GetSprite(){return\u sprite;}
void UpdateDisplay()
{
//更新精灵的位置和方向。
CCPoint pixel=Viewport::Instance().Convert(GetBody()->GetPosition());
_精灵->设置位置(像素);
_精灵->设置旋转(-CC_弧度到_度(GetBody()->GetAngle());
}
虚拟空间更新()
{
Body*Body=GetBody();
Vec2 vRadius=body->GetPosition();
Vec2 vTangent=vRadius.Skew();
vTangent.Normalize();
vRadius.Normalize();
//如果它不动了…让它旋转一下。
if(fabs(vTangent.Dot(body->GetLinearVelocity())<1)
{
阀体->设置线性阻尼(0.001);
body->ApplyForceToCenter(body->GetMass()*1.5*vTangent);
body->ApplyForce(vRadius,body->GetMass()*0.05*vRadius);
}
其他的
{
车身->设置线性阻尼(0.05);
}
}
~小行星()
{
}
小行星()
实体(HF_可以_移动| HF_更新_优先级5,50)
{
}
bool Create(b2World和world、常量字符串和shapeName、常量向量2和位置、float32 targetRadius)
{
_targetRadius=targetRadius;
_锚=位置;
字符串str=shapeName;
str+=“.png”;
_sprite=CCSprite::createWithPriteFrameName(str.c_str());
_sprite->setTag((int)this);
_sprite->Setancorpoint(ccp(0.5,0.5));
//_sprite->setVisible(假);
b2BodyDef-bodyDef;
bodyDef.position=位置;
bodyDef.type=b2_dynamicBody;
Body*Body=world.CreateBody(&bodyDef);
断言(body!=NULL);
//将多边形添加到bod