天天看點

(四)cocos2d -關節的使用(繩子)使用方式 (繩子為例)

cocos2d 中有很多中關節類,關節是為了讓兩個獨立物體之間建立某種聯系,使之猶如一體

常見的關節類有:

PhysicsJointXXX

含義 舉例說明
PhysicsJointDistance 設定兩個剛體間的固定距離
PhysicsJointFixed 将兩個剛體結合在了一起
PhysicsJointGear 使一對剛提的角速度比率保持一定比例 比如齒輪
PhysicsJointGroove 一個剛體連到線上,另一個連到點上
PhysicsJointLimit 限制兩個剛體間的最大距離 比如流星錘
PhysicsJointMotor 兩個剛體的相對角速度保持一個常數
PhysicsJointPin 兩個剛體獨立的圍繞錨點進行旋轉
PhysicsJointRatchet 與套筒扳手的工作類似,單向旋轉,不能轉回來,比如自行車的飛輪,正想踏實有動力的,反向是沒有動力的
PhysicsJointRotoryLimit 與限制關節類似,增加了自旋 地球繞太陽運動(地球同時在自旋))
PhysicsJointRotarySpring 與彈簧關節相似,增加自旋 汽車的懸挂系統
PhysicsJointSpring 永泰黃來連接配接兩個實體剛體

使用方式 (繩子為例)

使用 PhysicsJointDistance 将多個節點連接配接起來,實作繩子下落擺動的效果

基本步驟:

  1. 固定一個端點,并且設定body
  2. 循環增加節點,将節點addChild() 添加到場景中
  3. 相鄰選兩個節點建立一個關節 PhysicsJointDistance::cons
  4. 将關節 添加到PhysicsWorld對象 中

demo代碼片段:

#include "HelloWorldScene.h"
#include "cocostudio/CocoStudio.h"
#include "ui/CocosGUI.h"

USING_NS_CC;

using namespace cocostudio::timeline;
#define PHYSICS_MATERIAL1  PhysicsMaterial(1,1,0)
#define PHYSICS_MATERIAL2  PhysicsMaterial(1,0,0)
PhysicsWorld * world;
Scene* HelloWorld::createScene()
{
    // 'scene' is an autorelease object
    //auto scene = Scene::create();
	// 建立帶實體特性的世界
	auto  scene = Scene::createWithPhysics();
	world = scene->getPhysicsWorld();
	scene->getPhysicsWorld()->setGravity(Vec2(0, -980));
	//scene->getPhysicsWorld()->setAutoStep(false);
	//PhysicsWorld::DEBUGDRAW_JOINT
	//scene->getPhysicsWorld()->setDebugDrawMask(PhysicsWorld::DEBUGDRAW_ALL);
    // 'layer' is an autorelease object
    auto layer = HelloWorld::create();


    // add layer as a child to scene
    scene->addChild(layer);

    // return the scene
    return scene;
}

// on "init" you need to initialize your instance
bool HelloWorld::init()
{
  
    // 1. super init first
    if ( !Layer::init() )
    {
        return false;
    }
    
   /* auto rootNode = CSLoader::createNode("MainScene.csb");
	
    addChild(rootNode);*/

	Size visibleSize = Director::getInstance()->getVisibleSize();
	Vec2 origin = Director::getInstance()->getVisibleOrigin();


	


	

        auto rootNode = CSLoader::createNode("MainScene.csb");
		Sprite * edgeBox = dynamic_cast<Sprite*>(rootNode->getChildByName("Default"));

		auto edgeBody = PhysicsBody::createEdgeBox(visibleSize, PHYSICS_MATERIAL1,3);
		edgeBody->setDynamic(false);
		edgeBox->setPhysicsBody(edgeBody);
		addChild(rootNode);

	      //   使用關節 實作繩子效果

		Sprite * nodes[10];
		PhysicsBody * bodys[10];
		PhysicsJointDistance * pjd[10];

		// 1. 固定第一個節點 

		nodes[0] = Sprite::create();
		Vec2 point(visibleSize.width / 2, 9* visibleSize.height /10);
		nodes[0]->setPosition(point);
		addChild(nodes[0]);
		bodys[0] = PhysicsBody::createCircle(20, PHYSICS_MATERIAL1);
		bodys[0]->setCategoryBitmask(0);
		bodys[0]->setDynamic(false);
		nodes[0]->setPhysicsBody(bodys[0]);
		
		for (int i = 1; i < 10; i++) {
			nodes[i] = Sprite::create("rope05HA.png");
			nodes[i]->setPosition(point.x+40*i,point.y);
			addChild(nodes[i]);
			bodys[i]= PhysicsBody::createCircle(20, PHYSICS_MATERIAL1);
			bodys[i]->setCategoryBitmask(0);
			nodes[i]->setPhysicsBody(bodys[i]);
			pjd[i - 1] = PhysicsJointDistance::construct(bodys[i - 1], bodys[i], Vec2(18,0), Vec2(-18, 0));
			world->addJoint(pjd[i - 1]);// 将關節加入世界
		}




		return true;
}

           

效果(這是失敗的效果):

(四)cocos2d -關節的使用(繩子)使用方式 (繩子為例)

解決:

出現問題是因為在設定關節時,設定前後兩個節點的關節作用錨點位置弄錯了,都弄到各自的中心去了

一個節點的尺寸是 40x18 的

A-B

中間的**-** 表示關節

我們想做的當然是A的末端與B的起端相連接配接,達到下面的效果

而錨點預設是在sprite 的中間,也就是(0.5,0.5) //這是按照尺寸的百分比來的

錨點位置坐标也可以小于0,也可以大于1,也就是說錨點可以不在sprite 内部

(四)cocos2d -關節的使用(繩子)使用方式 (繩子為例)
pjd[i - 1] = PhysicsJointDistance::construct(bodys[i - 1], bodys[i], Vec2(18,0), Vec2(-18, 0));
// 由于 每個節點的尺寸都是40*18 ,我們通過指定關節連接配接作用的相對于錨點的一個位置.建立連接配接
Vec2(18,0): 關節的第一個點作用于A節點的相對于錨點靠右18個像素的位置
Vec2(-18,0):關節的第二個點作用于B節點的相對于錨點靠左18個像素的位置
達到的效果大體是A節點的末端與B節點的起端相連接配接,這點可以指定
scene->getPhysicsWorld()->setDebugDrawMask(PhysicsWorld::DEBUGDRAW_ALL); 來觀察
           

開啟 scene->getPhysicsWorld()->setDebugDrawMask(PhysicsWorld::DEBUGDRAW_ALL);

效果:

(四)cocos2d -關節的使用(繩子)使用方式 (繩子為例)

如果把那個相對位置設定大一些,可能更加直覺,看出相鄰兩個節點的之間的關節作用位置(圖中綠色的點)

設定為30吧

(四)cocos2d -關節的使用(繩子)使用方式 (繩子為例)

成功的效果:

(四)cocos2d -關節的使用(繩子)使用方式 (繩子為例)

完整的資源以及代碼已上傳至github

https://github.com/TopForethought/cocos2dx/tree/master/關節繩子

後序會嘗試做一個帶有懸挂系統的越野車,哈哈!

蹦蹦救護車已上線

(四)cocos2d -關節的使用(繩子)使用方式 (繩子為例)

代碼資源:

https://github.com/TopForethought/cocos2dx/tree/master/關節-蹦蹦車

繼續閱讀