P2的形状属性
P2所有形状都继承至Shape类,所以拥有一些共同属性,这些属性包含在Shape的构造函数中,具体如下:
function Shape(optins:{
position?:number[];
angle?:number;
collisionGroup?:number;
collisionMask?:number;
sensor?:boolean;
collisionResponse?:boolean;
type?:number;
material?:Material;
});
参数说明:
position:形状相对与刚体本地坐标中心的偏移量。这个偏移量会影响到刚体的重心位置
angle:形状在刚体本地坐标系统中倾斜的角度。
collisionGroup:碰撞分组,与接下来的collisionMask一起使用,限制当前形状只与指定条件的形状碰撞。
假设当前形状为si,要检测的形状为sj,那么collisionGroup 和collisionMask 属性实现形状之间的碰撞限制的原理,如以下代码:
if(!(
(si.collisionGroup & sj.collisionMask) !== 0 &&
(sj.collisionGroup & si.collisionMask) !== 0
)){
continue;
}
大致过程是这样的。首先进行形状si的collisionGroup 和形状sj的collisionMask属性按位与运算,再进行形状sj的collisionGroup和形状si的collisionMask属性按位与运算,如果两个结果都不为0,则忽略此次碰撞检测,即si和sj不会发生碰撞。
因为是按位运算,所以在设置collisionGroup和collisionMask时候,最好设置成2的倍数。
sensor:设置形状是否为感应区域,默认为false。如果设置为true,则该形状不参与碰撞模拟,只作为感应区域,不过此时会正常触发碰撞事件,但不会生成ContactEquation(关于ContactEquation的内容,请参考“碰撞处理一节”)。
collisionResponse:当与其他刚体发生碰撞时,当前形状是否进行碰撞模拟,默认为true,如果collisionResponse为false,则碰撞发生时,当前形状不进行碰撞模拟,会穿过碰撞刚体,效果与sensor类似。但此时依然会发生碰撞事件,同时生成ContactEquation。
type:刚体类型,取值范围是Shape.CIRCLE 和 Shape.BOX等常量之一。我们不需要刻意设置此参数,子类形状会自动设置。
material:形状材质,1个Material对象。用来设置形状发生碰撞时,所表现出的相应特性,这些特性包括摩擦力、弹性系数等。
实际上,Material类中并不包含摩擦力、弹性系数等属性,它只是1个标识类,只是1个ID,而真正实现碰撞相应特性的是ContactMaterial类。
ContactMaterial类
ContactMaterial类,用来为添加了materialA和materialB标识的两个形状设置独特的碰撞相应特性。其构造函数如下:
function ContactMaterial(
materialA:Material,
materialB:Material,
options?:{
friction:number;
restitution:number;
stiffness:number;
relaxation:number;
frictionStuffness:number;
frictionRelaxation:number;
surfaceVelocity:number;
}
)
参数说明如下:
materialA:形状ShapeA的材质标识。
materialA:形状ShapeB的材质标识。
options:两个形状发生碰撞时候,相应特性的设置,具体如下:
friction:两个形状接触面的摩擦系数,默认值=0.3。该属性值越大,摩擦系数越大
restitution:两个形状碰撞时候的弹性系数,默认值=0.该值越大,弹性系数越大。数值过大的时候,会崩溃,例如=10的时候就会崩溃
stiffness:等同于ContactEquation的stiffness属性。指碰撞形状的表面硬度,这是1个大于0的数值,默认100000.当 stiffness 取值较小的时候,形状之间可以形成重叠,以及1个排斥力,促使形状分离,形成类似海绵、水面等有弹性的表面。
relaxation:等同于ContactEquation的relaxation属性。指当形状之间发生重叠后,在1次碰撞模拟计算过程中,实施排斥力的次数。可以想象成形状之间的粘稠度。取值较大,形状粘稠度较大,刚体速度衰减得越快。
surfaceVelocity:当两个刚体接触时候,接触面方向上两个刚体的相对速度。如果其中1个刚体为静态刚体,则 surfaceVelocity 表示另外1个刚体的速度,这种情况经常用来模拟传送带效果。
ContactMaterial的用法,不难,首先声明2个Material对象:MaterialA 和 MaterialB ,并分别设置两个不同形状的 Material 属性,然后以 MaterialA 和 MaterialB 为参数,创建1个ContactMaterial对象,最后通过 addContactMaterial方法,将其添加到world世界中去。
具体代码示例如下: