Physics Hand Bone
Last updated
Last updated
PhysicsHandBone is an abstract type of HandBone that is intended to be implemented by hand bones that move to different poses via physics, be it by manipulating velocities on the bone's physics body or by using different joints and their means of manipulating velocities (joint drives/motors) or in any other way using hand bone's physics related properties.
There are several PhysicsHandBone derived scripts defined in OctoXR that are also abstract and serve as base scripts for PhysicsHandBones that are more specialized in different ways, those are covered briefly in scripting section and will not be mentioned here.
The most basic type of PhysicsHandBone. It requires a Rigidbody attached to the same object it is attached to and moves to target poses either by manipulating the body's velocities or by setting the body's position and rotation directly via MovePosition and MoveRotation methods of the Rigidbody class.
Properties exposed in the inspector panel of the RigidBodyHandBone are mostly the ones inherited from HandBone, the ones specific to RigidBodyHandBones are:
Linear Move: Specifies in what way will the bone's position be moved towards target position
Angular Move: Specifies in what way will the bone's rotation be moved towards target rotation
Both linear and angular move offer these options:
None: Position/rotation will not be changed; this option could be viewed as disabling the bone's movement
Set Velocity: Target position/rotation will be achieved by setting the bone's velocity/angular velocity to appropriate value
Set Position: Target position/rotation will be achieved by setting the bone's position/rotation directly using the bone's Rigidbody MovePosition/MoveRotation
Joint: Target position/rotation will be achieved using the bone's joint; how exactly will this be done depends on the specific PhysicsHandBone and what type of Joint component it uses, it can be by using joint's drive properties, joint motor and others. This option is not used by the RigidBodyHandBone, specifying it for the RigidBodyHandBone will have the same effect as specifying None
Important to note is that if the bone's Rigidbody is kinematic (IsKinematic is set to true on the Rigidbody component), then it will always be moved towards target position and rotation by setting position and rotation on the Rigidbody directly, these options are ignored for kinematic bodies, except the None option which will still disable the bone's linear/angular movement. This behaviour generally goes for all rigid body based physics hand bones defined in OctoXR.
If you intend to use physics hand bone that is always kinematic, then RigiBodyHandBone is probably the best choice since it's the most light-weight rigid body based hand bone, it doesn't use physics joints that would just end up being useless for kinematic bones.
You are free to set the properties of the bone's Rigidbody component as you see fit, RigidBodyHandBone does not prevent or override that at all, with the exception of Use Gravity property - it will always disable gravity for its rigid body. Feel free to experiment and try out different values for the bone's rigid body properties as much as you like.
This physics hand bone is basically identical to the previously described RigidBodyHandBone, but it additionally requires a ConfigurableJoint attached to the same GameObject it is attached to.
Note that the RigidBodyConfigurableJointHandBone still does not use the Joint option for linear and angular movement, the required ConfigurableJoint is used just to connect the bone to its parent bone from the same HandSkeleton it is added to, if it has a parent bone.
These joint connections can result in additional stability when moving this type of bones to the target poses and the joints on them provide many additional options, such as setting the rotational limits to approximately match the rotational limits of human fingers for example.
It might seem redundant to have this particular PhysicsHandBone defined at all considering there is a ConfigurableJointHandBone (described bellow) that can accomplish the same things as this one while also providing additional functionalities to those of RigidBodyConfigurableJointHandBone. The reason for having this hand bone is in the fact that it uses a physics joint to connect itself to its parent bone for additional stability and provided flexibility while not having a more complex logic involved in moving it to target pose implemented, it still uses the relatively simple logic of RigidBodyHandBone for that.
Probably the most versatile rigid body based hand bone. It requires a ConfigurableJoint, which it can use to move to target poses.
Like the RigidBodyConfigurableJointHandBone described above, the ConfigurableJoint used by this bone is used to connect it to its parent bone, but it is potentially additionally used to move the bone to target poses as well, depending on the bone's Linear/Angular Move option.
ConfigurableJointHandBone does not expose any properties in its inspector panel that are different than those of the RigidBodyHandBone described above. If the Joint option is used for its linear and/or angular movement, then ConfigurableJointHandBone will move towards target positions/rotations using its ConfiguarbleJoint drives.
Important to mention is that the bone's joint drive properties are not controlled by the bone. That means that you choose all of the drive related properties on the bone's ConfigurableJoint component (position spring, damping, maximum force) for each drive separately. Many other joint's properties are also free to be set - joint angular limits are probably the ones you are most interested in.
As for the joint anchors, axes and motion properties, those should be left alone for the most part, but you can try and experiment with those too. Just keep in mind that messing with those properties is probably going to result in a strange behaviour.
This specific PhysicsHandBone is much like the previously described ConfigurableJointHandBone, except, unsurprisingly, it requires a HingeJoint instead of ConfigurableJoint.
By having a HingeJoint, it is limited to rotate around a single axis relative to its parent bone. Axis can be specified by the Axis property it defines and it can be set to either X, Y or Z.
If the option to move the bone to target rotations using its joint is chosen then the HingeJointHandBone will rotate either by configuring joint spring or by configuring joint motor of its HingeJoint. Which one depends on the values set for UseMotor and UseSpring properties on the bone's HingeJoint - UseMotor takes priority over UseSpring. If none is enabled then no action is performed.
HingeJointHandBone supports Joint option for its linear movement as well, it will accomplish this by manipulating its joint's anchors.
Knowing all that, this type of physics hand bone is obviously fit to be used for any of the finger bones, excluding the first phalanges that are connected to the WristRoot since those bones rotate around two axes when it comes to human hand. The second and third phalanges rotate around the single axis for the most part and when it comes to default configuration and all of the models and scripts in OctoXR, this is the X axis.
PhysicsHandBones described on this page can all be added to the same PhysicsHandSkeleton, you can mix the types however you want and you are encouraged to try all sorts of different combinations.
Keep in mind that the root bone of a PhysicsHandSkeleton must be manually added to the GameObject before PhysicsHandSkeleton is added to it, as already mentioned on the page dedicated to PhysicsHandSkeleton.
When using Auto Add Bones functionality on the PhysicsHandSkeleton's inspector panel, RigidBodyHandBones are added by the skeleton if the skeleton successfully determines GameObjects that could be its hand bones. So if you want different types of bones, you will have to manually add the desired types of PhysicsHandBones to the GameObjects first, then you can either assign those GameObjects to the desired hand bone fields in the PhysicsHandSkeleton's inspector one by one or you can try using Auto Add Bones after adding all the bones manually - PhysicsHandSkeleton will potentially detect existing bones with no HandSkeleton associated.
There is one important detail left to mention concerning PhysicsHandBones that move to target poses using their joints. Because of certain inner workings of the Unity engine and PhysX engine used by it, physics joints get reset every time a GameObject with the joint is deactivated and then activated again, or every time other GameObject connected to the joint is (re)activated. This mainly affects the rotation constraints applied by the joint. Target rotations that are set to the joints are actually offsets from the joints' rest rotations. Joint's rest rotation is, in simple terms, the relative rotation between connected bodies at the moment of the connected object's (re)activation. These rest rotations get reset on connected object's (re)activation and therefore target joint rotations that the physics hand bones continue to set end up looking incorrect after they are activated again.
There are some possible workarounds:
If you deactivate a physics hand bone with a joint, then before activating it again, set its Transform back to the bone's bind pose (BindPose property of the hand bone). You should, however, do this with the bone's child bones in the same hand skeleton too
It is still best to avoid deactivating the bone with the joint on it. If you want to disable the bone as a consequence of hand tracking being lost/low confidence and you don't want that bone affecting other objects any more, you could deactivate the bone's collider(s) instead - either disable the collider component(s) or deactivate the GameObject(s) that have bone collider(s) attached, so long as they don't include the GameObject with the bone's joint
This joint resetting also has the consequence of resetting the joint rotational limits, because limits are applied as offsets to the relative rotation between connected bodies at the moment of the joint's (re)activation. This might not matter much if you are not limiting the joint rotations on the physics bones, but it is something to keep in mind as well.