cocos2dx 以box2d做個小車test

在看了一些box2d 知識後,做了個小車的demo 

在HelloWorldScene.h中,我以一個矩形作爲車的主體,請看以下

    virtual bool init();  
    static cocos2d::CCScene* scene();
    CREATE_FUNC(HelloWorld);
	void update(float time);

	virtual void ccTouchesBegan(CCSet *pTouches, CCEvent *pEvent); //處理按下事件 
	virtual void ccTouchesMoved(CCSet *pTouches, CCEvent *pEvent); //處理按下並移動事件 
	virtual void ccTouchesEnded(CCSet *pTouches, CCEvent *pEvent); //處理鬆開事件 

	b2Body *ground;
	b2World *world;
	b2Body *m_car;
	b2Body *m_wheel1;
	b2Body *m_wheel2;
	b2WheelJoint* m_spring1;  //輪子鏈接
	b2WheelJoint* m_spring2;
	float32 m_hz;
	float32 m_zeta;
	float32 m_speed;
	b2Fixture *carbody;//車子主體
	b2Fixture *w1;//輪子材料
	b2Fixture *w2;//輪子材料
	b2MouseJoint *_mouseJoint;//鼠標鏈接
	bool flag;
在HelloWorldScene.cpp中的init()實現

	m_hz = 4.0f;
		m_zeta = 0.7f;
		m_speed = 50.0f;
        CC_BREAK_IF(! CCLayer::init());
		CCSize winsize=CCDirector::sharedDirector()->getWinSize();

		b2Vec2 vector=b2Vec2(0.0f,-10.0f);
		
		bool dosleep=true;

		world=new b2World(vector);

		world->SetAllowSleeping(dosleep);

		world->SetContinuousPhysics(true);

		b2BodyDef b2bodydef;

		b2bodydef.position.Set(0.0f,0.0f);

		ground=world->CreateBody(&b2bodydef);

		b2PolygonShape groundBox; 
		//buttom 
		groundBox.SetAsBox(winsize.width/PTM_RATIO, 0, b2Vec2(0, 0), 0); 
		ground->CreateFixture(&groundBox, 0); 
		// top
		groundBox.SetAsBox(winsize.width/PTM_RATIO, 0, b2Vec2(0, winsize.height/PTM_RATIO), 0);
		ground->CreateFixture(&groundBox, 0); 
		// left 
		groundBox.SetAsBox(0, winsize.height/PTM_RATIO, b2Vec2(0, 0), 0);
		ground->CreateFixture(&groundBox, 0);
		// right
		groundBox.SetAsBox(0, winsize.height/PTM_RATIO, b2Vec2(winsize.width/PTM_RATIO, 0), 0);
		ground->CreateFixture(&groundBox, 0); 

		flag=false;

		CCSprite *sprite=CCSprite::create("CloseNormal.png");
		this->addChild(sprite);

		CCSprite *sprite1=CCSprite::create("CloseNormal.png");
		this->addChild(sprite1);

		CCSprite *sprite2=CCSprite::create("rect.png");
		this->addChild(sprite2);

		b2PolygonShape chassis;
		chassis.SetAsBox(sprite2->getContentSize().width/PTM_RATIO/2, sprite2->getContentSize().height/PTM_RATIO/2); 

		b2CircleShape circle;
		circle.m_radius = 0.4f;

		b2BodyDef bd;
		bd.userData=sprite2;
		bd.type = b2_dynamicBody;
		bd.position.Set((winsize.width/2)/PTM_RATIO, (winsize.height/2)/PTM_RATIO);
		m_car = world->CreateBody(&bd);
		carbody=m_car->CreateFixture(&chassis, 1.0f);

		b2FixtureDef fd;
		fd.shape = &circle;
		fd.density = 1.0f;
		fd.friction = 0.9f;

		bd.position.Set((winsize.width/2+20)/PTM_RATIO, (winsize.height/2-sprite->getContentSize().height/2)/PTM_RATIO);
		bd.userData=sprite;
		m_wheel1 = world->CreateBody(&bd);
		w1=m_wheel1->CreateFixture(&fd);

		bd.position.Set((winsize.width/2-20)/PTM_RATIO, (winsize.height/2-sprite1->getContentSize().height/2)/PTM_RATIO);
		bd.userData=sprite1;
		m_wheel2 = world->CreateBody(&bd);
		w2=m_wheel2->CreateFixture(&fd);

		b2WheelJointDef jd;
		b2Vec2 axis(0.0f, 1.0f);

		jd.Initialize(m_car, m_wheel1, m_wheel1->GetPosition(), axis);
		jd.motorSpeed = 0.0f;
		jd.maxMotorTorque = 20.0f;
		jd.enableMotor = true;
		jd.frequencyHz = m_hz;
		jd.dampingRatio = m_zeta;
		m_spring1 = (b2WheelJoint*)world->CreateJoint(&jd);

		jd.Initialize(m_car, m_wheel2, m_wheel2->GetPosition(), axis);
		jd.motorSpeed = 0.0f;
		jd.maxMotorTorque = 10.0f;
		jd.enableMotor = false;
		jd.frequencyHz = m_hz;
		jd.dampingRatio = m_zeta;
		m_spring2 = (b2WheelJoint*)world->CreateJoint(&jd);

		this->scheduleUpdate();
		this->setTouchEnabled(true);
這樣子即可組成一個小車了

可我們要update函數,這樣纔可以實現車子不斷地更新位置,

	int velocityIterations = 8; //速度迭代,可以調整物體的運動
	int positionIterations = 1; //位置迭代,可以調整物體的位置,減少物體間的重疊。



	world->Step(time,velocityIterations,positionIterations);
	b2Body* node=world->GetBodyList();
	while(node->GetUserData()!=NULL){
		b2Body* b=node;
		node=node->GetNext();
		CCSprite *Sprite = (CCSprite*)b->GetUserData();
		Sprite->setPosition( ccp(b->GetPosition().x*PTM_RATIO,
			b->GetPosition().y*PTM_RATIO) );

		Sprite->setRotation( -1*CC_RADIANS_TO_DEGREES(b->GetAngle()) );
	}
在用到touch類的函數及爲實現小車的點擊拖移,及加一個鼠標節點。

如在void HelloWorld::ccTouchesBegan(CCSet *pTouches, CCEvent *pEvent)函數中實現

	//if (_mouseJoint != NULL)   return;    
	CCLOG("b");
	CCTouch *touch = (CCTouch*)pTouches->anyObject();   //使用CCSet的方法
	// 獲取點在視圖中的座標(左上角爲原點)
	CCPoint location = touch->getLocation(); 
	b2Vec2 p = b2Vec2(location.x/PTM_RATIO, location.y/PTM_RATIO); 

	CCLOG("c");
	if(carbody->TestPoint(p))    
	{   
		CCLOG("d");
		b2MouseJointDef md;     
		md.bodyA = ground;      
		md.bodyB = m_car;       
		md.target = p;                  //移動的目標
		md.collideConnected = true;    //設置碰撞鏈接   
		md.maxForce = 1000.0f * m_car->GetMass();  
		_mouseJoint = (b2MouseJoint *)world->CreateJoint(&md);  
		m_car->SetAwake(true);     
		flag = true;  
	}   
	if (w1->TestPoint(p))   
	{ 
		CCLOG("e");
		b2MouseJointDef md;     
		md.bodyA = ground;         
		md.bodyB = m_wheel1;      
		md.target = p;             //移動的目標
		md.collideConnected = true;//設置碰撞鏈接
		md.maxForce = 1000.0f * m_wheel1->GetMass();   
		_mouseJoint = (b2MouseJoint *)world->CreateJoint(&md);      
		m_wheel1->SetAwake(true);    
		flag = true;  
	}
	if (w2->TestPoint(p))   
	{ 
		CCLOG("e");
		b2MouseJointDef md;     
		md.bodyA = ground;         
		md.bodyB = m_wheel2;      
		md.target = p;             //移動的目標
		md.collideConnected = true;//設置碰撞鏈接
		md.maxForce = 1000.0f * m_wheel2->GetMass();   
		_mouseJoint = (b2MouseJoint *)world->CreateJoint(&md);      
		m_wheel2->SetAwake(true);    
		flag = true;  
	}
void HelloWorld::ccTouchesMoved(CCSet *pTouches, CCEvent *pEvent)中設置位置座標

	if (_mouseJoint == NULL || flag == false)   return;    
	CCTouch *touch = (CCTouch*)pTouches->anyObject(); //使用CCSet的方法
	// 獲取點在視圖中的座標(左上角爲原點)
	CCPoint location = touch->getLocation(); 
	b2Vec2 locationWorld = b2Vec2(location.x/PTM_RATIO, location.y/PTM_RATIO);   
	_mouseJoint->SetTarget(locationWorld); 

void HelloWorld::ccTouchesEnded(CCSet *pTouches, CCEvent *pEvent) 

	if(_mouseJoint != NULL && flag == true)  
	{     
		world->DestroyJoint(_mouseJoint);     
		_mouseJoint = NULL;    
	} 



box2d 中demo下載 點擊打開鏈接

發佈了53 篇原創文章 · 獲贊 4 · 訪問量 12萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章