Farseer Physics Engine Manual 2.1中文

image

 

Farseer Physics Engine Manual

先知物理引擎教程

翻译:k    e-mailbox: kevin-ss30@163.com

下载:http://files.cnblogs.com/kevinss30/%5B%E7%BF%BB%E8%AF%91%5DFarseer%E6%8C%87%E5%8D%97.pdf 

支持Microsoft's XNA, Silverlight, WPF, and Vanilla .NET

 

关键词:

spin旋转 torque力矩 body物体 collision碰撞 polygon多边形 convex凸

concave凹 vertice顶点 impulse冲量 mass规模 moment of inertia转动惯量

overload重载 geometry几何体 counter clockwise逆时针方向

joint 关节 anchor 固定点 contact point接触点 revolute joint转动关节

angle joint角接关节 pin joint销接关节 slide joint滑动关节 arbiter判决器

 

 

 

1. Body

手动建立一个简单的body

int mass = 1;

float width = 128;

float height = 128;

Body rectBody = new Body();

rectBody.Mass = mass;

rectBody.MomentOfInertia = mass * (width * width + height * height) / 12;

rectBody.Position = new Vector2(100, 200);

MOI转动惯量使用这个公式 image

使用Body Factory可以让Farseer替你计算MOI。所有的position定义都是基于图形的中心。同样,向屏幕绘制一个Body也是相对于屏幕中心

image

 

1.1. Body Factory(BF)

可以这样使用factory来建立body :

Body rectBody = BodyFactory.Instance.CreateRectangleBody(PhysicsSimulator, 128, 128, 1);

这个body宽度128,高度128,群数为1。

可以使用factory来建立矩形,圆形,多边形和Body形(当你不想使用Farseer计算MOI时仍然可以使用factory来建立clones of bodies)的body

Body Factory有两种重载,其中一种会使用PhysicsSimulator对象,如果使用这种重载方法,建立的body将会加入simulator

2. Geometry(在Farseer中简写为Geom)

几何体geom是碰撞检测的核心。一个geom需要一个body和一些顶点(顺序为逆时针方向)来定义形状的边缘。

手动建立一个简单的geometry

Body rectBody = BodyFactory.Instance.CreateRectangleBody(128, 128, 1);

Vertices vertices = new Vertices();

vertices.Add(new Vector2(-64, -64));

vertices.Add(new Vector2(64, -64));

vertices.Add(new Vector2(64, 64));

vertices.Add(new Vector2(-64, 64));

Geom rectGeom = new Geom(rectBody, vertices, 11);

将建立一个矩形body其中一系列顶点表示出矩形的轮廓(相对于(0,0)点),还有一个新的geometry。在Geom构造函数中的11是表示网格单元尺寸的参数。

2.1.Geometry Factory(GF)

可以使Geometry Factory来更方便的建立geometry。Geometry Factory可以为简单图形如矩形和圆形建立一个顶点集,只需要定义矩形的宽和高或者圆形的半径。

Body rectBody = BodyFactory.Instance.CreateRectangleBody(128, 64, 1);

Geom rectGeom = GeomFactory.Instance.CreateRectangleGeom(PhysicsSimulator, rectBody, 128, 64);

注意你并没有提供任何顶点或者网格单元尺寸grid cell size,Geometry Factory已经替你指定了。

当你想使用GF控制网格单元尺寸时,可以使用下面的重载方法

Geom rectGeom = GeomFactory.Instance.CreateRectangleGeom(PhysicsSimulator, rectBody, 128, 64, 6.4f);

这样就得到了网格单元尺寸为6.4的body

如果在网格单元尺寸的位置输入0,系统将会主动计算。计算方法是找到几何体的最短边,乘以0.1,就得到了6.4。

你可以通过设置在GF对象中的GridCellSizeAABBFactor来调整默认网格单元尺寸

3. Physics Simulator View(PSV)

PSV用来调试关节、body位置、几何体队列和碰撞。当被激活时,可以发现关节、碰撞、接触点、中心、AABB(见下文)和其他信息在使用Farseer解决相关问题时是必要的。

PSV目前只支持XNA。

image

说明:

debug view有多种配置结构:

1)性能面板

a.显示关于引擎时间,当前body数目,几何体,关节,弹簧,控制器,判决器的信息;

b.清理时间Clean up:在上一次的更新update中加入与移除单位的时间

c.宽阶段检测时间Broad Phase Collision(两步检测法第一步。两步检测法即先使用宽阶段检测即大范围的检测确定是否有碰撞可能,如果可能碰撞再使用窄阶段检测即小范围物体模型碰撞检测确定是否碰撞。这种方法可以在保持精度的同时有效降低碰撞检测的计算量—译者注

 image

d.窄阶段检测时间Narrow Phase Collision

e.施加力时间Apply Forces:对于弹簧,body和控制器施加力的时间

f.冲量时间Apply Impulses:对于关节和判决器施加冲量的时间

g.更新位置时间Update Position:更新所有body位置的时间

2)顶点Vertices:

a.显示构成几何体的顶点,用黑色像素点表示。

3)AABB:

a.显示轴对齐边界框Axis Aligned Bounding Box

4)接触点Contacts:

a.显示接触的顶点,用红色像素点表示。

5)坐标轴Coordinate Axis:

a.显示body的中心,用黑色十字表示。

6)网格Grid:

a.显示用于检测窄阶段检测的几何体之间的距离网格。因为一个网格可以由很多的点,所以这个选项可能会大大降低绘制图形的速度(在上图中没有开启)。

7)边界Edge:

a.显示几何体边界的轮廓,用黑色的边界表示。

8)关节Joints:

a.转动、滑动、销接关节可见。

9)弹簧Springs:

a.线性弹簧(包括固定的和普通的)使用两个终点和一条黑线来表示,线上有三个圆来表示弹簧的压缩与伸展。

4. Joints

Farseer现在具有转动关节*,角接关节*,限角关节*,销接关节和滑动关节,使用这些组合几乎可以做到任何动态行为。

*表示有改进版本,改进版本的关节是固定在全局中,而不是其他body上。

共享的变量:

a.Enabled

b.IsDisposed—joint是否被释放

c.JointError—得到joint的误差。注意不是所有的joint都能产生误差。

d.BreakPoint—定义joint误差允许的最大值,超过后joint就会断开。默认为浮点数最大,即不可损坏。

e.Softness—joint的柔性从0.0f到1.0f。注意即使定义为0.0f,有些joint仍然具有一定的柔性。

f.BiasFactor—joint的偏差系数。指对于joint误差进行修正的强度, 从0.0f到1.0f,默认为0.2f。注意对这个参数设置过大或过小会使物理系统不稳定,所以要小幅度的修改。

g.Broke—在joint断开后生效的句柄。你可以给它规定一个方法或者干脆什么都不发生。

h.Tag—标签,这个你可以随意取。

共享的方法:

a.Validate—判断是否所有相关的body都被释放,如果不是,则释放所有。

b.PreStep—只有你自己写joint时需要

c.Update—只在你自己写joint时需要

d.Dispose—释放joint

4.1. Revolute Joint

转动关节

这个类型的joint适合加入旋转或者将多个目标连在一起。这个joint需要一个全局向量,但是会按照内部的两个局部向量来储存joint的位置。这个joint的误差由两个局部向量的间距决定。

转动关节可以是body之间连接,也可以是body和固定式fixed types连接,当body之间连接时,body仍然可以线性移动,但是body与固定式连接时只能进行转动。

属性:

a.Body1—Get/Set第一个joint的body。这个属性在固定转动关节中叫Body。

b.Body2—Get/Set第二个joint的body。这个属性在固定转动关节中不存在。

c.Anchor—Get/Set joint的anchor。使用全局坐标。

d.CurrentAnchor—仿真开始后获得joint的全局位置。

e.SetInitialAnchor—仿真开始前设置joint的anchor

示例见Demo1

注:见http://www.farseergames.com/storage/farseerphysics/Manual2.1.htm

需要支持SilverLight,下同。

4.2. Angle Joint

角接关节

这个joint用来连接两个body的角度为相同的值。固定式角接关节会保持body在一个特定的角度。

属性:

a.TargetAngle—目标角度

b.MaxImpulse—最大力矩(英文名字是最大冲量,解释为最大力矩,可能是最大冲击力矩)。默认为浮点数最大值。

c.Body1

d.Body2

示例二

4.3. Angle Limited Joint

与Angle Limited相同,但是具有角度限制,并且没有冲击力矩。

属性:

a.LowerLimit—得到或设置最小的body角度,弧度制。

b.UpperLimit—得到或设置最大的body角度,弧度制。

c.Slop溢出—得到或设置允许的溢出值。

d.Body1

e.Body2

示例三

4.4. Pin Joint销接关节

这个关节可以称为棍型关节,作用是使两个body保持一定距离并且可以旋转。

属性:

a.TargetDistance—两个body的目标距离,如果未指定,则默认为两body的距离

b.Body1

c.Body2

d.Anchor1

e.Anchor2

f.WorldAnchor1

g.WorldAnchor2

示例四

4.5. Slider Joint滑动关节

与销接关节类似,但是有最大最小的距离限制,仍然可以旋转。

属性:

a.TargetDistance

b.Body1

c.Body2

d.Anchor1

e.Anchor2

f.WorldAnchor1

g.WorldAnchor2

h.Min

i.Max

j.Slop

4.7. Joint Factories(JF)

可以使用相同的参数批量产生joint。但是并不是所有的参数在JF里都可以设置。

Revolute Joint Factory

1. CreateRevoluteJoint(PhysicsSimulator physicsSimulator, Body body1, Body body2, Vector2 initialAnchorPosition)

2. CreateRevoluteJoint(Body body1, Body body2, Vector2 initialAnchorPosition)

Fixed Revolute Joint Factory

1. CreateFixedRevoluteJoint(PhysicsSimulator physicsSimulator, Body body, Vector2 anchor)

2. CreateFixedRevoluteJoint(Body body, Vector2 anchor)

Pin Joint Factory

1. CreatePinJoint(PhysicsSimulator physicsSimulator, Body body1, Vector2 anchor1, Body body2, Vector2 anchor2)

2. CreatePinJoint(Body body1, Vector2 anchor1, Body body2, Vector2 anchor2)

Slider Joint Factory

1. CreateSliderJoint(PhysicsSimulator physicsSimulator, Body body1, Vector2 anchor1, Body body2, Vector2 anchor2, float min, float max)

2. CreateSliderJoint(Body body1, Vector2 anchor1, Body body2, Vector2 anchor2, float min, float max)

Angle Joint Factory

1. CreateAngleJoint(PhysicsSimulator physicsSimulator, Body body1, Body body2)

2. CreateAngleJoint(Body body1, Body body2)

3. CreateAngleJoint(PhysicsSimulator physicsSimulator, Body body1, Body body2, float softness, float biasFactor)

4. CreateAngleJoint(Body body1, Body body2, float softness, float biasFactor)

Fixed Angle Joint Factory

1. CreateFixedAngleJoint(PhysicsSimulator physicsSimulator, Body body)

2. CreateFixedAngleJoint(Body body)

Angle Limit Joint Factory

1. CreateAngleLimitJoint (PhysicsSimulator physicsSimulator, Body body1, Body body2, float min, float max)

2. CreateAngleLimitJoint (Body body1, Body body2, float min, float max)

Fixed Angle Limit Joint Factory

1. CreateFixedAngleLimitJoint (PhysicsSimulator physicsSimulator, Body body, float min, float max)

2. CreateFixedAngleLimitJoint (Body body, float min, float max)

5. Springs弹簧

包括线性弹簧和角度弹簧,都有fixed版本。

注意:

1. 有些弹簧需要相对于body位置的anchor,有些则需要相对于全局位置的anchor。

2. 弹簧附着于body

3. 弹簧有共享的变量和方法。

4. 弹簧不一定要在body内部附着于几何体上。

5. 弹簧损坏后将失效。

开发者注意:

所有的弹簧都是从基类Spring产生出来的,所以如果你具备自己加入约束条件的能力请注意确认自己的弹簧也是基于Spring的(并且请和大家分享)。

共享的变量:

a. Enabled

b. IsDisposed

c. DampningConstant阻尼常数(实际为Dampening Constant)

d. SpringConstant弹簧常数

e. SpringError

f. BreakPoint

g. Broke

h. Tag

共享方法

a. Validate验证弹簧的body是否存在,不存在则释放弹簧资源。

b. Update

c. Dispose

5.1. Linear Spring线性弹簧

可以对body产生推力或拉力。

属性:

a. Body1

b. Body2

c. Anchor1

d.Anchor2

e.RestLength静止长度

示例五

5.2. 角度弹簧

属性:

a. Body1

b. Body2

c. Anchor1

d. Anchor2

e. TargetAngle预定角度,在这个角度弹簧不产生力,弧度制。

f. MaxTorgue定义尝试达到预定角度所可以达到的最大力矩。

g. TorgueMultiplier力矩的乘数因子,力矩将与这个数相乘,默认为1.0f。

示例六

5.3. Spring Factory

Linear Spring Factory

1. CreateLinearSpring(PhysicsSimulator physicsSimulator, Body body1, Vector2 anchor1, Body body2, Vector2 anchor2, float springConstant, float dampningConstant)

2. CreateLinearSpring(Body body1, Vector2 anchor1, Body body2, Vector2 anchor2, float springConstant, float dampningConstant)

Fixed Linear Spring Factory

1. CreateFixedLinearSpring(PhysicsSimulator physicsSimulator, Body body, Vector2 anchor1, Vector2 anchor2, float springConstant, float dampningConstant)

2. CreateFixedLinearSpring(Body body, Vector2 anchor1, Vector2 anchor2, float springConstant, float dampningConstant)

Angle Spring Factory

1. CreateAngleSpring(PhysicsSimulator physicsSimulator, Body body1, Body body2, float springConstant, float dampningConstant)

2. CreateAngleSpring(Body body1, Body body2, float springConstant, float dampningConstant)

Fixed Angle Spring Factory

1. CreateFixedAngleSpring(PhysicsSimulator physicsSimulator, Body body, float springConstant, float dampningConstant)

2. CreateFixedAngleSpring(Body body, float springConstant, float dampningConstant)

6. Collision Detection碰撞检测

Farseer物理引擎提供简便实用的碰撞系统,包括两个部分,每部分都有一个或多个算法。

1) Broad phase collision detection宽阶段碰撞检测

a) AABB

2) Narrow phase collision detection窄阶段碰撞检测

a) Distance Grid

b) SAT(Separation of Axis Theorem)分离轴线理论

6.1. 宽阶段

我们现在有三种宽阶段碰撞检测算法:

1) Sweep And Prune(SAP)扫描并修剪(逐维递归分组法—译者注)

2) Selective Sweep选择性扫描

3) Brute Force暴力法

SAP是帧相关的,也就是说如果物体在屏幕上移动很多这个算法将会是糟糕的选择,而如果物体的位置接近于上一帧的位置,这个算法表现很好。更多关于SAP的信息请看:

http://en.wikipedia.org/wiki/Sweep_and_prune

http://www.ziggyware.com/readarticle.php?article_id=128 (叫sort and prune)

SS是Farseer默认的算法。SS最初以SAP为基础,但是有一些改进使得它表现比SAP更好。更多关于SS的信息请看:

http://www.codeplex.com/FarseerPhysics/Thread/View.aspx?ThreadId=17811

BF是这三个算法中最简单的,同时表现也是最差的,它迭代所有几何体并比较它们的AABB(见下文)。只对于少量的几何体速度较快。

6.2. AABB

AABB指Axis Aligned Bounding Box轴对齐包容盒子,简称包围盒,用来在宽阶段检测中快速测试两个几何体是否靠近或者接触,可以使用以下代码实现:

if (AABB.Intersect (_circleGeom.AABB,_rectangleGeom.AABB))

{

//The 2 AABB's intersect

}

当两个几何体的包围盒相交时,并不代表发生碰撞。

相交

image

相交并碰撞

image

6.3. 窄阶段

当宽阶段检测认为“发生碰撞”时,就使用窄阶段检测进行进一步的检查。

这里给出窄阶段发生事件的概述。

我们假设宽阶段给出包含在一个判决器Arbiter中的一对碰撞几何体。

1) 在第一个几何体上迭代所有全局顶点

2) 判断当前的vector是否与第二个几何体相交

a) 否:继续判断下一个vector

b) 是:建立一个接触点并将其插入接触点表

3) 对第二个几何体进行第一、二步骤

4) 如果接触点表里面有任一接触点,激活OnCollision事件

Arbiter类也用来计算当几何体碰撞时应该施加在它们上面的冲量。

6.4. Distance Grid间距网格

所有的几何体都包含一个Grid对象。一个间距网格是一个预先计算好的网格,其中每一个网格点包含到达最近点的间距和法向。(更多关于法向的信息请看物理Physics章节)

所有在几何体内部的网格点的间距都是无效的。grid与其point如下图:

image

一旦预先计算出间距网格,那么所有grid的point的间距和法向就都可以通过已知网格点的值计算出来。grid是当使用GeomFactory或由Geom constructor构造器提供的grid cell size网格单位尺寸来计算的。小的网格单位尺寸可以使网格更加精确,因此也会使得碰撞检测更加精确。

对于grid的计算是非常耗时的,所以预先计算好你的几何体模型并选择一个合适的网格单位尺寸是一个好主意。更多请看性能Performance章。

6.5. SAT

(注解:即Separating Axis Theorem,为一种可以快速检测不规则的凸多边形是否碰撞的算法:给出两个凸多边形体,如果我们能找到一个轴线,使两物体在此轴线上的投影不重叠,则这两个物体之间没有发生碰撞,这个轴线叫做Separating Axis(红色轴线)。

image 

image

对于2D的例子来说,可能存在的Separating Axis为垂直于多边形各个边的轴(红色轴线)

image

因此,如果我们要检查两多边形是否碰撞,就去检查两多边形在每个所有可能的轴上的投影是否重叠。

image

如果我们找到一个轴,使得两多边形在这个轴上的投影并不重叠,则我们可以知道两多边形没有碰撞发生。

image

以上关于SAT部分均引用自http://www.cnblogs.com/fireyang/archive/2006/11/17/563458.html—译者注)

 

SAT只支持凸多边形,但是性能比Distance Grid更好。需要作出如下改变:

a) 如果产生一个凹多边形,SAT将把它自动分解为一组凸多边形。

b) SAT使用两个顶点处理任何长度的边界。

注意:Vertices.CreateRectangle产生一个16个顶点的矩形,只有四个是需要的。使用Vertices.CreateSimpleRectangle来代替,可以只产生4个顶点。

c) SAT提供杰出的重叠多边形分离功能,反之,Distance Grid经常使多边形互相重叠并产生多余的碰撞。

d) SAT不需要预计算时间

e) SAT允许几何体动态的变化,也就是说,你可以即时的移动定义几何体的顶点。

使用SAT作为窄阶段检测的方法为:

PhysicsSimulator.NarrowPhaseCollider = new SAT(PhysicsSimulator);

6.6. Collision group and categories碰撞组与类别

Farseer提供一种新的产生不同碰撞组与更先进碰撞种类的方式。

默认情况下,所有的几何体都在collision group 0,就是说它们之间都可以发生碰撞。如果两个几何体在同一个碰撞组(除了collision group 0)中,则它们之间不会发生碰撞。

下面是对一个几何体设置碰撞组的方法:

Body rectBody = BodyFactory. Instance. CreateRectangleBody (PhysicsSimulator, 128, 128, 1);

rectBody. Position = new Vector2 (250, 400);

Geom rectGeom = GeomFactory. Instance. CreateRectangleGeom (PhysicsSimulator, rectBody, 128, 128);

rectGeom. CollisionGroup = 10;

Body circleBody = BodyFactory. Instance. CreateCircleBody (PhysicsSimulator, 64, 1);

circleBody. Position = new Vector2 (300, 400);

Geom circleGeom = GeomFactory. Instance. CreateCircleGeom (PhysicsSimulator, circleBody, 64, 20);

circleGeom. CollisionGroup = 10;

虽然rectGeom和circleGeom互相重叠,但是并不会发生碰撞。尽管碰撞组使用非常方便,但是限制很大,这就是为什么会有collision category碰撞类别。

以下是使用collision category的两个附加属性:

1) CollisionCategories

a) 默认为CollisionCategory.All

b) 用来定义几何体是哪一个类别的成员。

2) CollideWith

a) 默认为CollideCategory.All

b) 用来定义几何体与哪一类别可以发生碰撞。

碰撞类别使用一个枚举类型叫做CollisionCategory,它具有一个特殊的标志位处于激活状态,所以可以做到逐位运算。(更多请见

http://msdn.microsoft.com/en-us/library/system.flagsattribute.aspx

示例:

Body rectBody = BodyFactory.Instance.CreateRectangleBody(PhysicsSimulator, 128, 128, 1);

rectBody.Position = new Vector2(250, 400);

Geom rectGeom = GeomFactory.Instance.CreateRectangleGeom(PhysicsSimulator, rectBody, 128, 128);

rectGeom.CollisionCategory = CollisionCategories.Cat5;

rectGeom.CollidesWith = CollisionCategories.All & ~CollisionCategories.Cat4;

Body circleBody = BodyFactory.Instance.CreateCircleBody(PhysicsSimulator, 64, 1);

circleBody.Position = new Vector2(300, 400);

Geom circleGeom = GeomFactory.Instance.CreateCircleGeom(PhysicsSimulator, circleBody, 64, 20);

circleGeom.CollisionCategory = CollisionCategories.Cat4;

circleGeom.CollidesWith = CollisionCategories.All & ~CollisionCategories.Cat5;

其中,|表示或,&表示与,~表示非。

rectGeom为Cat5的成员,会与除了Cat4以外所有的物体发生碰撞。

circleGeom为Cat4的成员,会与除了Cat5以外所有的物体发生碰撞。

也就是说两者不会发生碰撞。

6.7. Collision Events

有三种不同的碰撞事件:

1. OnCollision(in Geom class)

2. OnSeparation(in Geom class)

3. OnBroadPhaseCollision(in BroadPhaseCollider interface)

OnCollision事件在一个几何体接触另一个几何体后激活,你需要返回一个布尔值来指示碰撞是否要发生。

OnSeparation事件在碰撞发生之后分离时被激活。

OnBroadPhaseCollision事件与OnCollision事件相似,但是在宽阶段检测时就已经被激活。取消这个事件将不会产生判决器arbiter,也就是对于涉及的几何体将不会施加冲量,也不会发生窄阶段检测。

使用这些事件的方法:

Body circleBody = BodyFactory. Instance. CreateCircleBody (PhysicsSimulator, 64, 1);

Geom circleGeom = GeomFactory. Instance. CreateCircleGeom (PhysicsSimulator, circleBody, 64, 20);

circleGeom.OnSeparation += OnSeperation;

circleGeom.OnCollision += OnCollision;

PhysicsSimulator.BroadPhaseCollider.OnBroadPhaseCollision+= OnBroadPhaseCollision;

注意OnBroadPhaseCollision事件在PhysicsSimulator中的BroadPhaseCollider中使用。

当事件激活时,方法是这样运行的

private bool OnCollision(Geom geom1, Geom geom2, ContactList contactList)

{

return true;

}

private void OnSeperation(Geom geom1, Geom geom2)

{

}

private bool OnBroadPhaseCollision(Geom geom1, Geom geom2)

{

return true;

}

7. Impulse冲量

对于冲量有两个系统:

1. Collision response

2. Manual impulses

collision response是当2个几何体碰撞时发生什么。在“Narrow Phase”章中描述的Arbiter类负责当碰撞发生时冲量的计算。

如果我们更加深入一些,实际上发生的是在窄阶段检测计算出的接触点获得一个冲量,这样几何体表现得像在真实的物理环境中。

collision response可以通过设置几何体的CollisionResponseEnabled属性为false使其失效。如:

Geom circleGeom = GeomFactory.Instance.CreateCircleGeom(PhysicsSimulator, circleBody, 64, 20);

circleGeom.CollisionResponseEnabled = false;

禁止collision response意味着将跳过其他所有几何体,但是仍然会激活碰撞事件。

你也可以对一个body使用手动冲量manual impulses。(记住是body控制动作而几何体控制碰撞,但是arbiter控制与碰撞相关的几何体冲量)你可以对一个body使用三种力或者冲量:

1)Force

a. ApplyForce

b. ApplyForceAtLocalPoint

c. ApplyForceAtWorldPoint

d. ClearForce

2)Impulse

a. ApplyImpulse

b. ClearImpulse

c. ApplyAngularImpulse

3)Torgue

a. ApplyTorgue

b. ClearTorgue

力Force用来使body加速。可以对物体整体或一个点施加力。你可以使用这个方法来对你的角色增加一个喷气背包,它的速度将随时间增加。

冲量Impulse用来对body施加冲量。冲量用来改变物体的速度而不是像力一样改变物体的加速度。你可以使用冲量来使你的游戏角色跳跃。跳跃是瞬时的变化,而不是加速。

力矩Torgue用来对body施加力矩(旋转)。你可以使轮子旋转或者岩石滚上山坡。

8. Physics Properties物理属性

Farseer具有强大的用于改变body和几何体物理属性的接口。大部分属性在物理引擎工作时可以即时更改,这给了我们创造完美动态效果的机会。

物理属性:

Body中的类:

AngularVelocity:角速度,单位为弧度/秒。

LinearVelocity:线速度,这是一个向量,不仅有速率,还包括方向。

LinearDragCoefficient:线性阻力系数。表示在流体或气体中拖曳物体时的阻力大小。在Farseer中我们没有body可以移入的介质(medium),所以我们必须手动设置body的阻力系数。

RotationDragCoefficient:转动阻力系数。此系数为0时,body可以一直旋转下去。

Moment of Inertia(MOI):转动惯量。为标量,表示物体绕其质心旋转的困难程度。

Geom中的类:

RestitutionCoefficient:恢复系数。为撞击之前与之后的速度之比,如果设为1,下落到地面的小球会速率不变向相反的方向运动,设为0则不会弹起。

FrictionCoefficient:摩擦系数。摩擦力就是阻止两物体接触的表面产生相对运动的力。Farseer具有两种控制摩擦力的方式,你可以使用PhysicsSimulator中的FrictionType来设定其中的一种:

a. Average平均:两个发生摩擦的几何体表面摩擦系数取平均,比如5和3就取4.

b. Minimum最小:取最小值。比如摩擦系数5和3,取3。

9. 水面模拟

Farseer具有实现流体动态效果和计算波浪的方法。叫FluidDragController的控制器负责计算流体动态效果,WaveController计算波浪的形状。

流体系统包括四个部分:

1) FluidDragController流体阻力控制器

你可以简单的创造一个FluidDragController的实例,对其进行初始化并把它加入物理引擎。FluidDragController需要设置它的大小,这个可以使用IFluidContainer接口,将在下文中介绍。

2) WaveController波浪控制器

这个类可以使用数学算法创造出逼真的波浪。WaveController看起来是一个矩形,但是它的上部变为由一组顶点定义的多边形。在算法处理时,这些顶点中的任何一个在y轴引起的干扰,将会引起其他点的波动。

包括WaveGeneratorMax,WaveGeneratorMin和WaveGeneratorStep.

3) IFluidContainer流体容器

就是一个简单的定义FluidDragController边界的接口。

4) AABBFluidContainer包围盒流体容器

使用包围盒来确定几何体是否在流体容器内部。

10. Extensions to Farseer(Farseer扩展)

从Farseer物理引擎2.0版本开始,我们加入了一些方法来帮助处理相同的操作。这些扩展只是一些高等函数,并不会改变物理引擎的表现。

10.1. Texture to vertices

在Farseer物理引擎2.0中,我们对于分离的多边形使用一种算法,来查找一个无符号整型数组(uint[] array)然后映射它们的位置。这使得人们可以更加简单的使用自制的纹理。使用texture to vertices算法,你只需按照下面来做:

//载入将要绘制body的纹理

Texture2D polygonTexture = ScreenManager.ContentManager.Load<Texture2D>("Content/Texture");

//建立一个数组来保存纹理的数据

uint[] data = new uint[polygonTexture.Width * polygonTexture.Height];

//将纹理数据转移到数组

polygonTexture.GetData(data);

//由数组计算顶点

Vertices verts = Vertices.CreatePolygon(data, polygonTexture.Width, polygonTexture.Height);

//确保纹理的原点在图心(几何体的真正中心)

Vector2 polygonOrigin = verts.GetCentroid();

//使用body factory来建立body

Body polygonBody = BodyFactory.Instance.CreatePolygonBody(PhysicsSimulator, verts, 5);

polygonBody.Position = new Vector2(500, 400);

GeomFactory.Instance.CreatePolygonGeom(PhysicsSimulator, polygonBody, verts, 0);

10.2. Path Generator路径产生器

路径产生器的作用是沿曲线建立body,并且使用joint或spring来连接它们。可以用来:建立坦克履带;绳桥;链条。

注意:Path Generator存在于Path类中,在ComplexFactory中建立链chains或绳rope。

你也可以使用Path Generator为所有的body产生几何体,它允许与其他物体产生碰撞。

10.3. Planetary Gravity地心引力

Farseer引擎2.1中新加入的控制器,可以在一系列的点上产生引力效果。

11. Performance性能

略。

转载于:https://www.cnblogs.com/kevinss30/archive/2011/05/11/2043395.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值