Merge pull request #226 from TwistedTwigleg/3D_IK_Demo

3D IK demo (fixed)
This commit is contained in:
Nathan Lovato
2018-03-31 12:05:26 +09:00
committed by GitHub
37 changed files with 6814 additions and 0 deletions

BIN
3d/ik/GunMaterial.material Normal file

Binary file not shown.

View File

@@ -0,0 +1,597 @@
tool
extends Spatial
"""
A FABRIK IK chain with a middle joint helper.
"""
export (NodePath) var skeleton_path setget _set_skeleton_path
export (PoolStringArray) var bones_in_chain setget _set_bone_chain_bones
export (PoolRealArray) var bones_in_chain_lengths setget _set_bone_chain_lengths
export (int, "_process", "_physics_process", "_notification", "none") var update_mode = 0 setget _set_update_mode
var target = null
var skeleton
# A dictionary holding all of the bone IDs (from the skeleton) and a dictionary holding
# all of the bone helper nodes
var bone_IDs = {}
var bone_nodes = {}
# The position of the origin
var chain_origin = null
# The combined length of every bone in the bone chain
var total_length = null
# The delta/tolerance for the bone chain (how do the bones need to be before it is considered satisfactory)
const CHAIN_TOLERANCE = 0.01
# The amount of interations the bone chain will go through in an attempt to get to the target position
const CHAIN_MAX_ITER = 10
# The amount of iterations we've been through, and whether or not we want to limit our solver to CHAIN_MAX_ITER
# amounts of interations.
export (int) var chain_iterations = 0
export (bool) var limit_chain_iterations = true
# Should we reset chain_iterations on movement during our update method?
export (bool) var reset_iterations_on_update = false
# A boolean to track whether or not we want to move the middle joint towards middle joint target.
export (bool) var use_middle_joint_target = false
var middle_joint_target = null
# NOT WORKING.
# A boolean to track whether or not we want to constrain the bones in the bone chain.
#export (bool) var constrained = false
# A array of strings contraining the bone constraints for each bone (assuming the order is the same
# as bones_in_chain). (ORDER: Left,Right,Up,Down)
#export (PoolStringArray) var bone_constraints
# Have we called _set_skeleton_path or not already. Due to some issues using exported NodePaths,
# we need to ignore the first _set_skeleton_path call.
var first_call = true
# A boolean to track whether or not we want to print debug messages
var debug_messages = false
func _ready():
if (target == null):
# NOTE: you HAVE to have a node called target as a child of this node!
# so we create one if one doesn't already exist
if has_node("target") == false:
target = Spatial.new()
add_child(target)
if Engine.editor_hint == true:
if get_tree() != null:
if get_tree().edited_scene_root != null:
target.set_owner(get_tree().edited_scene_root)
target.name = "target"
else:
target = get_node("target")
# If we are in the editor, we want to make a sphere at this node
if Engine.editor_hint == true:
_make_editor_sphere_at_node(target, Color(1, 0, 1, 1))
if middle_joint_target == null:
if has_node("middle_joint_target") == false:
middle_joint_target = Spatial.new()
add_child(middle_joint_target)
if Engine.editor_hint == true:
if get_tree() != null:
if get_tree().edited_scene_root != null:
middle_joint_target.set_owner(get_tree().edited_scene_root)
middle_joint_target.name = "middle_joint_target"
else:
middle_joint_target = get_node("middle_joint_target")
# If we are in the editor, we want to make a sphere at this node
if Engine.editor_hint == true:
_make_editor_sphere_at_node(middle_joint_target, Color(1, 0.24, 1, 1))
# Make all of the bone nodes for each bone in the IK chain
_make_bone_nodes()
# Make sure we're using the right update mode
_set_update_mode(update_mode)
func _make_editor_sphere_at_node(node, color):
# So we can see the target in the editor, let's create a mesh instance,
# Add it as our child, and name it
var indicator = MeshInstance.new()
node.add_child(indicator)
indicator.name = "(EditorOnly) Visual indicator"
# We need to make a mesh for the mesh instance.
# The code below makes a small sphere mesh
var indicator_mesh = SphereMesh.new()
indicator_mesh.radius = 0.1
indicator_mesh.height = 0.2
indicator_mesh.radial_segments = 8
indicator_mesh.rings = 4
# The mesh needs a material (unless we want to use the defualt one).
# Let's create a material and use the EditorGizmoTexture to texture it.
var indicator_material = SpatialMaterial.new()
indicator_material.flags_unshaded = true
indicator_material.albedo_texture = preload("editor_gizmo_texture.png")
indicator_material.albedo_color = color
indicator_mesh.material = indicator_material
indicator.mesh = indicator_mesh
############# SETGET FUNCTIONS #############
func _set_update_mode(new_value):
update_mode = new_value
set_process(false)
set_physics_process(false)
set_notify_transform(false)
if update_mode == 0:
set_process(true)
elif update_mode == 1:
set_process(true)
elif update_mode == 2:
set_notify_transform(true)
else:
if debug_messages == true:
print (name, " - IK_FABRIK: Unknown update mode. NOT updating skeleton")
return
func _set_skeleton_path(new_value):
# Because get_node doesn't work in the first call, we just want to assign instead
if first_call == true:
skeleton_path = new_value
return
skeleton_path = new_value
if skeleton_path == null:
if debug_messages == true:
print (name, " - IK_FABRIK: No Nodepath selected for skeleton_path!")
return
var temp = get_node(skeleton_path)
if temp != null:
# If it has the method "get_bone_global_pose" it is likely a Skeleton
if temp.has_method("get_bone_global_pose") == true:
skeleton = temp
bone_IDs = {}
# (Delete all of the old bone nodes and) Make all of the bone nodes for each bone in the IK chain
_make_bone_nodes()
if debug_messages == true:
print (name, " - IK_FABRIK: Attached to a new skeleton")
# If not, then it's (likely) not a Skeleton node
else:
skeleton = null
if debug_messages == true:
print (name, " - IK_FABRIK: skeleton_path does not point to a skeleton!")
else:
if debug_messages == true:
print (name, " - IK_FABRIK: No Nodepath selected for skeleton_path!")
############# OTHER (NON IK SOLVER RELATED) FUNCTIONS #############
func _make_bone_nodes():
# Remove all of the old bone nodes
# TODO: (not a huge concern, as these can be removed in the editor)
for bone in range(0, bones_in_chain.size()):
var bone_name = bones_in_chain[bone]
if has_node(bone_name) == false:
var new_node = Spatial.new()
bone_nodes[bone] = new_node
add_child(bone_nodes[bone])
if Engine.editor_hint == true:
if get_tree() != null:
if get_tree().edited_scene_root != null:
bone_nodes[bone].set_owner(get_tree().edited_scene_root)
bone_nodes[bone].name = bone_name
else:
bone_nodes[bone] = get_node(bone_name)
# If we are in the editor, we want to make a sphere at this node
if Engine.editor_hint == true:
_make_editor_sphere_at_node(bone_nodes[bone], Color(0.65, 0, 1, 1))
func _set_bone_chain_bones(new_value):
bones_in_chain = new_value
_make_bone_nodes()
func _set_bone_chain_lengths(new_value):
bones_in_chain_lengths = new_value
total_length = null
# NOT USED -- part of the (not working) constraint system
"""
func get_bone_constraints(index):
# NOTE: assumed angle constraint order:
# Left angle in degrees, right angle in degrees, up angle in degress, down angle in degrees.
if index <= bones_in_chain.size()-1:
var index_str = bone_constraints[index]
var floats = index_str.split_floats(",", false)
if (floats.size() >= 4):
return floats
else:
print (self.name, " - IK_FABRIK: Not all constraints are present for bone number ", index, " found!")
return null
print (self.name, " - IK_FABRIK: No constraints for bone number ", index, " found!")
return null
"""
# Various upate methods
# ---------------------
func _process(delta):
if reset_iterations_on_update == true:
chain_iterations = 0
update_skeleton()
func _physics_process(delta):
if reset_iterations_on_update == true:
chain_iterations = 0
update_skeleton()
func _notification(what):
if what == NOTIFICATION_TRANSFORM_CHANGED:
if reset_iterations_on_update == true:
chain_iterations = 0
update_skeleton()
############# IK SOLVER RELATED FUNCTIONS #############
func update_skeleton():
#### ERROR CHECKING conditions
if first_call == true:
_set_skeleton_path(skeleton_path)
first_call = false
if skeleton == null:
_set_skeleton_path(skeleton_path)
return
if bones_in_chain == null:
if debug_messages == true:
print (name, " - IK_FABRIK: No Bones in IK chain defined!")
return
if bones_in_chain_lengths == null:
if debug_messages == true:
print (name, " - IK_FABRIK: No Bone lengths in IK chain defined!")
return
if bones_in_chain.size() != bones_in_chain_lengths.size():
if debug_messages == true:
print (name, " - IK_FABRIK: bones_in_chain and bones_in_chain_lengths!")
return
################################
# Set all of the bone IDs in bone_IDs, if they are not already made
var i = 0
if bone_IDs.size() <= 0:
for bone_name in bones_in_chain:
bone_IDs[bone_name] = skeleton.find_bone(bone_name)
# Set the bone node to the currect bone position
bone_nodes[i].global_transform = get_bone_transform(i)
# If this is not the last bone in the bone chain, make it look at the next bone in the bone chain
if i < bone_IDs.size()-1:
bone_nodes[i].look_at(get_bone_transform(i+1).origin + skeleton.global_transform.origin, Vector3(0, 1, 0))
i += 1
# Set the total length of the bone chain, if it is not already set
if total_length == null:
total_length = 0
for bone_length in bones_in_chain_lengths:
total_length += bone_length
# Solve the bone chain
solve_chain()
func solve_chain():
# If we have reached our max chain iteration, and we are limiting ourselves, then return.
# Otherwise set chain_iterations to zero (so we constantly update)
if chain_iterations >= CHAIN_MAX_ITER and limit_chain_iterations == true:
return
else:
chain_iterations = 0
# Update the origin with the current bone's origin
chain_origin = get_bone_transform(0)
# Get the direction of the final bone by using the next to last bone if there is more than 2 bones.
# If there are only 2 bones, we use the target's forward Z vector instead (not ideal, but it works fairly well)
#var dir = -target.global_transform.basis.z.normalized()
var dir
if bone_nodes.size() > 2:
dir = bone_nodes[bone_nodes.size()-2].global_transform.basis.z.normalized()
else:
dir = -target.global_transform.basis.z.normalized()
# Get the target position (accounting for the final bone and it's length)
var target_pos = target.global_transform.origin + (dir * bones_in_chain_lengths[bone_nodes.size()-1])
# If we are using middle joint target (and have more than 2 bones), move our middle joint towards it!
if use_middle_joint_target == true:
if bone_nodes.size() > 2:
var middle_point_pos = middle_joint_target.global_transform
bone_nodes[bone_nodes.size()/2].global_transform.origin = middle_point_pos.origin
# Get the distance from the origin to the target
var distance = (chain_origin.origin - target_pos).length()
# If the distance is farther than our total reach, the target cannot be reached.
# Make the bone chain a straight line pointing towards the target
if distance > total_length:
for i in range (0, bones_in_chain.size()):
# Create a direct line to target and make this bone travel down that line
var r = (target_pos - bone_nodes[i].global_transform.origin).length()
var l = bones_in_chain_lengths[i] / r
# Find new join position
var new_pos = (1-l) * bone_nodes[i].global_transform.origin + l * target_pos
# Apply it to the bone node
bone_nodes[i].look_at(new_pos, Vector3(0, 1, 0))
bone_nodes[i].global_transform.origin = new_pos
# Apply the rotation to the first node in the bone chain, making it look at the next bone in the bone chain
bone_nodes[0].look_at(bone_nodes[1].global_transform.origin, Vector3(0, 1, 0))
# If the distance is NOT farther than our total reach, the target can be reached.
else:
# Get the difference between our end effector (the final bone in the chain) and the target
var dif = (bone_nodes[bone_nodes.size()-1].global_transform.origin - target_pos).length()
# Check to see if the distance from the end effector to the target is within our error margin (CHAIN_TOLERANCE).
# If it not, move the chain towards the target (going forwards, backwards, and then applying rotation)
while dif > CHAIN_TOLERANCE:
chain_backward()
chain_forward()
chain_apply_rotation()
# Update the difference between our end effector (the final bone in the chain) and the target
dif = (bone_nodes[bone_nodes.size()-1].global_transform.origin - target_pos).length()
# Add one to chain_iterations. If we have reached our max iterations, then break
chain_iterations = chain_iterations + 1
if chain_iterations >= CHAIN_MAX_ITER:
break
# Reset the bone node transforms to the skeleton bone transforms
#if (constrained == false): # Resetting seems to break bone constraints...
for i in range(0, bone_nodes.size()):
var reset_bone_trans = get_bone_transform(i)
bone_nodes[i].global_transform = reset_bone_trans
func chain_backward():
# Backward reaching pass
#var dir = -target.global_transform.basis.z.normalized()
# Get the direction of the final bone by using the next to last bone if there is more than 2 bones.
# If there are only 2 bones, we use the target's forward Z vector instead (not ideal, but it works fairly well)
var dir
if bone_nodes.size() > 2:
dir = bone_nodes[bone_nodes.size()-2].global_transform.basis.z.normalized()
else:
dir = -target.global_transform.basis.z.normalized()
# Set the position of the end effector (the final bone in the chain) to the target position
bone_nodes[bone_nodes.size()-1].global_transform.origin = target.global_transform.origin + (dir * bones_in_chain_lengths[bone_nodes.size()-1])
# For all of the other bones, move them towards the target
var i = bones_in_chain.size() - 1
while i >= 1:
i -= 1
var r = bone_nodes[i+1].global_transform.origin - bone_nodes[i].global_transform.origin
var l = bones_in_chain_lengths[i] / r.length()
# Apply the new joint position
bone_nodes[i].global_transform.origin = (1 - l) * bone_nodes[i+1].global_transform.origin + l * bone_nodes[i].global_transform.origin
func chain_forward():
# Forward reaching pass
# Set root at initial position
bone_nodes[0].global_transform.origin = chain_origin.origin
# Go through every bone in the bone chain
var i = 0
while i < bones_in_chain.size() - 1:
var r = (bone_nodes[i+1].global_transform.origin - bone_nodes[i].global_transform.origin)
var l = bones_in_chain_lengths[i] / r.length()
# Set the new joint position
var new_pos = (1 - l) * bone_nodes[i].global_transform.origin + l * bone_nodes[i+1].global_transform.origin
# Apply constraints (if we have them)
# NOTE: this does not work. It is left in as an example to help others if they decide to add constraints
"""
if (constrained == true):
var cf = bone_nodes[i].global_transform
cf = cf.looking_at(bone_nodes[i+1].global_transform.origin, Vector3(0, 1, 0))
var line = (new_pos - bone_nodes[i+1].global_transform.origin).normalized() * bones_in_chain_lengths[i]
new_pos += chain_constrain(new_pos, line, cf, i+1)
"""
# Apply the new joint position, (potentially with constraints), to the bone node
bone_nodes[i+1].global_transform.origin = new_pos
i += 1
# NOT USED -- part of the (not working) constraint system
"""
func chain_constrain(calc, line, cf, bone):
var scalar = calc.dot(line) / line.length()
var proj = scalar * line.normalized()
# NOTE: Something in the calculation for proj may be wrong.
# get axis that is closest
# NOTE: Not sure if we need to do a calculation or not. For now, we are just going to use Basis
var tmp = cf.looking_at(cf.origin - Vector3(0, 1, 0), Vector3(1, 0, 0))
var upvec = cf.basis.x
tmp = cf.looking_at(cf.origin - Vector3(1, 0, 0), Vector3(0, 1, 0))
var rightvec = cf.basis.z
# Get the vector from the projection to the calculated vector
var adjust = calc - proj
if scalar > 0:
# If we are below the cone, flip the projection vector
proj = -proj
pass
# Get the 2D components
var xaspect = adjust.dot(rightvec)
var yaspect = adjust.dot(upvec)
# Get the cross section of the cone
var constraint_angles = get_bone_constraints(bone)
var left = -(proj.length() * tan(deg2rad(constraint_angles[0])) )
var right = (proj.length() * tan(deg2rad(constraint_angles[1])) )
var up = (proj.length() * tan(deg2rad(constraint_angles[2])) )
var down = -(proj.length() * tan(deg2rad(constraint_angles[3])) )
# Find the quadrant
var xbound = xaspect >= 0 and right or left
var ybound = yaspect >= 0 and up or down
if xbound == true:
xbound = 1
else:
xbound = 0
if ybound == true:
ybound = 1
else:
ybound = 0
var f = calc
# Check if in 2D point lies in the ellipse
var ellipse = pow(xaspect, 2)/pow(xbound, 2) + pow(yaspect, 2)/pow(ybound, 2)
var inbounds = ellipse <= 1 and scalar >= 0
if not inbounds:
# Get the angle of our out of ellipse point
var a = atan2(yaspect, xaspect)
# Find the nearest point
var x = xbound * cos(a)
var y = ybound * sin(a)
# Convert back to 3D
#f = (proj + rightvec * x + upvec * y ).normalized() * calc.length()
f = (proj + rightvec * x + upvec * y ).normalized() * bones_in_chain_lengths[bone]
return f
"""
func chain_apply_rotation():
# Make all of the bones rotated correctly.
# For each bone in the bone chain
for i in range(0, bones_in_chain.size()):
# Get the bone's transform, NOT converted to world space
var bone_trans = get_bone_transform(i, false)
# If this is the last bone in the bone chain, rotate the bone so it faces
# the same direction as the next to last bone in the bone chain if there are more than
# two bones. If there are only two bones, rotate the end effector towards the target
if i == bones_in_chain.size()-1:
if bones_in_chain.size() > 2:
# Get the bone node for this bone, and the previous bone
var b_target = bone_nodes[i].global_transform
var b_target_two = bone_nodes[i-1].global_transform
# Convert the bone nodes positions from world space to bone/skeleton space
b_target.origin = skeleton.global_transform.xform_inv(b_target.origin)
b_target_two.origin = skeleton.global_transform.xform_inv(b_target_two.origin)
# Get the direction that the previous bone is pointing towards
var dir = (target.global_transform.origin - b_target_two.origin).normalized()
# Make this bone look in the same the direction as the last bone
bone_trans = bone_trans.looking_at(b_target.origin + dir, Vector3(0, 1, 0))
else:
var b_target = target.global_transform
b_target.origin = skeleton.global_transform.xform_inv(b_target.origin)
bone_trans = bone_trans.looking_at(b_target.origin, Vector3(0, 1, 0))
# If this is NOT the last bone in the bone chain, rotate the bone to look at the next
# bone in the bone chain.
else:
# Get the bone node for this bone, and the next bone
var b_target = bone_nodes[i].global_transform
var b_target_two = bone_nodes[i+1].global_transform
# Convert the bone nodes positions from world space to bone/skeleton space
b_target.origin = skeleton.global_transform.xform_inv(b_target.origin)
b_target_two.origin = skeleton.global_transform.xform_inv(b_target_two.origin)
# Get the direction towards the next bone
var dir = (b_target_two.origin - b_target.origin).normalized()
# Make this bone look towards the direction of the next bone
bone_trans = bone_trans.looking_at(b_target.origin + dir, Vector3(0, 1, 0))
# The the bone's (updated) transform
set_bone_transform(i, bone_trans)
func get_bone_transform(bone, convert_to_world_space=true):
# Get the global transform of the bone
var ret = skeleton.get_bone_global_pose(bone_IDs[bones_in_chain[bone]])
# If we need to convert the bone position from bone/skeleton space to world space, we
# use the Xform of the skeleton (because bone/skeleton space is relative to the position of the skeleton node).
if convert_to_world_space == true:
ret.origin = skeleton.global_transform.xform(ret.origin)
return ret
func set_bone_transform(bone, trans):
# Set the global transform of the bone
skeleton.set_bone_global_pose(bone_IDs[bones_in_chain[bone]], trans)

Binary file not shown.

After

Width:  |  Height:  |  Size: 180 B

View File

@@ -0,0 +1,33 @@
[remap]
importer="texture"
type="StreamTexture"
path.s3tc="res://.import/editor_gizmo_texture.png-be14d96c2d7829c8511766ceb15d5a7f.s3tc.stex"
path.etc2="res://.import/editor_gizmo_texture.png-be14d96c2d7829c8511766ceb15d5a7f.etc2.stex"
[deps]
source_file="res://addons/sade/editor_gizmo_texture.png"
source_md5="14289d2a3712e442d3d3adf307a54241"
dest_files=[ "res://.import/editor_gizmo_texture.png-be14d96c2d7829c8511766ceb15d5a7f.s3tc.stex", "res://.import/editor_gizmo_texture.png-be14d96c2d7829c8511766ceb15d5a7f.etc2.stex" ]
dest_md5="3279a3a982c66d6f404c81517b218531"
[params]
compress/mode=2
compress/lossy_quality=0.7
compress/hdr_mode=0
compress/normal_map=0
flags/repeat=true
flags/filter=false
flags/mipmaps=true
flags/anisotropic=false
flags/srgb=1
process/fix_alpha_border=true
process/premult_alpha=false
process/HDR_as_SRGB=false
stream=false
size_limit=0
detect_3d=false
svg/scale=1.0

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.2 KiB

View File

@@ -0,0 +1,32 @@
[remap]
importer="texture"
type="StreamTexture"
path="res://.import/ik_fabrik.png-c3d637ec075c87710a4a8abbfbd526e1.stex"
[deps]
source_file="res://addons/SADE/ik_fabrik.png"
source_md5="2909090602f64d38ce0bb7314ec7b39d"
dest_files=[ "res://.import/ik_fabrik.png-c3d637ec075c87710a4a8abbfbd526e1.stex" ]
dest_md5="80bbb72f55f6ea1f119b08dc61b9526e"
[params]
compress/mode=0
compress/lossy_quality=0.7
compress/hdr_mode=0
compress/normal_map=0
flags/repeat=0
flags/filter=true
flags/mipmaps=false
flags/anisotropic=false
flags/srgb=2
process/fix_alpha_border=true
process/premult_alpha=false
process/HDR_as_SRGB=false
stream=false
size_limit=0
detect_3d=true
svg/scale=1.0

View File

@@ -0,0 +1,205 @@
tool
extends Spatial
export (NodePath) var skeleton_path setget _set_skeleton_path
export (String) var bone_name = ""
export (int, "_process", "_physics_process", "_notification", "none") var update_mode = 0 setget _set_update
export (int, "X-up", "Y-up", "Z-up") var look_at_axis = 1
export (bool) var use_our_rot_x = false
export (bool) var use_our_rot_y = false
export (bool) var use_our_rot_z = false
export (bool) var use_negative_our_rot = false
export (Vector3) var additional_rotation = Vector3()
export (bool) var debug_messages = false
var skeleton_to_use
var first_call = true
const empty_vector = Vector3()
func _ready():
set_process(false)
set_physics_process(false)
set_notify_transform(false)
if update_mode == 0:
set_process(true)
elif update_mode == 1:
set_physics_process(true)
elif update_mode == 2:
set_notify_transform(true)
else:
if debug_messages == true:
print (name, " - IK_LookAt: Unknown update mode. NOT updating skeleton")
if Engine.editor_hint == true:
_setup_for_editor()
func _setup_for_editor():
# So we can see the target in the editor, let's create a mesh instance,
# Add it as our child, and name it
var indicator = MeshInstance.new()
add_child(indicator)
indicator.name = "(EditorOnly) Visual indicator"
# We need to make a mesh for the mesh instance.
# The code below makes a small sphere mesh
var indicator_mesh = SphereMesh.new()
indicator_mesh.radius = 0.1
indicator_mesh.height = 0.2
indicator_mesh.radial_segments = 8
indicator_mesh.rings = 4
# The mesh needs a material (unless we want to use the defualt one).
# Let's create a material and use the EditorGizmoTexture to texture it.
var indicator_material = SpatialMaterial.new()
indicator_material.flags_unshaded = true
indicator_material.albedo_texture = preload("editor_gizmo_texture.png")
indicator_material.albedo_color = Color(1, 0.5, 0, 1)
indicator_mesh.material = indicator_material
indicator.mesh = indicator_mesh
func _set_update(new_value):
update_mode = new_value
# Set all of our processes to false
set_process(false)
set_physics_process(false)
set_notify_transform(false)
# Based on the value of upate, change how we handle updating the skeleton
if update_mode == 0:
set_process(true)
if debug_messages == true:
print (name, " - IK_LookAt: updating skeleton using _process...")
elif update_mode == 1:
set_physics_process(true)
if debug_messages == true:
print (name, " - IK_LookAt: updating skeleton using _physics_process...")
elif update_mode == 2:
set_notify_transform(true)
if debug_messages == true:
print (name, " - IK_LookAt: updating skeleton using _notification...")
else:
if debug_messages == true:
print (name, " - IK_LookAt: NOT updating skeleton due to unknown update method...")
func _set_skeleton_path(new_value):
# Because get_node doesn't work in the first call, we just want to assign instead
# This is to get around a issue with NodePaths exposed to the editor
if first_call == true:
skeleton_path = new_value
return
# Assign skeleton_path to whatever value is passed
skeleton_path = new_value
if skeleton_path == null:
if debug_messages == true:
print (name, " - IK_LookAt: No Nodepath selected for skeleton_path!")
return
# Get the node at that location, if there is one
var temp = get_node(skeleton_path)
if temp != null:
# If the node has the method "find_bone" then we can assume it is (likely) a skeleton
if temp.has_method("find_bone") == true:
skeleton_to_use = temp
if debug_messages == true:
print (name, " - IK_LookAt: attached to (new) skeleton")
# If not, then it's (likely) not a skeleton
else:
skeleton_to_use = null
if debug_messages == true:
print (name, " - IK_LookAt: skeleton_path does not point to a skeleton!")
else:
if debug_messages == true:
print (name, " - IK_LookAt: No Nodepath selected for skeleton_path!")
func update_skeleton():
# NOTE: Because get_node doesn't work in _ready, we need to skip
# a call before doing anything.
if first_call == true:
first_call = false
if skeleton_to_use == null:
_set_skeleton_path(skeleton_path)
# If we do not have a skeleton and/or we're not supposed to update, then return.
if skeleton_to_use == null:
return
if update_mode >= 3:
return
# Get the bone
var bone = skeleton_to_use.find_bone(bone_name)
# If no bone is found (-1), then return (and optionally print an error)
if bone == -1:
if debug_messages == true:
print (name, " - IK_LookAt: No bone in skeleton found with name [", bone_name, "]!")
return
# get the bone's rest position, and our position
var rest = skeleton_to_use.get_bone_global_pose(bone)
var our_position = global_transform.origin
# Convert our position relative to the skeleton's transform
var target_pos = skeleton_to_use.global_transform.xform_inv(global_transform.origin)
# Call helper's look_at function with the chosen up axis.
if look_at_axis == 0:
rest = rest.looking_at(target_pos, Vector3(1, 0, 0))
elif look_at_axis == 1:
rest = rest.looking_at(target_pos, Vector3(0, 1, 0))
elif look_at_axis == 2:
rest = rest.looking_at(target_pos, Vector3(0, 0, 1))
else:
rest = rest.looking_at(target_pos, Vector3(0, 1, 0))
if debug_messages == true:
print (name, " - IK_LookAt: Unknown look_at_axis value!")
# Get our rotation euler, and the bone's rotation euler
var rest_euler = rest.basis.get_euler()
var self_euler = global_transform.basis.orthonormalized().get_euler()
# If we using negative rotation, we flip our rotation euler
if use_negative_our_rot == true:
self_euler = -self_euler
# Apply our rotation euler, if wanted/required
if use_our_rot_x == true:
rest_euler.x = self_euler.x
if use_our_rot_y == true:
rest_euler.y = self_euler.y
if use_our_rot_z == true:
rest_euler.z = self_euler.z
# Rotate the bone by the (potentially) changed euler angle(s)
rest.basis = Basis(rest_euler)
# If we have additional rotation, then rotate it by the local rotation vectors
if additional_rotation != empty_vector:
rest.basis = rest.basis.rotated(rest.basis.x, deg2rad(additional_rotation.x))
rest.basis = rest.basis.rotated(rest.basis.y, deg2rad(additional_rotation.y))
rest.basis = rest.basis.rotated(rest.basis.z, deg2rad(additional_rotation.z))
# Finally, apply the bone rotation to the skeleton
skeleton_to_use.set_bone_global_pose(bone, rest)
# Various upate methods
# ---------------------
func _process(delta):
update_skeleton()
func _physics_process(delta):
update_skeleton()
func _notification(what):
if what == NOTIFICATION_TRANSFORM_CHANGED:
update_skeleton()

Binary file not shown.

After

Width:  |  Height:  |  Size: 328 B

View File

@@ -0,0 +1,32 @@
[remap]
importer="texture"
type="StreamTexture"
path="res://.import/ik_look_at.png-ec8164b5f09a539e05ec8153e50e1d99.stex"
[deps]
source_file="res://addons/SADE/ik_look_at.png"
source_md5="49fed7fb3ba1856215d1f334ed8bc583"
dest_files=[ "res://.import/ik_look_at.png-ec8164b5f09a539e05ec8153e50e1d99.stex" ]
dest_md5="690d9e1323d33b31eefd4014776d78d4"
[params]
compress/mode=0
compress/lossy_quality=0.7
compress/hdr_mode=0
compress/normal_map=0
flags/repeat=0
flags/filter=true
flags/mipmaps=false
flags/anisotropic=false
flags/srgb=2
process/fix_alpha_border=true
process/premult_alpha=false
process/HDR_as_SRGB=false
stream=false
size_limit=0
detect_3d=true
svg/scale=1.0

View File

@@ -0,0 +1,7 @@
[plugin]
name="S.A.D.E (Skeleton additions and extensions)"
description="S.A.D.E is A bunch of helpful nodes designed to make using skeletons in Godot powerful and easy."
author="TwistedTwigleg"
version="0.1.0"
script="plugin_main.gd"

View File

@@ -0,0 +1,21 @@
tool
extends EditorPlugin
func _enter_tree():
# Plugin Initialization here!
# ------ IK STUFF ------
add_custom_type("IK_LookAt", "Spatial", preload("ik_look_at.gd"), preload("ik_look_at.png"))
add_custom_type("IK_FABRIK", "Spatial", preload("ik_fabrik.gd"), preload("ik_fabrik.png"))
# ------ ---------- ------
func _exit_tree():
# Plugin Clean-up here!
# ------ IK STUFF ------
remove_custom_type("IK_LookAt")
remove_custom_type("IK_FABRIK")
# ------ ---------- ------

Binary file not shown.

Binary file not shown.

View File

@@ -0,0 +1,10 @@
extends Button
export (String, FILE) var scene_to_change_to = null
func _ready():
connect("pressed", self, "change_scene")
func change_scene():
if scene_to_change_to != null:
get_tree().change_scene(scene_to_change_to)

101
3d/ik/default_env.tres Normal file
View File

@@ -0,0 +1,101 @@
[gd_resource type="Environment" load_steps=2 format=2]
[sub_resource type="ProceduralSky" id=1]
radiance_size = 4
sky_top_color = Color( 0.0470588, 0.454902, 0.976471, 1 )
sky_horizon_color = Color( 0.556863, 0.823529, 0.909804, 1 )
sky_curve = 0.25
sky_energy = 1.0
ground_bottom_color = Color( 0.101961, 0.145098, 0.188235, 1 )
ground_horizon_color = Color( 0.482353, 0.788235, 0.952941, 1 )
ground_curve = 0.01
ground_energy = 1.0
sun_color = Color( 1, 1, 1, 1 )
sun_latitude = 35.0
sun_longitude = 0.0
sun_angle_min = 1.0
sun_angle_max = 100.0
sun_curve = 0.05
sun_energy = 16.0
texture_size = 2
[resource]
background_mode = 2
background_sky = SubResource( 1 )
background_sky_custom_fov = 0.0
background_color = Color( 0, 0, 0, 1 )
background_energy = 1.0
background_canvas_max_layer = 0
ambient_light_color = Color( 0, 0, 0, 1 )
ambient_light_energy = 1.0
ambient_light_sky_contribution = 1.0
fog_enabled = false
fog_color = Color( 0.5, 0.6, 0.7, 1 )
fog_sun_color = Color( 1, 0.9, 0.7, 1 )
fog_sun_amount = 0.0
fog_depth_enabled = true
fog_depth_begin = 10.0
fog_depth_curve = 1.0
fog_transmit_enabled = false
fog_transmit_curve = 1.0
fog_height_enabled = false
fog_height_min = 0.0
fog_height_max = 100.0
fog_height_curve = 1.0
tonemap_mode = 0
tonemap_exposure = 1.0
tonemap_white = 1.0
auto_exposure_enabled = false
auto_exposure_scale = 0.4
auto_exposure_min_luma = 0.05
auto_exposure_max_luma = 8.0
auto_exposure_speed = 0.5
ss_reflections_enabled = false
ss_reflections_max_steps = 64
ss_reflections_fade_in = 0.15
ss_reflections_fade_out = 2.0
ss_reflections_depth_tolerance = 0.2
ss_reflections_roughness = true
ssao_enabled = false
ssao_radius = 1.0
ssao_intensity = 1.0
ssao_radius2 = 0.0
ssao_intensity2 = 1.0
ssao_bias = 0.01
ssao_light_affect = 0.0
ssao_color = Color( 0, 0, 0, 1 )
ssao_quality = 0
ssao_blur = 3
ssao_edge_sharpness = 4.0
dof_blur_far_enabled = false
dof_blur_far_distance = 10.0
dof_blur_far_transition = 5.0
dof_blur_far_amount = 0.1
dof_blur_far_quality = 1
dof_blur_near_enabled = false
dof_blur_near_distance = 2.0
dof_blur_near_transition = 1.0
dof_blur_near_amount = 0.1
dof_blur_near_quality = 1
glow_enabled = false
glow_levels/1 = false
glow_levels/2 = false
glow_levels/3 = true
glow_levels/4 = false
glow_levels/5 = true
glow_levels/6 = false
glow_levels/7 = false
glow_intensity = 0.8
glow_strength = 1.0
glow_bloom = 0.0
glow_blend_mode = 2
glow_hdr_threshold = 1.0
glow_hdr_scale = 2.0
glow_bicubic_upscale = false
adjustment_enabled = false
adjustment_brightness = 1.0
adjustment_contrast = 1.0
adjustment_saturation = 1.0

241
3d/ik/example_player.gd Normal file
View File

@@ -0,0 +1,241 @@
extends KinematicBody
# Walking variables.
const norm_grav = -38.8
var vel = Vector3()
const MAX_SPEED = 22
const JUMP_SPEED = 26
const ACCEL= 8.5
# A vector for storing the direction the player intends to walk towards.
var dir = Vector3()
# Sprinting variables. Similar to the varibles above, just allowing for quicker movement
const MAX_SPRINT_SPEED = 34
const SPRINT_ACCEL = 18
# A boolean to track whether or not we are sprinting
var is_sprinting = false
# How fast we slow down, and the steepest angle we can climb.
const DEACCEL= 28
const MAX_SLOPE_ANGLE = 40
# We need the camera for getting directional vectors. We rotate ourselves on the Y-axis using
# the camera_holder to avoid rotating on more than one axis at a time.
var camera
var camera_holder
# You may need to adjust depending on the sensitivity of your mouse
var MOUSE_SENSITIVITY = 0.08
# A boolean for tracking whether the jump button is down
var jump_button_down = false
# The current lean value (our position on the lean track) and the path follow node
var lean_value = 0.5
var path_follow_node = null
# A variable for tracking if the right mouse button is down.
var right_mouse_down = false
# A variable for tracking if we can fire using the left mouse button
var left_mouse_timer = 0
const LEFT_MOUSE_FIRE_TIME = 0.15
# How fast the bullets launch
const BULLET_SPEED = 100
# The animation player for aiming down the sights
var anim_player = null
# A boolean for tracking whether we can change animations or not
var anim_done = true
# The current animation name
var current_anim = "Starter"
# The end of the pistol
var pistol_end = null
# The simple bullet rigidbody
var simple_bullet = preload("res://simple_bullet.tscn")
func _ready():
camera = get_node("CameraHolder/Lean_Path/PathFollow/IK_LookAt_Chest/Camera")
camera_holder = get_node("CameraHolder")
path_follow_node = get_node("CameraHolder/Lean_Path/PathFollow")
anim_player = get_node("CameraHolder/AnimationPlayer")
anim_player.connect("animation_finished", self, "animation_finished")
pistol_end = get_node("CameraHolder/Weapon/Pistol/Pistol_end")
set_physics_process(true)
Input.set_mouse_mode(Input.MOUSE_MODE_CAPTURED)
set_process_input(true)
func _physics_process(delta):
process_input(delta)
process_movement(delta)
func process_input(delta):
# Reset dir, so our previous movement does not effect us
dir = Vector3()
# Get the camera's global transform so we can use its directional vectors
var cam_xform = camera.get_global_transform()
# ----------------------------------
# Walking
if Input.is_key_pressed(KEY_UP) or Input.is_key_pressed(KEY_W):
dir += -cam_xform.basis[2]
if Input.is_key_pressed(KEY_DOWN) or Input.is_key_pressed(KEY_S):
dir += cam_xform.basis[2]
if Input.is_key_pressed(KEY_LEFT) or Input.is_key_pressed(KEY_A):
dir += -cam_xform.basis[0]
if Input.is_key_pressed(KEY_RIGHT) or Input.is_key_pressed(KEY_D):
dir += cam_xform.basis[0]
if Input.is_action_just_pressed("ui_cancel"):
if Input.get_mouse_mode() == Input.MOUSE_MODE_VISIBLE:
Input.set_mouse_mode(Input.MOUSE_MODE_CAPTURED)
else:
Input.set_mouse_mode(Input.MOUSE_MODE_VISIBLE)
if Input.is_mouse_button_pressed(2):
if right_mouse_down == false:
right_mouse_down = true
if anim_done == true:
if current_anim != "Aiming":
anim_player.play("Aiming")
current_anim = "Aiming"
else:
anim_player.play("Idle")
current_anim = "Idle"
anim_done = false
else:
right_mouse_down = false
if Input.is_mouse_button_pressed(1):
if left_mouse_timer <= 0:
left_mouse_timer = LEFT_MOUSE_FIRE_TIME
# Create a bullet
var new_bullet = simple_bullet.instance()
get_tree().root.add_child(new_bullet)
new_bullet.global_transform = pistol_end.global_transform
new_bullet.linear_velocity = new_bullet.global_transform.basis.z * BULLET_SPEED
if left_mouse_timer > 0:
left_mouse_timer -= delta
# ----------------------------------
# ----------------------------------
# Sprinting
if Input.is_key_pressed(KEY_SHIFT):
is_sprinting = true
else:
is_sprinting = false
# ----------------------------------
# ----------------------------------
# Jumping
if Input.is_key_pressed(KEY_SPACE):
if jump_button_down == false:
jump_button_down = true
if is_on_floor():
vel.y = JUMP_SPEED
else:
jump_button_down = false
# ----------------------------------
# ----------------------------------
# Leaninng
if Input.is_key_pressed(KEY_Q):
lean_value += 1.2 * delta
elif Input.is_key_pressed(KEY_E):
lean_value -= 1.2 * delta
else:
if lean_value > 0.5:
lean_value -= 1 * delta
if lean_value < 0.5:
lean_value = 0.5
elif lean_value < 0.5:
lean_value += 1 * delta
if lean_value > 0.5:
lean_value = 0.5
lean_value = clamp(lean_value, 0, 1)
path_follow_node.unit_offset = lean_value
if lean_value < 0.5:
var lerp_value = lean_value * 2
path_follow_node.rotation_degrees.z = (20 * (1 - lerp_value))
else:
var lerp_value = (lean_value - 0.5) * 2
path_follow_node.rotation_degrees.z = (-20 * lerp_value)
# ----------------------------------
func process_movement(delta):
var grav = norm_grav
dir.y = 0
dir = dir.normalized()
vel.y += delta*grav
var hvel = vel
hvel.y = 0
var target = dir
if is_sprinting:
target *= MAX_SPRINT_SPEED
else:
target *= MAX_SPEED
var accel
if dir.dot(hvel) > 0:
if is_sprinting == false:
accel = ACCEL
else:
accel = SPRINT_ACCEL
else:
accel = DEACCEL
hvel = hvel.linear_interpolate(target, accel*delta)
vel.x = hvel.x
vel.z = hvel.z
vel = move_and_slide(vel,Vector3(0,1,0))
# Mouse based camera movement
func _input(event):
if event is InputEventMouseMotion && Input.get_mouse_mode() == Input.MOUSE_MODE_CAPTURED:
rotate_y(deg2rad(event.relative.x * MOUSE_SENSITIVITY * -1))
camera_holder.rotate_x(deg2rad(event.relative.y * MOUSE_SENSITIVITY))
# We need to clamp the camera's rotation so we cannot rotate ourselves upside down
var camera_rot = camera_holder.rotation_degrees
if camera_rot.x < -40:
camera_rot.x = -40
elif camera_rot.x > 60:
camera_rot.x = 60
camera_holder.rotation_degrees = camera_rot
else:
pass
func animation_finished(anim):
anim_done = true

629
3d/ik/fabrik_ik.tscn Normal file
View File

@@ -0,0 +1,629 @@
[gd_scene load_steps=15 format=2]
[ext_resource path="res://addons/sade/editor_gizmo_texture.png" type="Texture" id=1]
[ext_resource path="res://godot_battle_bot.dae" type="PackedScene" id=2]
[ext_resource path="res://Target_From_MousePos.gd" type="Script" id=3]
[ext_resource path="res://addons/sade/ik_look_at.gd" type="Script" id=4]
[ext_resource path="res://addons/sade/ik_look_at.png" type="Texture" id=5]
[ext_resource path="res://addons/SADE/IK_FABRIK.gd" type="Script" id=6]
[ext_resource path="res://addons/SADE/IK_FABRIK.png" type="Texture" id=7]
[ext_resource path="res://Button_Change_Scene.gd" type="Script" id=8]
[sub_resource type="PlaneMesh" id=1]
size = Vector2( 40, 40 )
subdivide_width = 0
subdivide_depth = 0
[sub_resource type="SpatialMaterial" id=2]
render_priority = 0
flags_transparent = false
flags_unshaded = false
flags_vertex_lighting = false
flags_no_depth_test = false
flags_use_point_size = false
flags_world_triplanar = false
flags_fixed_size = false
flags_albedo_tex_force_srgb = false
vertex_color_use_as_albedo = false
vertex_color_is_srgb = false
params_diffuse_mode = 0
params_specular_mode = 0
params_blend_mode = 0
params_cull_mode = 0
params_depth_draw_mode = 0
params_line_width = 1.0
params_point_size = 1.0
params_billboard_mode = 0
params_grow = false
params_use_alpha_scissor = false
albedo_color = Color( 1, 1, 1, 1 )
albedo_texture = ExtResource( 1 )
metallic = 0.0
metallic_specular = 0.5
metallic_texture_channel = 0
roughness = 0.2
roughness_texture_channel = 0
emission_enabled = false
normal_enabled = false
rim_enabled = false
clearcoat_enabled = false
anisotropy_enabled = false
ao_enabled = false
depth_enabled = false
subsurf_scatter_enabled = false
transmission_enabled = false
refraction_enabled = false
detail_enabled = false
uv1_scale = Vector3( 0.25, 0.25, 0.25 )
uv1_offset = Vector3( 0, 0, 0 )
uv1_triplanar = true
uv1_triplanar_sharpness = 1.0
uv2_scale = Vector3( 1, 1, 1 )
uv2_offset = Vector3( 0, 0, 0 )
uv2_triplanar = false
uv2_triplanar_sharpness = 1.0
proximity_fade_enable = false
distance_fade_enable = false
_sections_unfolded = [ "UV1" ]
[sub_resource type="ProceduralSky" id=3]
radiance_size = 4
sky_top_color = Color( 0.0470588, 0.454902, 0.976471, 1 )
sky_horizon_color = Color( 0.556863, 0.823529, 0.909804, 1 )
sky_curve = 0.25
sky_energy = 1.0
ground_bottom_color = Color( 0.101961, 0.145098, 0.188235, 1 )
ground_horizon_color = Color( 0.482353, 0.788235, 0.952941, 1 )
ground_curve = 0.01
ground_energy = 1.0
sun_color = Color( 1, 1, 1, 1 )
sun_latitude = 35.0
sun_longitude = 0.0
sun_angle_min = 1.0
sun_angle_max = 100.0
sun_curve = 0.05
sun_energy = 16.0
texture_size = 2
[sub_resource type="Environment" id=4]
background_mode = 2
background_sky = SubResource( 3 )
background_sky_custom_fov = 0.0
background_color = Color( 0, 0, 0, 1 )
background_energy = 1.0
background_canvas_max_layer = 0
ambient_light_color = Color( 0, 0, 0, 1 )
ambient_light_energy = 1.0
ambient_light_sky_contribution = 1.0
fog_enabled = false
fog_color = Color( 0.5, 0.6, 0.7, 1 )
fog_sun_color = Color( 1, 0.9, 0.7, 1 )
fog_sun_amount = 0.0
fog_depth_enabled = true
fog_depth_begin = 10.0
fog_depth_curve = 1.0
fog_transmit_enabled = false
fog_transmit_curve = 1.0
fog_height_enabled = false
fog_height_min = 0.0
fog_height_max = 100.0
fog_height_curve = 1.0
tonemap_mode = 3
tonemap_exposure = 1.0
tonemap_white = 1.0
auto_exposure_enabled = false
auto_exposure_scale = 0.4
auto_exposure_min_luma = 0.05
auto_exposure_max_luma = 8.0
auto_exposure_speed = 0.5
ss_reflections_enabled = false
ss_reflections_max_steps = 64
ss_reflections_fade_in = 0.15
ss_reflections_fade_out = 2.0
ss_reflections_depth_tolerance = 0.2
ss_reflections_roughness = true
ssao_enabled = false
ssao_radius = 1.0
ssao_intensity = 1.0
ssao_radius2 = 0.0
ssao_intensity2 = 1.0
ssao_bias = 0.01
ssao_light_affect = 0.0
ssao_color = Color( 0, 0, 0, 1 )
ssao_quality = 0
ssao_blur = 3
ssao_edge_sharpness = 4.0
dof_blur_far_enabled = false
dof_blur_far_distance = 10.0
dof_blur_far_transition = 5.0
dof_blur_far_amount = 0.1
dof_blur_far_quality = 1
dof_blur_near_enabled = false
dof_blur_near_distance = 2.0
dof_blur_near_transition = 1.0
dof_blur_near_amount = 0.1
dof_blur_near_quality = 1
glow_enabled = true
glow_levels/1 = true
glow_levels/2 = true
glow_levels/3 = true
glow_levels/4 = false
glow_levels/5 = false
glow_levels/6 = false
glow_levels/7 = false
glow_intensity = 0.2
glow_strength = 1.0
glow_bloom = 0.03
glow_blend_mode = 0
glow_hdr_threshold = 1.0
glow_hdr_scale = 2.0
glow_bicubic_upscale = false
adjustment_enabled = false
adjustment_brightness = 1.0
adjustment_contrast = 1.0
adjustment_saturation = 1.0
_sections_unfolded = [ "Glow", "Glow/levels" ]
[sub_resource type="CubeMesh" id=5]
size = Vector3( 1, 1, 1 )
subdivide_width = 0
subdivide_height = 0
subdivide_depth = 0
[sub_resource type="SpatialMaterial" id=6]
render_priority = 0
flags_transparent = false
flags_unshaded = false
flags_vertex_lighting = false
flags_no_depth_test = false
flags_use_point_size = false
flags_world_triplanar = false
flags_fixed_size = false
flags_albedo_tex_force_srgb = false
vertex_color_use_as_albedo = false
vertex_color_is_srgb = false
params_diffuse_mode = 0
params_specular_mode = 0
params_blend_mode = 0
params_cull_mode = 0
params_depth_draw_mode = 0
params_line_width = 1.0
params_point_size = 1.0
params_billboard_mode = 0
params_grow = false
params_use_alpha_scissor = false
albedo_color = Color( 0, 0.191406, 0.765625, 1 )
metallic = 0.0
metallic_specular = 0.5
metallic_texture_channel = 0
roughness = 0.0
roughness_texture_channel = 0
emission_enabled = false
normal_enabled = false
rim_enabled = false
clearcoat_enabled = false
anisotropy_enabled = false
ao_enabled = false
depth_enabled = false
subsurf_scatter_enabled = false
transmission_enabled = false
refraction_enabled = false
detail_enabled = false
uv1_scale = Vector3( 1, 1, 1 )
uv1_offset = Vector3( 0, 0, 0 )
uv1_triplanar = false
uv1_triplanar_sharpness = 1.0
uv2_scale = Vector3( 1, 1, 1 )
uv2_offset = Vector3( 0, 0, 0 )
uv2_triplanar = false
uv2_triplanar_sharpness = 1.0
proximity_fade_enable = false
distance_fade_enable = false
_sections_unfolded = [ "Albedo" ]
[node name="FABRIK_IK" type="Spatial"]
[node name="Floor_plane" type="MeshInstance" parent="." index="0"]
layers = 1
material_override = null
cast_shadow = 1
extra_cull_margin = 0.0
use_in_baked_light = false
lod_min_distance = 0.0
lod_min_hysteresis = 0.0
lod_max_distance = 0.0
lod_max_hysteresis = 0.0
mesh = SubResource( 1 )
skeleton = NodePath("..")
material/0 = SubResource( 2 )
_sections_unfolded = [ "material" ]
[node name="DirectionalLight" type="DirectionalLight" parent="." index="1"]
transform = Transform( 0.56827, 0.673454, -0.472789, 0, 0.574581, 0.818448, 0.822842, -0.465099, 0.326517, -9.77531, 11.5204, 11.766 )
layers = 1
light_color = Color( 1, 1, 1, 1 )
light_energy = 1.0
light_indirect_energy = 1.0
light_negative = false
light_specular = 0.5
light_bake_mode = 1
light_cull_mask = -1
shadow_enabled = false
shadow_color = Color( 0, 0, 0, 1 )
shadow_bias = 0.1
shadow_contact = 0.0
shadow_reverse_cull_face = false
editor_only = false
directional_shadow_mode = 2
directional_shadow_split_1 = 0.1
directional_shadow_split_2 = 0.2
directional_shadow_split_3 = 0.5
directional_shadow_blend_splits = false
directional_shadow_normal_bias = 0.8
directional_shadow_bias_split_scale = 0.25
directional_shadow_depth_range = 0
directional_shadow_max_distance = 200.0
[node name="WorldEnvironment" type="WorldEnvironment" parent="." index="2"]
environment = SubResource( 4 )
[node name="BattleBot" parent="." index="3" instance=ExtResource( 2 )]
editor/display_folded = true
[node name="Camera" type="Camera" parent="." index="4"]
transform = Transform( 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 11.5014, 8.81922 )
keep_aspect = 1
cull_mask = 1048575
environment = null
h_offset = 0.0
v_offset = 0.0
doppler_tracking = 0
projection = 0
current = false
fov = 70.0
size = 1.0
near = 0.05
far = 100.0
script = ExtResource( 3 )
MOVEMENT_SPEED = -6.0
flip_axis = true
[node name="targets" type="Spatial" parent="Camera" index="0"]
transform = Transform( 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, -5.41814 )
[node name="IK_LookAt_Head" type="Spatial" parent="Camera/targets" index="0"]
script = ExtResource( 4 )
_sections_unfolded = [ "Transform" ]
__meta__ = {
"_editor_icon": ExtResource( 5 )
}
skeleton_path = NodePath("../../../BattleBot/Armature/Skeleton")
bone_name = "Head"
update_mode = 0
look_at_axis = 1
use_our_rot_x = false
use_our_rot_y = false
use_our_rot_z = false
use_negative_our_rot = false
additional_rotation = Vector3( 90, 0, 0 )
debug_messages = false
[node name="IK_FABRIK_Left_Arm" type="Spatial" parent="Camera/targets" index="1"]
editor/display_folded = true
script = ExtResource( 6 )
__meta__ = {
"_editor_icon": ExtResource( 7 )
}
skeleton_path = NodePath("../../../BattleBot/Armature/Skeleton")
bones_in_chain = PoolStringArray( "Left_UpperArm", "Left_LowerArm" )
bones_in_chain_lengths = PoolRealArray( 1.97, 3 )
update_mode = 0
chain_iterations = 10
limit_chain_iterations = false
reset_iterations_on_update = false
use_middle_joint_target = true
[node name="target" type="Spatial" parent="Camera/targets/IK_FABRIK_Left_Arm" index="0"]
editor/display_folded = true
transform = Transform( 0.518503, 0, -0.855076, 0, 1, 0, 0.855076, 0, 0.518503, 1.13159, 0, -0.155596 )
[node name="IK_LookAt_LH" type="Spatial" parent="Camera/targets/IK_FABRIK_Left_Arm/target" index="0"]
transform = Transform( 1, 0, 0, 0, 1, 0, 0, 0, 1, 0.343393, -0.133381, 0.836605 )
script = ExtResource( 4 )
__meta__ = {
"_editor_icon": ExtResource( 5 )
}
skeleton_path = NodePath("../../../../../BattleBot/Armature/Skeleton")
bone_name = "Left_Hand"
update_mode = 0
look_at_axis = 1
use_our_rot_x = false
use_our_rot_y = false
use_our_rot_z = false
use_negative_our_rot = false
additional_rotation = Vector3( 0, 0, 90 )
debug_messages = false
[node name="middle_joint_target" type="Spatial" parent="Camera/targets/IK_FABRIK_Left_Arm" index="1"]
transform = Transform( 1, 0, 0, 0, 1, 0, 0, 0, 1, 7.16849, 0, -5.31922 )
[node name="Left_UpperArm" type="Spatial" parent="Camera/targets/IK_FABRIK_Left_Arm" index="2"]
transform = Transform( -0.66477, 0.0771345, -0.743055, -2.23517e-08, 0.994655, 0.103252, 0.747048, 0.0686391, -0.661217, 1.53444, 0.300478, -3.63533 )
[node name="Left_LowerArm" type="Spatial" parent="Camera/targets/IK_FABRIK_Left_Arm" index="3"]
transform = Transform( -0.773624, -0.0228999, 0.633231, 2.98023e-08, 0.999347, 0.03614, -0.633645, 0.0279588, -0.773119, 2.94998, 0.10378, -2.37569 )
[node name="IK_FABRIK_Right_Arm" type="Spatial" parent="Camera/targets" index="2"]
editor/display_folded = true
script = ExtResource( 6 )
__meta__ = {
"_editor_icon": ExtResource( 7 )
}
skeleton_path = NodePath("../../../BattleBot/Armature/Skeleton")
bones_in_chain = PoolStringArray( "Right_UpperArm", "Right_LowerArm", "Right_Hand" )
bones_in_chain_lengths = PoolRealArray( 1.97, 3, 1.2 )
update_mode = 0
chain_iterations = 2
limit_chain_iterations = false
reset_iterations_on_update = false
use_middle_joint_target = true
[node name="target" type="Spatial" parent="Camera/targets/IK_FABRIK_Right_Arm" index="0"]
editor/display_folded = true
transform = Transform( 1, 0, 0, 0, 1, 0, 0, 0, 1, -0.229958, 0, 0.929313 )
[node name="IK_LookAt_RH" type="Spatial" parent="Camera/targets/IK_FABRIK_Right_Arm/target" index="0"]
transform = Transform( 1, 0, 0, 0, 1, 0, 0, 0, 1, 0.0544824, -0.133381, 0.332403 )
script = ExtResource( 4 )
__meta__ = {
"_editor_icon": ExtResource( 5 )
}
skeleton_path = NodePath("../../../../../BattleBot/Armature/Skeleton")
bone_name = "Right_Hand"
update_mode = 0
look_at_axis = 1
use_our_rot_x = false
use_our_rot_y = false
use_our_rot_z = false
use_negative_our_rot = false
additional_rotation = Vector3( 0, 0, 90 )
debug_messages = false
[node name="middle_joint_target" type="Spatial" parent="Camera/targets/IK_FABRIK_Right_Arm" index="1"]
transform = Transform( 1, 0, 0, 0, 1, 0, 0, 0, 1, -6.34515, 0, -3.7843 )
[node name="Right_UpperArm" type="Spatial" parent="Camera/targets/IK_FABRIK_Right_Arm" index="2"]
transform = Transform( -0.694982, -0.0753926, 0.715064, -7.45058e-09, 0.994488, 0.104854, -0.719028, 0.0728714, -0.691151, -1.53339, 0.300478, -3.63533 )
[node name="Right_LowerArm" type="Spatial" parent="Camera/targets/IK_FABRIK_Right_Arm" index="3"]
transform = Transform( -0.792024, 0.0165705, -0.610266, 0, 0.999631, 0.0271429, 0.61049, 0.0214978, -0.791732, -2.89561, 0.100753, -2.31866 )
[node name="Right_Hand" type="Spatial" parent="Camera/targets/IK_FABRIK_Right_Arm" index="4"]
transform = Transform( -0.678335, 0.00698586, -0.734719, -1.86265e-09, 0.999955, 0.00950778, 0.734753, 0.00644946, -0.678304, -1.07914, 0.0200729, 0.0379109 )
[node name="MeshInstance" type="MeshInstance" parent="Camera/targets" index="3"]
layers = 1
material_override = null
cast_shadow = 1
extra_cull_margin = 0.0
use_in_baked_light = false
lod_min_distance = 0.0
lod_min_hysteresis = 0.0
lod_max_distance = 0.0
lod_max_hysteresis = 0.0
mesh = SubResource( 5 )
skeleton = NodePath("..")
material/0 = SubResource( 6 )
_sections_unfolded = [ "material" ]
[node name="Control" type="Control" parent="." index="5"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_right = 40.0
margin_bottom = 40.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
mouse_filter = 0
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 1
[node name="Panel" type="Panel" parent="Control" index="0"]
modulate = Color( 1, 1, 1, 0.784314 )
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_left = -2.0
margin_top = 530.0
margin_right = 1028.0
margin_bottom = 600.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
mouse_filter = 0
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 1
_sections_unfolded = [ "Visibility" ]
[node name="Label" type="Label" parent="Control/Panel" index="0"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_left = 12.0
margin_top = 10.0
margin_right = 1012.0
margin_bottom = 41.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
mouse_filter = 2
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 4
text = "F.A.B.R.I.K IK
Move mouse to move IK targets
(Using 3 bones in the right hand, only 2 in the left. 3+ recommended)"
align = 1
valign = 1
percent_visible = 1.0
lines_skipped = 0
max_lines_visible = -1
[node name="Label_extra" type="Label" parent="Control/Panel" index="1"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_left = 12.0
margin_top = 80.0
margin_right = 1012.0
margin_bottom = 128.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
mouse_filter = 2
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 4
text = "NOTE: You will get a few errors when saving with FABRIK IK nodes in your scene
This is a known bug. Please ignore the errors for now, as they do not do anything
(They're just annoying. If you find a fix, please add it to the demo repository!)"
align = 1
valign = 1
percent_visible = 1.0
lines_skipped = 0
max_lines_visible = -1
[node name="Label_left" type="Label" parent="Control/Panel" index="2"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_left = 782.0
margin_top = 4.0
margin_right = 895.0
margin_bottom = 18.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
mouse_filter = 2
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 4
text = "Left Hand"
align = 1
percent_visible = 1.0
lines_skipped = 0
max_lines_visible = -1
[node name="Label_right" type="Label" parent="Control/Panel" index="3"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_left = 136.0
margin_top = 5.0
margin_right = 249.0
margin_bottom = 19.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
mouse_filter = 2
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 4
text = "Right Hand"
align = 1
percent_visible = 1.0
lines_skipped = 0
max_lines_visible = -1
[node name="Button_Next" type="Button" parent="Control" index="1"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_left = 900.0
margin_top = 540.0
margin_right = 1019.0
margin_bottom = 590.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
focus_mode = 2
mouse_filter = 0
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 1
toggle_mode = false
enabled_focus_mode = 2
shortcut = null
group = null
text = "Next scene"
flat = false
align = 1
script = ExtResource( 8 )
scene_to_change_to = "res://fps_example.tscn"
[node name="Button_Previous" type="Button" parent="Control" index="2"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_left = 10.0
margin_top = 540.0
margin_right = 129.0
margin_bottom = 590.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
focus_mode = 2
mouse_filter = 0
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 1
toggle_mode = false
enabled_focus_mode = 2
shortcut = null
group = null
text = "Previous scene"
flat = false
align = 1
script = ExtResource( 8 )
scene_to_change_to = "res://look_at_ik.tscn"
[editable path="BattleBot"]

1599
3d/ik/fps_example.tscn Normal file

File diff suppressed because it is too large Load Diff

313
3d/ik/godot_battle_bot.dae Normal file

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load Diff

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

View File

@@ -0,0 +1,33 @@
[remap]
importer="texture"
type="StreamTexture"
path.s3tc="res://.import/godot_battle_bot_colors.png-e31963bb1727b598c8ab928a0383fa54.s3tc.stex"
path.etc2="res://.import/godot_battle_bot_colors.png-e31963bb1727b598c8ab928a0383fa54.etc2.stex"
[deps]
source_file="res://godot_battle_bot_colors.png"
source_md5="12a4d2c319a38483b2aa8d504f39b777"
dest_files=[ "res://.import/godot_battle_bot_colors.png-e31963bb1727b598c8ab928a0383fa54.s3tc.stex", "res://.import/godot_battle_bot_colors.png-e31963bb1727b598c8ab928a0383fa54.etc2.stex" ]
dest_md5="8fcf2a1031ed729de0ec7489bbbfff50"
[params]
compress/mode=2
compress/lossy_quality=0.7
compress/hdr_mode=0
compress/normal_map=0
flags/repeat=true
flags/filter=true
flags/mipmaps=true
flags/anisotropic=false
flags/srgb=1
process/fix_alpha_border=true
process/premult_alpha=false
process/HDR_as_SRGB=false
stream=false
size_limit=0
detect_3d=false
svg/scale=1.0

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.3 KiB

View File

@@ -0,0 +1,33 @@
[remap]
importer="texture"
type="StreamTexture"
path.s3tc="res://.import/godot_battle_bot_emission.png-c363ccbe8ada8fe822cd5528b54fc924.s3tc.stex"
path.etc2="res://.import/godot_battle_bot_emission.png-c363ccbe8ada8fe822cd5528b54fc924.etc2.stex"
[deps]
source_file="res://godot_battle_bot_emission.png"
source_md5="a9187c4786e7b546dee3dc4fd41f08b2"
dest_files=[ "res://.import/godot_battle_bot_emission.png-c363ccbe8ada8fe822cd5528b54fc924.s3tc.stex", "res://.import/godot_battle_bot_emission.png-c363ccbe8ada8fe822cd5528b54fc924.etc2.stex" ]
dest_md5="34ef476c1425bc7191891768528bbdce"
[params]
compress/mode=2
compress/lossy_quality=0.7
compress/hdr_mode=0
compress/normal_map=0
flags/repeat=true
flags/filter=true
flags/mipmaps=true
flags/anisotropic=false
flags/srgb=1
process/fix_alpha_border=true
process/premult_alpha=false
process/HDR_as_SRGB=false
stream=false
size_limit=0
detect_3d=false
svg/scale=1.0

BIN
3d/ik/gun_color.material Normal file

Binary file not shown.

BIN
3d/ik/gun_emission.material Normal file

Binary file not shown.

BIN
3d/ik/gun_textures.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 760 B

View File

@@ -0,0 +1,33 @@
[remap]
importer="texture"
type="StreamTexture"
path.s3tc="res://.import/gun_textures.png-d86dd13f7bab751a3c0100e83b6188ac.s3tc.stex"
path.etc2="res://.import/gun_textures.png-d86dd13f7bab751a3c0100e83b6188ac.etc2.stex"
[deps]
source_file="res://gun_textures.png"
source_md5="9e2cc48fd22430732940901b58005fef"
dest_files=[ "res://.import/gun_textures.png-d86dd13f7bab751a3c0100e83b6188ac.s3tc.stex", "res://.import/gun_textures.png-d86dd13f7bab751a3c0100e83b6188ac.etc2.stex" ]
dest_md5="7a556ab1eb4119f7a6a81568409d7291"
[params]
compress/mode=2
compress/lossy_quality=0.7
compress/hdr_mode=0
compress/normal_map=0
flags/repeat=true
flags/filter=true
flags/mipmaps=true
flags/anisotropic=false
flags/srgb=1
process/fix_alpha_border=true
process/premult_alpha=false
process/HDR_as_SRGB=false
stream=false
size_limit=0
detect_3d=false
svg/scale=1.0

BIN
3d/ik/icon.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 15 KiB

32
3d/ik/icon.png.import Normal file
View File

@@ -0,0 +1,32 @@
[remap]
importer="texture"
type="StreamTexture"
path="res://.import/icon.png-487276ed1e3a0c39cad0279d744ee560.stex"
[deps]
source_file="res://icon.png"
source_md5="654257205f0755621b814b013fac6039"
dest_files=[ "res://.import/icon.png-487276ed1e3a0c39cad0279d744ee560.stex" ]
dest_md5="09cf0e9e88dbe274951c3d78af897ef4"
[params]
compress/mode=0
compress/lossy_quality=0.7
compress/hdr_mode=0
compress/normal_map=0
flags/repeat=0
flags/filter=true
flags/mipmaps=false
flags/anisotropic=false
flags/srgb=2
process/fix_alpha_border=true
process/premult_alpha=false
process/HDR_as_SRGB=false
stream=false
size_limit=0
detect_3d=true
svg/scale=1.0

383
3d/ik/look_at_ik.tscn Normal file
View File

@@ -0,0 +1,383 @@
[gd_scene load_steps=11 format=2]
[ext_resource path="res://addons/sade/editor_gizmo_texture.png" type="Texture" id=1]
[ext_resource path="res://godot_battle_bot.dae" type="PackedScene" id=2]
[ext_resource path="res://Target_From_MousePos.gd" type="Script" id=3]
[ext_resource path="res://addons/sade/ik_look_at.gd" type="Script" id=4]
[ext_resource path="res://addons/sade/ik_look_at.png" type="Texture" id=5]
[ext_resource path="res://Button_Change_Scene.gd" type="Script" id=6]
[sub_resource type="PlaneMesh" id=1]
size = Vector2( 40, 40 )
subdivide_width = 0
subdivide_depth = 0
[sub_resource type="SpatialMaterial" id=2]
render_priority = 0
flags_transparent = false
flags_unshaded = false
flags_vertex_lighting = false
flags_no_depth_test = false
flags_use_point_size = false
flags_world_triplanar = false
flags_fixed_size = false
flags_albedo_tex_force_srgb = false
vertex_color_use_as_albedo = false
vertex_color_is_srgb = false
params_diffuse_mode = 0
params_specular_mode = 0
params_blend_mode = 0
params_cull_mode = 0
params_depth_draw_mode = 0
params_line_width = 1.0
params_point_size = 1.0
params_billboard_mode = 0
params_grow = false
params_use_alpha_scissor = false
albedo_color = Color( 1, 1, 1, 1 )
albedo_texture = ExtResource( 1 )
metallic = 0.0
metallic_specular = 0.5
metallic_texture_channel = 0
roughness = 0.2
roughness_texture_channel = 0
emission_enabled = false
normal_enabled = false
rim_enabled = false
clearcoat_enabled = false
anisotropy_enabled = false
ao_enabled = false
depth_enabled = false
subsurf_scatter_enabled = false
transmission_enabled = false
refraction_enabled = false
detail_enabled = false
uv1_scale = Vector3( 0.25, 0.25, 0.25 )
uv1_offset = Vector3( 0, 0, 0 )
uv1_triplanar = true
uv1_triplanar_sharpness = 1.0
uv2_scale = Vector3( 1, 1, 1 )
uv2_offset = Vector3( 0, 0, 0 )
uv2_triplanar = false
uv2_triplanar_sharpness = 1.0
proximity_fade_enable = false
distance_fade_enable = false
_sections_unfolded = [ "UV1" ]
[sub_resource type="ProceduralSky" id=3]
radiance_size = 4
sky_top_color = Color( 0.0470588, 0.454902, 0.976471, 1 )
sky_horizon_color = Color( 0.556863, 0.823529, 0.909804, 1 )
sky_curve = 0.25
sky_energy = 1.0
ground_bottom_color = Color( 0.101961, 0.145098, 0.188235, 1 )
ground_horizon_color = Color( 0.482353, 0.788235, 0.952941, 1 )
ground_curve = 0.01
ground_energy = 1.0
sun_color = Color( 1, 1, 1, 1 )
sun_latitude = 35.0
sun_longitude = 0.0
sun_angle_min = 1.0
sun_angle_max = 100.0
sun_curve = 0.05
sun_energy = 16.0
texture_size = 2
[sub_resource type="Environment" id=4]
background_mode = 2
background_sky = SubResource( 3 )
background_sky_custom_fov = 0.0
background_color = Color( 0, 0, 0, 1 )
background_energy = 1.0
background_canvas_max_layer = 0
ambient_light_color = Color( 0, 0, 0, 1 )
ambient_light_energy = 1.0
ambient_light_sky_contribution = 1.0
fog_enabled = false
fog_color = Color( 0.5, 0.6, 0.7, 1 )
fog_sun_color = Color( 1, 0.9, 0.7, 1 )
fog_sun_amount = 0.0
fog_depth_enabled = true
fog_depth_begin = 10.0
fog_depth_curve = 1.0
fog_transmit_enabled = false
fog_transmit_curve = 1.0
fog_height_enabled = false
fog_height_min = 0.0
fog_height_max = 100.0
fog_height_curve = 1.0
tonemap_mode = 3
tonemap_exposure = 1.0
tonemap_white = 1.0
auto_exposure_enabled = false
auto_exposure_scale = 0.4
auto_exposure_min_luma = 0.05
auto_exposure_max_luma = 8.0
auto_exposure_speed = 0.5
ss_reflections_enabled = false
ss_reflections_max_steps = 64
ss_reflections_fade_in = 0.15
ss_reflections_fade_out = 2.0
ss_reflections_depth_tolerance = 0.2
ss_reflections_roughness = true
ssao_enabled = false
ssao_radius = 1.0
ssao_intensity = 1.0
ssao_radius2 = 0.0
ssao_intensity2 = 1.0
ssao_bias = 0.01
ssao_light_affect = 0.0
ssao_color = Color( 0, 0, 0, 1 )
ssao_quality = 0
ssao_blur = 3
ssao_edge_sharpness = 4.0
dof_blur_far_enabled = false
dof_blur_far_distance = 10.0
dof_blur_far_transition = 5.0
dof_blur_far_amount = 0.1
dof_blur_far_quality = 1
dof_blur_near_enabled = false
dof_blur_near_distance = 2.0
dof_blur_near_transition = 1.0
dof_blur_near_amount = 0.1
dof_blur_near_quality = 1
glow_enabled = true
glow_levels/1 = true
glow_levels/2 = true
glow_levels/3 = true
glow_levels/4 = false
glow_levels/5 = false
glow_levels/6 = false
glow_levels/7 = false
glow_intensity = 0.2
glow_strength = 1.0
glow_bloom = 0.03
glow_blend_mode = 0
glow_hdr_threshold = 1.0
glow_hdr_scale = 2.0
glow_bicubic_upscale = false
adjustment_enabled = false
adjustment_brightness = 1.0
adjustment_contrast = 1.0
adjustment_saturation = 1.0
_sections_unfolded = [ "Glow", "Glow/levels" ]
[node name="LookAt_IK" type="Spatial"]
[node name="Floor_plane" type="MeshInstance" parent="." index="0"]
layers = 1
material_override = null
cast_shadow = 1
extra_cull_margin = 0.0
use_in_baked_light = false
lod_min_distance = 0.0
lod_min_hysteresis = 0.0
lod_max_distance = 0.0
lod_max_hysteresis = 0.0
mesh = SubResource( 1 )
skeleton = NodePath("..")
material/0 = SubResource( 2 )
_sections_unfolded = [ "material" ]
[node name="DirectionalLight" type="DirectionalLight" parent="." index="1"]
transform = Transform( 0.56827, 0.673454, -0.472789, 0, 0.574581, 0.818448, 0.822842, -0.465099, 0.326517, -9.77531, 11.5204, 11.766 )
layers = 1
light_color = Color( 1, 1, 1, 1 )
light_energy = 1.0
light_indirect_energy = 1.0
light_negative = false
light_specular = 0.5
light_bake_mode = 1
light_cull_mask = -1
shadow_enabled = false
shadow_color = Color( 0, 0, 0, 1 )
shadow_bias = 0.1
shadow_contact = 0.0
shadow_reverse_cull_face = false
editor_only = false
directional_shadow_mode = 2
directional_shadow_split_1 = 0.1
directional_shadow_split_2 = 0.2
directional_shadow_split_3 = 0.5
directional_shadow_blend_splits = false
directional_shadow_normal_bias = 0.8
directional_shadow_bias_split_scale = 0.25
directional_shadow_depth_range = 0
directional_shadow_max_distance = 200.0
[node name="WorldEnvironment" type="WorldEnvironment" parent="." index="2"]
environment = SubResource( 4 )
[node name="BattleBot" parent="." index="3" instance=ExtResource( 2 )]
editor/display_folded = true
[node name="Camera" type="Camera" parent="." index="4"]
transform = Transform( 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 11.5014, 8.81922 )
keep_aspect = 1
cull_mask = 1048575
environment = null
h_offset = 0.0
v_offset = 0.0
doppler_tracking = 0
projection = 0
current = false
fov = 70.0
size = 1.0
near = 0.05
far = 100.0
script = ExtResource( 3 )
MOVEMENT_SPEED = -2.0
flip_axis = true
[node name="targets" type="Spatial" parent="Camera" index="0"]
[node name="IK_LookAt_Head" type="Spatial" parent="Camera/targets" index="0"]
script = ExtResource( 4 )
_sections_unfolded = [ "Transform" ]
__meta__ = {
"_editor_icon": ExtResource( 5 )
}
skeleton_path = NodePath("../../../BattleBot/Armature/Skeleton")
bone_name = "Head"
update_mode = 0
look_at_axis = 1
use_our_rot_x = false
use_our_rot_y = false
use_our_rot_z = false
use_negative_our_rot = false
additional_rotation = Vector3( 90, 0, 0 )
debug_messages = false
[node name="IK_LookAt_LeftArm" type="Spatial" parent="Camera/targets" index="1"]
script = ExtResource( 4 )
_sections_unfolded = [ "Transform" ]
__meta__ = {
"_editor_icon": ExtResource( 5 )
}
skeleton_path = NodePath("../../../BattleBot/Armature/Skeleton")
bone_name = "Left_UpperArm"
update_mode = 0
look_at_axis = 1
use_our_rot_x = false
use_our_rot_y = false
use_our_rot_z = false
use_negative_our_rot = false
additional_rotation = Vector3( 0, 0, 0 )
debug_messages = false
[node name="IK_LookAt_RightArm" type="Spatial" parent="Camera/targets" index="2"]
script = ExtResource( 4 )
_sections_unfolded = [ "Transform" ]
__meta__ = {
"_editor_icon": ExtResource( 5 )
}
skeleton_path = NodePath("../../../BattleBot/Armature/Skeleton")
bone_name = "Right_UpperArm"
update_mode = 0
look_at_axis = 1
use_our_rot_x = false
use_our_rot_y = false
use_our_rot_z = false
use_negative_our_rot = false
additional_rotation = Vector3( 0, 0, 180 )
debug_messages = false
[node name="Control" type="Control" parent="." index="5"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_right = 40.0
margin_bottom = 40.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
mouse_filter = 0
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 1
[node name="Panel" type="Panel" parent="Control" index="0"]
modulate = Color( 1, 1, 1, 0.784314 )
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_left = -2.0
margin_top = 530.0
margin_right = 1028.0
margin_bottom = 600.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
mouse_filter = 0
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 1
_sections_unfolded = [ "Visibility" ]
[node name="Label" type="Label" parent="Control/Panel" index="0"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_left = 12.0
margin_top = 10.0
margin_right = 1012.0
margin_bottom = 41.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
mouse_filter = 2
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 4
text = "LookAt IK
Move mouse to move IK targets"
align = 1
valign = 1
percent_visible = 1.0
lines_skipped = 0
max_lines_visible = -1
[node name="Button_Next" type="Button" parent="Control" index="1"]
anchor_left = 0.0
anchor_top = 0.0
anchor_right = 0.0
anchor_bottom = 0.0
margin_left = 900.0
margin_top = 540.0
margin_right = 1019.0
margin_bottom = 590.0
rect_pivot_offset = Vector2( 0, 0 )
rect_clip_content = false
focus_mode = 2
mouse_filter = 0
mouse_default_cursor_shape = 0
size_flags_horizontal = 1
size_flags_vertical = 1
toggle_mode = false
enabled_focus_mode = 2
shortcut = null
group = null
text = "Next scene"
flat = false
align = 1
script = ExtResource( 6 )
scene_to_change_to = "res://fabrik_ik.tscn"
[editable path="BattleBot"]

28
3d/ik/project.godot Normal file
View File

@@ -0,0 +1,28 @@
; Engine configuration file.
; It's best edited using the editor UI and not directly,
; since the parameters that go here are not all obvious.
;
; Format:
; [section] ; section goes between []
; param=value ; assign values to parameters
config_version=3
[application]
config/name="3D IK"
run/main_scene="res://look_at_ik.tscn"
config/icon="res://icon.png"
[display]
window/stretch/mode="2d"
window/stretch/aspect="keep"
[editor_plugins]
enabled=PoolStringArray( "sade" )
[rendering]
environment/default_environment="res://default_env.tres"

13
3d/ik/simple_bullet.gd Normal file
View File

@@ -0,0 +1,13 @@
extends RigidBody
const KILL_TIME = 5
var timer = 0
func _ready():
set_physics_process(true);
func _physics_process(delta):
timer += delta
if timer > KILL_TIME:
queue_free()
timer = 0 # Make sure we are destroyed before we call this again!

123
3d/ik/simple_bullet.tscn Normal file
View File

@@ -0,0 +1,123 @@
[gd_scene load_steps=5 format=2]
[ext_resource path="res://simple_bullet.gd" type="Script" id=1]
[sub_resource type="SphereMesh" id=1]
radius = 1.0
height = 2.0
radial_segments = 64
rings = 32
is_hemisphere = false
[sub_resource type="SpatialMaterial" id=2]
render_priority = 0
flags_transparent = false
flags_unshaded = false
flags_vertex_lighting = false
flags_no_depth_test = false
flags_use_point_size = false
flags_world_triplanar = false
flags_fixed_size = false
flags_albedo_tex_force_srgb = false
vertex_color_use_as_albedo = false
vertex_color_is_srgb = false
params_diffuse_mode = 0
params_specular_mode = 0
params_blend_mode = 0
params_cull_mode = 0
params_depth_draw_mode = 0
params_line_width = 1.0
params_point_size = 1.0
params_billboard_mode = 0
params_grow = false
params_use_alpha_scissor = false
albedo_color = Color( 0.769531, 0.486969, 0, 1 )
metallic = 0.0
metallic_specular = 0.5
metallic_texture_channel = 0
roughness = 1.0
roughness_texture_channel = 0
emission_enabled = true
emission = Color( 1, 0.445313, 0, 1 )
emission_energy = 1.8
emission_operator = 0
emission_on_uv2 = false
normal_enabled = false
rim_enabled = false
clearcoat_enabled = false
anisotropy_enabled = false
ao_enabled = false
depth_enabled = false
subsurf_scatter_enabled = false
transmission_enabled = false
refraction_enabled = false
detail_enabled = false
uv1_scale = Vector3( 1, 1, 1 )
uv1_offset = Vector3( 0, 0, 0 )
uv1_triplanar = false
uv1_triplanar_sharpness = 1.0
uv2_scale = Vector3( 1, 1, 1 )
uv2_offset = Vector3( 0, 0, 0 )
uv2_triplanar = false
uv2_triplanar_sharpness = 1.0
proximity_fade_enable = false
distance_fade_enable = false
[sub_resource type="SphereShape" id=3]
radius = 0.4
[node name="SimpleBullet" type="RigidBody"]
input_ray_pickable = true
input_capture_on_drag = false
collision_layer = 1
collision_mask = 1
mode = 0
mass = 2.0
friction = 1.0
bounce = 0.5
gravity_scale = 3.0
custom_integrator = false
continuous_cd = true
contacts_reported = 0
contact_monitor = false
sleeping = false
can_sleep = false
axis_lock_linear_x = false
axis_lock_linear_y = false
axis_lock_linear_z = false
axis_lock_angular_x = false
axis_lock_angular_y = false
axis_lock_angular_z = false
linear_velocity = Vector3( 0, 0, 0 )
linear_damp = 0.4
angular_velocity = Vector3( 0, 0, 0 )
angular_damp = -1.0
script = ExtResource( 1 )
[node name="MeshInstance" type="MeshInstance" parent="." index="0"]
transform = Transform( 0.4, 0, 0, 0, 0.4, 0, 0, 0, 0.4, 0, 0, 0 )
layers = 1
material_override = null
cast_shadow = 0
extra_cull_margin = 0.0
use_in_baked_light = false
lod_min_distance = 0.0
lod_min_hysteresis = 0.0
lod_max_distance = 0.0
lod_max_hysteresis = 0.0
mesh = SubResource( 1 )
skeleton = NodePath("..")
material/0 = SubResource( 2 )
_sections_unfolded = [ "Geometry", "Transform", "material" ]
[node name="CollisionShape" type="CollisionShape" parent="." index="1"]
shape = SubResource( 3 )
disabled = false

View File

@@ -0,0 +1,20 @@
extends Camera
var targets = null
export (float) var MOVEMENT_SPEED = 10
export (bool) var flip_axis = false
func _ready():
targets = get_node("targets")
func _process(delta):
var mouse_to_world = project_local_ray_normal(get_viewport().get_mouse_position()) * MOVEMENT_SPEED
if flip_axis == false:
mouse_to_world.z *= -1
else:
mouse_to_world = -mouse_to_world
targets.transform.origin = mouse_to_world

166
3d/ik/weapon_pistol.dae Normal file

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load Diff