书名:代码本色:用编程模拟自然系统
作者:Daniel Shiffman
译者:周晗彬
ISBN:978-7-115-36947-5
目录
5.6 三要素:物体、形状和夹具
其实Box2D中的物体并不是直接存在于世界中,它就像脱离肉体的灵魂。对于一个有质量的物体,我们必须再定义一个形状,通过夹具将这个形状连接在物体上。
Box2D中形状类的主要职责就是管理与碰撞相关的几何结构,除此之外,你还可以通过它设置一些与运动相关的属性,比如设置决定物体质量的密度属性。形状还有摩擦性和复原性(“弹力”),这两个属性可以通过夹具设置。
Box2D区分了物体和形状的概念,并将它们独立地放在两个对象中,这是一个很不错的设计,如此一来,用户就可以将多个形状连接到同一个物体上。在后面的例子中,我们将看到这种用法。
为了创建一个形状,我们需要先确定形状的类型。多边形对象适用于大部分非圆形的情形。
举个例子,让我们来看看矩形的定义方法。
第1步:定义形状
PolygonShape ps = new PolygonShape(); 定义形状:一个多边形
下面,我们要设定矩形的宽度和高度。
假如本例要创建150像素×100像素的矩形,请记住:像素单位不能用于Box2D的形状设定!必须先用辅助函数转换这个单位。
float box2Dw = box2d.scalarPixelsToWorld(150); 将像素尺寸转化为Box2D尺寸
float box2Dh = box2d.scalarPixelsToWorld(100);
ps.setAsBox(box2Dw, box2Dh); 用setAsBox()函数将形状定义为矩形
第2步:创建夹具
形状和物体是两个独立的实体,为了把形状加在物体上,我们需要创建一个夹具对象。夹具的创建方式和物体一样,要用夹具定义(FixtureDef类)创建,此外还要为夹具对象指定一个形状对象。
FixtureDef fd = new FixtureDef();
fd.shape = ps; 将刚刚创建的PolygonShape对象赋给夹具对象
一旦有了夹具定义对象,我们就可以为它连接的形状设置各种物理属性。
fd.friction = 0.3; 形状的摩擦系数,一般介于0~1;
fd.restitution = 0.5; 形状的复原性(也就是弹性):0~1;
fd.density = 1.0; 形状的密度,以kg/m<sup>2</sup>为单位
第3步:用夹具将形状连接到物体上
夹具被定义之后,剩下的事情就是调用createFixture()函数将形状连接到物体上。
body.createFixture(fd); 创建夹具,将形状加到物体对象上
如果你不需要设置物理属性,可以跳过第2步(Box2D会使用默认的物理属性),将创建夹具和连接形状这两个操作合并成一步。
body.createFixture(ps,1); 创建夹具,连接形状,将密度设为1
在大部分例子中,我们都是在物体创建时为它连接一个形状,但这并不是因为Box2D的限制,Box2D也允许我们在运行期创建和删除形状。
将上述代码放入Processing Sketch之前,先总结创建物体需要经过哪些步骤:
- 1.用BodyDef对象定义一个物体(设置一些属性,比如位置);
- 2.用定义对象创建物体对象;
- 3.用多边形类(PolygonShape)、圆形类(CircleShape)和其他形状类创建形状对象;
- 4.用FixtureDef定义一个夹具对象,为夹具对象指定形状对象(设置一些属性,比如摩擦系数、密度和复原性);
- 5.把形状连接到物体上。
BodyDef bd = new BodyDef(); 第1步:定义物体
bd.position.set(box2d.coordPixelsToWorld(width/2,height/2));
Body body = box2d.createBody(bd); 第2步:创建物体
PolygonShape ps = new PolygonShape(); 第3步:定义形状
float w = box2d.scalarPixelsToWorld(150);
float h = box2d.scalarPixelsToWorld(100);
ps.setAsBox(w, h);
FixtureDef fd = new FixtureDef(); 第5步:把形状连接到物体上
fd.shape = ps;
fd.density = 1;
fd.friction = 0.3;
fd.restitution = 0.5;
body.createFixture(fd);