Skip to content

Commit

Permalink
Add many bone ik
Browse files Browse the repository at this point in the history
We use quaternion axis angle because it is normalized.
  • Loading branch information
fire committed Jan 6, 2023
1 parent b14f7aa commit 9f02c41
Show file tree
Hide file tree
Showing 44 changed files with 7,051 additions and 0 deletions.
15 changes: 15 additions & 0 deletions modules/many_bone_ik/SCsub
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
#!/usr/bin/env python

Import("env")

env_many_bone_ik = env.Clone()
env_many_bone_ik.Prepend(CPPPATH=["#modules/many_bone_ik"])
env_many_bone_ik.Prepend(CPPPATH=["#modules/many_bone_ik/src/math"])
env_many_bone_ik.Prepend(CPPPATH=["#modules/many_bone_ik/src"])
env_many_bone_ik.add_source_files(env.modules_sources, "constraints/*.cpp")
env_many_bone_ik.add_source_files(env.modules_sources, "src/math/*.cpp")
env_many_bone_ik.add_source_files(env.modules_sources, "src/*.cpp")
env_many_bone_ik.add_source_files(env.modules_sources, "*.cpp")

if env.editor_build:
env_many_bone_ik.add_source_files(env.modules_sources, "editor/*.cpp")
24 changes: 24 additions & 0 deletions modules/many_bone_ik/config.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
def can_build(env, platform):
return True


def configure(env):
pass


def get_doc_classes():
return [
"ManyBoneIK3D",
"IKBone3D",
"IKEffector3D",
"IKBoneSegment3D",
"IKEffectorTemplate3D",
"IKKusudama3D",
"IKRay3D",
"IKNode3D",
"IKLimitCone3D",
]


def get_doc_path():
return "doc_classes"
10 changes: 10 additions & 0 deletions modules/many_bone_ik/design_docs/AUTHORS.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# Many Bone IK authors

This project is originally a port from a Java project by Eron Gjoni https://github.com/EGjoni/Everything-Will-Be-IK.

GitHub usernames are indicated in parentheses.

- K. S. Ernest (iFire) Lee (fire)
- Eron Gjoni (EGjoni)
- rafallus Rafael M. G. (rafallus)
- lyuma (lyuma)
Binary file not shown.
5 changes: 5 additions & 0 deletions modules/many_bone_ik/design_docs/ik_box_test_procedure.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
# IK Box Test procedure

1. Move the target of the effector to one of the corners
2. Move to the 8 corners of a virtual box.
3. Look for instability like shaking.
21 changes: 21 additions & 0 deletions modules/many_bone_ik/design_docs/open_problems.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
# Open problems

Our system attempts to infer some sane default transforms and parameters when the user hasn't specified anything. If the user has manually specified something, our system should prefer to use those user specified values instead of the inferred values. What is the best way to accomplish this?

Add handles.

Kusuduama cone radius is bugged.

Overlapping limit cones don't visualize.

1. for limit cone directions: intersect camera mouse ray with the kusudama sphere and pick the closest intersection.
2. for limit cone radius, same as direction, except take the arccosine of the dot product with the direction to get the radius
3. for axial angle: intersect with xz plane, take arcosine of dot product with the z axis

Mirror button for kusudama cones.

Make changing the skeleton not lose the set parameters. Don't rebuild the skeleton from scratch. Reuse the the parameters already set.

Leave stabilizing pass counts off when developing. Add a ui for it.

We don't like painfullness but it seems to work in the reference implementation.
42 changes: 42 additions & 0 deletions modules/many_bone_ik/doc_classes/IKBone3D.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
<?xml version="1.0" encoding="UTF-8" ?>
<class name="IKBone3D" inherits="Resource" is_experimental="true" version="4.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../doc/class.xsd">
<brief_description>
</brief_description>
<description>
</description>
<tutorials>
</tutorials>
<methods>
<method name="get_constraint" qualifiers="const">
<return type="IKKusudama3D" />
<description>
</description>
</method>
<method name="get_constraint_orientation_transform">
<return type="IKNode3D" />
<description>
</description>
</method>
<method name="get_constraint_twist_transform">
<return type="IKNode3D" />
<description>
</description>
</method>
<method name="get_pin" qualifiers="const">
<return type="IKEffector3D" />
<description>
</description>
</method>
<method name="is_pinned" qualifiers="const">
<return type="bool" />
<description>
</description>
</method>
<method name="set_pin">
<return type="void" />
<param index="0" name="pin" type="IKEffector3D" />
<description>
</description>
</method>
</methods>
</class>
22 changes: 22 additions & 0 deletions modules/many_bone_ik/doc_classes/IKBoneSegment3D.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
<?xml version="1.0" encoding="UTF-8" ?>
<class name="IKBoneSegment3D" inherits="Resource" is_experimental="true" version="4.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../doc/class.xsd">
<brief_description>
</brief_description>
<description>
</description>
<tutorials>
</tutorials>
<methods>
<method name="get_ik_bone" qualifiers="const">
<return type="IKBone3D" />
<param index="0" name="bone" type="int" />
<description>
</description>
</method>
<method name="is_pinned" qualifiers="const">
<return type="bool" />
<description>
</description>
</method>
</methods>
</class>
32 changes: 32 additions & 0 deletions modules/many_bone_ik/doc_classes/IKEffector3D.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
<?xml version="1.0" encoding="UTF-8" ?>
<class name="IKEffector3D" inherits="Resource" is_experimental="true" version="4.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../doc/class.xsd">
<brief_description>
</brief_description>
<description>
</description>
<tutorials>
</tutorials>
<methods>
<method name="get_target_node" qualifiers="const">
<return type="NodePath" />
<description>
</description>
</method>
<method name="set_target_node">
<return type="void" />
<param index="0" name="skeleton" type="Skeleton3D" />
<param index="1" name="node" type="NodePath" />
<description>
</description>
</method>
</methods>
<members>
<member name="passthrough_factor" type="float" setter="set_passthrough_factor" getter="get_passthrough_factor" default="0.0">
Pins can be ultimate targets or intermediary targets.
By default, each pin is treated as an ultimate target, meaning any bones which are ancestors to that pin's effector are not aware of any pins which are the target of bones descending from that effector.
Changing this value makes ancestor bones aware and determines how much less they care with each level down.
Presuming all descendants of this pin have a falloff of 1, then: A pin falloff of 0 on this pin means only this pin is reported to ancestors. A pin falloff of 1 on this pin means ancestors care about all descendant pins equally (after accounting for their pin weight), regardless of how many levels down they are. A pin falloff of 0.5 means each descendant pin is used about half as much as its ancestor. The pin's falloff of a descendant is taken into account for each level with each level.
Meaning, if this pin has a falloff of 1 and its descendent has a falloff of 0.5, then it will be reported with total weight. Then, its descendant will be calculated with total weight; the descendant of that pin will be calculated with half weight. Finally, the descendant of that one's descendant will be with calculated quarter weight.
</member>
</members>
</class>
19 changes: 19 additions & 0 deletions modules/many_bone_ik/doc_classes/IKEffectorTemplate3D.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
<?xml version="1.0" encoding="UTF-8" ?>
<class name="IKEffectorTemplate3D" inherits="Resource" is_experimental="true" version="4.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../doc/class.xsd">
<brief_description>
</brief_description>
<description>
</description>
<tutorials>
</tutorials>
<members>
<member name="direction_priorities" type="Vector3" setter="set_direction_priorities" getter="get_direction_priorities" default="Vector3(0.2, 0, 0.2)">
</member>
<member name="passthrough_factor" type="float" setter="set_passthrough_factor" getter="get_passthrough_factor" default="0.0">
</member>
<member name="target_node" type="NodePath" setter="set_target_node" getter="get_target_node" default="NodePath(&quot;&quot;)">
</member>
<member name="weight" type="float" setter="set_weight" getter="get_weight" default="1.0">
</member>
</members>
</class>
25 changes: 25 additions & 0 deletions modules/many_bone_ik/doc_classes/IKKusudama3D.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
<?xml version="1.0" encoding="UTF-8" ?>
<class name="IKKusudama3D" inherits="Resource" is_experimental="true" version="4.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../doc/class.xsd">
<brief_description>
Kusudamas are a sequential collection of reach cones, forming a path by their tangents.
</brief_description>
<description>
A Kusudama is a ball with a bunch of reach-cones sticking out of it. Except that these reach cones are arranged sequentially, and a smooth path is automatically inferred leading from one cone to the next.
Kusudama is taken from the Japanese word for "ball with a bunch of cones sticking out of it".
</description>
<tutorials>
</tutorials>
<methods>
<method name="get_limit_cones" qualifiers="const">
<return type="IKLimitCone3D[]" />
<description>
</description>
</method>
<method name="set_limit_cones">
<return type="void" />
<param index="0" name="limit_cones" type="IKLimitCone3D[]" />
<description>
</description>
</method>
</methods>
</class>
10 changes: 10 additions & 0 deletions modules/many_bone_ik/doc_classes/IKLimitCone3D.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
<?xml version="1.0" encoding="UTF-8" ?>
<class name="IKLimitCone3D" inherits="Resource" is_experimental="true" version="4.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../doc/class.xsd">
<brief_description>
</brief_description>
<description>
A reach cone is a cone bounding the rotation of a ball-and-socket joint. A reach cone is defined as a vector pointing in the direction which the cone is opening, and a radius (in radians) representing how much the cone is opening up.
</description>
<tutorials>
</tutorials>
</class>
21 changes: 21 additions & 0 deletions modules/many_bone_ik/doc_classes/IKNode3D.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
<?xml version="1.0" encoding="UTF-8" ?>
<class name="IKNode3D" inherits="RefCounted" is_experimental="true" version="4.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../doc/class.xsd">
<brief_description>
</brief_description>
<description>
</description>
<tutorials>
</tutorials>
<methods>
<method name="get_global_transform" qualifiers="const">
<return type="Transform3D" />
<description>
</description>
</method>
<method name="get_transform" qualifiers="const">
<return type="Transform3D" />
<description>
</description>
</method>
</methods>
</class>
30 changes: 30 additions & 0 deletions modules/many_bone_ik/doc_classes/IKRay3D.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
<?xml version="1.0" encoding="UTF-8" ?>
<class name="IKRay3D" inherits="RefCounted" is_experimental="true" version="4.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../doc/class.xsd">
<brief_description>
</brief_description>
<description>
</description>
<tutorials>
</tutorials>
<methods>
<method name="get_heading">
<return type="Vector3" />
<description>
</description>
</method>
<method name="get_intersects_plane">
<return type="Vector3" />
<param index="0" name="a" type="Vector3" />
<param index="1" name="b" type="Vector3" />
<param index="2" name="c" type="Vector3" />
<description>
</description>
</method>
<method name="get_scaled_projection">
<return type="float" />
<param index="0" name="input" type="Vector3" />
<description>
</description>
</method>
</methods>
</class>
Loading

0 comments on commit 9f02c41

Please sign in to comment.