自由旋转角度
为单个链提供位置目标后,将保持明显的自由度:绕末端效应器轴(EE 轴)旋转。使用旋转角度,可以定量地说明这种自由度。
1. 起始关节
2. 末端效应器
3. EE 轴
解算器平面
我们称通过所有关节的平面为“解算器平面”。如果关节不位于平面上,该平面的定义如下:(A) 通过“起始关节”和“结束关节”;(B) 在某种意义上,距离其余关节最近。
“旋转角度”说明了“解算器平面”的自由度。它只包含“起始关节”。
零平面贴图
为了定量说明解算器平面,必须就 0 的含义达成一致。末端效应器的位置给定时,“零(解算器)平面”的位置如何?“零平面贴图”用作参数 EE 轴,因此可以为零平面生成法线。
使用 IK 系统,各个解算器插件都能定义自己的“零平面贴图”。如果未定义,IK 系统将会提供默认值。
“零平面贴图”的参数是一个提供 EE 轴方向的单位向量。同样,EE 沿着 EE 轴滑动时,应该固定解算器平面。因此,“零平面贴图”可以定义向量场或球体。如果提供球体上的点,将会生成切向单位向量,以其作为零平面的法线进行插补。
1. 零平面的法线
翻转解算器平面
球体上不存在连续的向量场属于数学事实。无论做何努力,邻近向量会大幅更改的球体上始终存在着一点。这是末端效应器轴向其靠近时解算器平面要发生翻转的位置。
一方面,这是因为,根据历史独立型要求,我们必须向单点分配固定向量。另外一方面,无论分配什么向量,该向量将会与分配给邻近点的某些向量明显不同。
球体的固有参考帧
为了定义“零平面贴图”,必须定义球体的参考帧。该参考帧是关节链本身所固有的。
球体可以通过中心、水平面和子午线(零纬度)来定义。该中心分配给起始关节。
如果所有的关节角度都假定为首选角度,则姿势尤其重要。我们称之为首选姿势。
我们将处于首选姿势的解算器平面用作水平面。因为使用旋转角度可以控制起始关节,所以,起始关节处的首选角度并非是固有的。另外,使用解算器平面定义水平面是合理的。其中,通过向起始关节分配零平面,而向其他关节分配首选角度,可以生成该解算器平面。
EE 轴可以定义子午线。此时,球体的定义如下图所述:
1. EE 轴
所有关节都假定了首选角度。“零平面贴图”将在该球体上加以定义。
事实上,定义其自身的“零平面贴图”时所用的插件解算器 API 可以向处于首选姿势的解算器平面分配 EE 轴和法线:
virtual const IKSys::ZeroPlaneMap* GetZeroPlaneMap(const Point3& a0, const Point3& n0) const
其中,a0 和 n0 分别是 EE 轴和处于首选姿势的解算器平面。ZeroPlaneMap 的对象是一个向球体上每点分配平面法线的函数。
默认零平面贴图
如果未由插件解算器提供,(IK 解算器本身作为插件解算器实施)IK 系统将会提供默认值。该贴图是通过下列规则定义的:
A:对于水平面与球体相交得到的赤道上的每个点,法线向量是作为垂直向量定义的。该向量所指的方向与处于首选姿势的解算器平面的法线方向相同。
B:对于球体而不是两极上的任何点,存在一个通过该点和南北两极的大圆。该圆与赤道相交于两点。一点比较靠近指定点。按着大圆方向将赤道上更近的点处的法线沿着切线方向移动到该点,即可定义指定点处的法线向量。
生成零平面的默认法线
无疑,这种方法不会延伸到南北极。南北极是单点。EE 轴穿越两极时,法线将会突然改变方向,即通过用户视口进行翻转。
通常,首选姿势是首次分配解算器时的姿势。因此,放置点的平面与此处的水平面相对应。规则 A 可以确保,如果在平面上移动目标,该链将一直处于该平面中。
规则 B 表明,沿着与赤道垂直的大圆移动到赤道时,该链一直处于垂直位置,穿过两极(该贴图的单点)时除外。
父空间
到目前为止,我们已经介绍了很多内容,就好像整个世界只包含 IK 元素一样。事实上,IK 链和目标位于各个变换层次的点上。最终,我们必须绘制末端效应器的位置。在世界中,该位置是指球体上的某个点。根据球体相对于末端效应器位置的安装方式,经度和纬度的显示不尽相同。要在其中放置该球体的父变换空间称“旋转角度父空间”或“父空间”(如果环境明确的话)。
对于 IK 参数,父空间必须是恒定不变的。刚才,我们已经提供了两种选择方案:
起始关节“旋转角度父空间”与“起始关节”的父空间相同。
IK 目标“旋转角度父空间”是 IK 目标的父级。
示例 1
如果起始关节和目标直接位于世界中,选择“父空间”不会有任何区别。在下例中,起始关节是对象 A 的父级。
此时,可以(通过起始关节)将 IK 链设置为对象 A 的父级。
假定这是分配 IK 解算器时的姿势。因此,这是首选姿势。展开关节的平面是球体的水平面(“零平面贴图”)。
A:“父空间”是“起始关节”。在这种情况下,将该球体设置为 A 的父级。如果 A 绕着绘制的轴旋转,该球体将会与其一同旋转。目标位于各个变换层次中。该目标将会保持原位。末端效应器因 IK 解决方案而与其相连。因为(平面)法线对球体是固定的,所以,它也会与 A 一起旋转。为此,整个链似乎与父对象一起旋转。
B:“父空间”是“IK 目标”。假定该目标是世界的父级。在这种情况下,由于球体已设置为世界的父级,因此保持不变。因此法线对球体是固定的,所以,旋转 A 时,该链将保持静止。
示例 2
在下例中,我们将要了解一下分配 IK 解算器后父空间存在的旋转情况。
分配 IK 解算器后,IK 链的父空间将会包含一个旋转。
父 A 包含 90 度的旋转。如果用户没有使用 IK 解算器创建四个骨骼,并在稍后分配一个 IK 解算器(从 Bone2 到 Bone4),就属于抽象概念。如果直接将链设置为世界的父级,它将会显示在右图中:解算器平面变成水平状态。
A:“父空间”是“起始关节”。旋转 A 后,将会安装球体。因此,“水平面”与视口中所示的链平面相符。单点相对于该平面与“起始关节”垂直。在平面上移动目标/末端效应器时,它决不会与单点交叉,也不会进行翻转。
B:“父空间”是“IK 目标”。另外,我们假定目标的父空间是世界。此时,该球体的“水平面”将变成水平状态,如右图所示。单点和两极都位于展开关节的平面上。因此,用户左右移动目标/末端效应器时,末端效应器将会通过单点,还会进行翻转。
B 的问题在于,决不会向用户显示右图。因此,必须对其进行设想,以便了解翻转。
示例 3
本例介绍了重新分配“起始关节”时生成的结果。假定我们有一个包含四个骨骼节点的 IK 链。
1. Bone01
2. Bone02
3. Bone03
4. Bone04
“起始关节”和“结束关节”分别是 Bone01 和 Bone04。假定图中所示的姿势是首选姿势,且 Bone01 包含一个旋转。如果直接将 Bone02 设置为世界的父级,右图中将会显示 Bone02 的层次。
向 Bone02 重新分配“起始关节”时,“零平面贴图”球体将会基于右侧的配置。
A:“父空间”是“起始关节”。在这种情况下,固定进行正确配置的球体将被设置为 Bone01 的父级。它将会与基于 Bone01 到 Bone04 的球体相同。因此,可以获得相同的法线,而链将会保持不变。
B:“父空间”是“IK 目标”。在这种情况下,球体处于世界中,而 Bone02 被设置为 Bone01 的父级。如果 Bone04 因 Bone01 变换而移动到左侧,对球体(对世界固定)固定的观察者将会发现,Bone04 正在远离首选姿势定义的中性位置。此后,将会对“零平面贴图”应用算法,以便在替换位置处找到法线。通常,它不会与视口垂直。因此,使用新的“起始关节”时,只会翻转一次。
如果删除解算器/目标,并已分配新对象(从 Bone02 到 Bone04),您将会发现,该链不会翻转。为什么?分配“起始关节”和创建新的 IK 链/目标是不同的。“起始关节”是很多 IK 参数之一。重新分配“起始关节”与修改任何参数完全相同。其余参数将保持完好。尤其是,执行重新分配操作后,不会更改“旋转角度”。
创建新的 IK 链/目标会有所不同。试图确保关节链处于固定状态,方法是对参数进行相应的调整。尤其是,“旋转角度”将会设置为某个值,使解算器平面可以在视口中保持固定。
,