刚体的重要属性

刚体和质点是物理学中的重要概念,质点把物体抽象为一个点,忽略了物体的自身形状。
刚体则具体考虑物体的形状,它包括运动、重力、碰撞等属性。

如果启用了刚体的质量、dynamic等属性,则刚体的位置和旋转都是由物理计算出来的,开发者不应该直接设置刚体的物理和旋转。
开发者可以给刚体施加力。一句话总结就是,改变游戏物体的Transform这一动作,在每一个阶段都应该由特定控制器负责,如果多个控制器同时修改物体的Transform,会造成游戏物体的瞬移、抖动等不可控情况。

如果不想使用重力

  1. 直接把物体的重力系数设置为0即可。
  2. 把物体设置为kinematic,只有运动,没有质量。物体的Transform属性不会被物理引擎所驱动,只能通过代码修改Transform属性对其进行操作。
  3. 把物体的UseGravity设置成0

给物体施加力

rigidbody.AddForce rigidbody.AddForceAtPosition

刚体(RegidBody)的三种类型

  • dynamic:有质量、有速度
  • kinematic(运动学的):只有速度没有质量
  • static:只有质量没有速度,永远静止的物体。

只有有质量的两个物体才有可能相撞,没有质量的两个物体无法相撞。

Dynamic:这种刚体类型具有可用的全套属性(例如有限质量和阻力),并受重力和作用力的影响。Dynamic刚体类型将与每个其它刚体类型碰撞,是最具互动性的刚体类型。这是需要移动的对象的最常见刚体类型,因此是2D刚体的默认刚体类型。此外,由于具有动态性并与周围所有对象互动,因此也是性能成本最高的刚体类型。选择此刚体类型时,所以2D刚体属性均可用。 Kinematic:这种类型的2D刚体仅在非常明确的用户控制下进行移动。虽然Dynamic2D刚体受重力和作用力的影响,但Kinematic2D刚体并不会受此影响。因此,Kinematic2D刚体的速度很快,与Dynamic比,对系统资源的需求更低。 Kinematic2D刚体仍然通过速度移动,但是此速度不受作用力和重力的影响。Kinematic2D刚体不会与其它Kinematic2D刚体和Static2D刚体碰撞,只会与Dynamic2D刚体碰撞。与Static2D刚体(见下文)相似,Kinematic2D刚体在碰撞期间的行为类似于不可移动的对象(就像具有无限质量)。选择此刚体类型时,与质量相关的属性将不可用。 (简单来说,Kinematic只能通过更改刚体的速度属性来改变位置,不会受到其它物理效果的影响。) Static2D刚体设计为在模拟条件下完全不动(Play模式);如果任何对象与Static2D刚体碰撞,此刚体类型的行为类似于不可移动的对象(就像具有无限质量)。此刚体类型也是使用资源最少的刚体类型。Static刚体只能与Dynamic2D刚体碰撞。不可支持两个Static2D刚体进行碰撞,因为这种刚体不是为了移动而设计的。

Rigidbody组件的属性

Mass 质量:用来模拟物体的质量,单位为千克。质量会影响惯性大小,而且质量不同的两个刚体相互碰撞时,它们各自的反应也不同。要注意物体的质量大小不会影响自由落体时的速度,想想伽利略的两个铁球同时落地。

Drag 空气阻力:物体受力移动时受到的空气阻力大小,0 表示没有空气阻力。如果想让两个物体自由落体时速度不同,就给它们设置不同的空气阻力。空气阻力越大,物体感觉起来就越轻,比如铁块的空气阻力可以设置为 0.001,羽毛的空气阻力可以设置为 10。这个值一般不需要设置,如有特殊需要的话,就参考铁块和羽毛的阻力范围进行设置。Drag可以理解为"拉风",风对它的阻力。

Angular Drag 角阻力:物体受力旋转时受到的空气阻力大小。因为物体旋转时的速度叫做角速度,所以旋转时受到的阻力就叫做角阻力。这个属性和 Drag 空气阻力属性类似, Drag 空气阻力属性会影响物体在空气中移动时的速度,Angular Drag 角阻力会影响物体在空气中旋转时的速度。

Use Gravity 启用重力:物体是否受重力影响。受重力影响的物体会进行自由落体。

Is Kinematic 运动学:如果我们只是需要让物理系统进行碰撞检测,不需要使用物理系统控制游戏对象,而是在脚本中使用 Transform 控制物体,此时我们可以勾选刚体组件中的 Is Kinematic 属性。

Interpolate 插值:物体在进行物理运动时的插值方式,默认是 None 不使用插值。

  • None 不使用插值:这个选项是默认值,一般情况下此选项不需要设置。如果物体在物理系统控制下,会发生轻微的抖动,可以尝试使用另外两种选项。
  • Interpolate 插值:这个选项会根据上一帧中物体的 Transform 来计算当前帧的插值。
  • Extrapolate 向后推断:这个选项会推断下一帧中物体的 Transform 来计算当前帧的插值。

Collision Detection 碰撞检测:碰撞检测模式,默认是 Discrete 离散检测。

  • Discrete 离散检测:对场景中的其它碰撞体使用离散碰撞检测。一般情况下我们不需要修改此属性。物理系统默认的碰撞检测是离散的,所以有时高速移动的刚体会穿透障碍物,此时我们才需要使用另外两种碰撞检测模式。
  • Continuous 连续检测:刚体对其它没有刚体的碰撞器采用连续检测,防止刚体速度过快穿透障碍物。比如快速飞行的子弹碰撞静止的墙壁,此时如果采用 Dscrete 离散检测,子弹不会打在墙壁上反弹,而是会穿透墙壁。但该模式下并不能正确检测两颗高速飞行的子弹相互碰撞,因为它们两个都带有刚体,此时请使用第三种模式。要注意连续检测会影响物理性能,非必要情况请使用默认的 Discrete 离散碰撞检测。
  • Continuous Dynamic 连续动态检测:会对其它刚体(碰撞检测模式不能是 Discrete 离散碰撞检测)进行连续检测,防止互相穿透。对没有刚体的碰撞器也会采用连续碰撞检测

Constraints 限制:对刚体的运动进行限制。 Freeze Position 冻结位移:当刚体移动时,可选地忽略在某个轴上的位移。有 3 个可勾选属性 X、Y、Z,分别表示在 X 轴、Y 轴和 Z 轴方向上的位移。如果勾选了 Y 则表示,刚体受力运动后,不会在 Y 轴方向上发生位移。 Freeze Rotation 冻结旋转:当刚体旋转时,可选地忽略绕某个轴的旋转。也有 3 个可勾选属性,分别表示绕 X 轴旋转、绕 Y 轴旋转和绕 Z 轴旋转。如果勾选了 X 则表示,刚体受力运动后,不会绕 X 轴发生旋转。

刚体的睡眠

当刚体移动速度低于规定的最小线性速度或转速时,物理引擎会认为刚体已经停止。发生这种情况时,游戏对象在受到碰撞或力之前不会再次移动,因此将其设置为“睡眠”模式。这种优化意味着,在刚体下一次被“唤醒”(即再次进入运动状态)之前,不会花费处理器时间来更新刚体。

在大多数情况下,刚体组件的睡眠和唤醒是透明发生的。但是,如果通过修改__变换__位置将静态碰撞体(即,没有刚体的碰撞体)移入游戏对象或远离游戏对象,则可能无法唤醒游戏对象。这种情况下可能会导致问题,例如,已经从刚体游戏对象下面移走地板时,刚体游戏对象会悬在空中。在这种情况下,可以使用 WakeUp 函数显式唤醒游戏对象。有关睡眠的更多信息,请参阅刚体和 2D 刚体组件页面。

恒力组件

Unity提供了一个Constant Force 组件,这个组件如果开发者自己实现也用不了几行代码。
它的属性包括:力、相对力、力矩、相对力矩。