Browse Source

Fix physics for RigidBody character

master
Luna 7 years ago
parent
commit
18028e0c9e
4 changed files with 62 additions and 53 deletions
  1. +9
    -7
      scenes/heroes/0.tscn
  2. +11
    -9
      scenes/player.tscn
  3. +23
    -11
      scripts/heroes/0.gd
  4. +19
    -26
      scripts/player.gd

+ 9
- 7
scenes/heroes/0.tscn View File

@ -20,23 +20,25 @@ radial_segments = 64
rings = 8 rings = 8
_sections_unfolded = [ "Resource" ] _sections_unfolded = [ "Resource" ]
[node name="RigidBody" type="RigidBody" index="0"]
[node name="RigidBody" type="RigidBody" groups=[
"player",
]]
input_ray_pickable = true input_ray_pickable = true
input_capture_on_drag = false input_capture_on_drag = false
collision_layer = 1 collision_layer = 1
collision_mask = 1 collision_mask = 1
mode = 2 mode = 2
mass = 1.0
friction = 0.0
mass = 100.0
friction = 1.0
bounce = 0.0 bounce = 0.0
gravity_scale = 1.0 gravity_scale = 1.0
custom_integrator = true
continuous_cd = true
contacts_reported = 8
custom_integrator = false
continuous_cd = false
contacts_reported = 4
contact_monitor = true contact_monitor = true
sleeping = false sleeping = false
can_sleep = false
can_sleep = true
axis_lock_linear_x = false axis_lock_linear_x = false
axis_lock_linear_y = false axis_lock_linear_y = false
axis_lock_linear_z = false axis_lock_linear_z = false


+ 11
- 9
scenes/player.tscn View File

@ -20,23 +20,25 @@ radial_segments = 64
rings = 8 rings = 8
_sections_unfolded = [ "Resource" ] _sections_unfolded = [ "Resource" ]
[node name="RigidBody" type="RigidBody" index="0"]
[node name="RigidBody" type="RigidBody" index="0" groups=[
"player",
]]
input_ray_pickable = true input_ray_pickable = true
input_capture_on_drag = false input_capture_on_drag = false
collision_layer = 1 collision_layer = 1
collision_mask = 1 collision_mask = 1
mode = 2 mode = 2
mass = 1.0
friction = 0.0
mass = 200.0
friction = 1.0
bounce = 0.0 bounce = 0.0
gravity_scale = 1.0 gravity_scale = 1.0
custom_integrator = true
continuous_cd = true
contacts_reported = 8
contact_monitor = true
custom_integrator = false
continuous_cd = false
contacts_reported = 0
contact_monitor = false
sleeping = false sleeping = false
can_sleep = false
can_sleep = true
axis_lock_linear_x = false axis_lock_linear_x = false
axis_lock_linear_y = false axis_lock_linear_y = false
axis_lock_linear_z = false axis_lock_linear_z = false
@ -48,7 +50,7 @@ linear_damp = -1.0
angular_velocity = Vector3( 0, 0, 0 ) angular_velocity = Vector3( 0, 0, 0 )
angular_damp = -1.0 angular_damp = -1.0
script = ExtResource( 1 ) script = ExtResource( 1 )
_sections_unfolded = [ "Angular", "Axis Lock", "Collision", "Linear", "Pause", "Transform", "Visibility", "collision" ]
_sections_unfolded = [ "Angular", "Axis Lock", "Collision", "Linear", "Transform", "Visibility", "collision" ]
[node name="Body" type="CollisionShape" parent="." index="0"] [node name="Body" type="CollisionShape" parent="." index="0"]


+ 23
- 11
scripts/heroes/0.gd View File

@ -1,9 +1,8 @@
extends "res://scripts/player.gd" extends "res://scripts/player.gd"
const wallride_speed = 0
const wallride_speed_necessary = 15
const wallride_leap_height = 20
const wallride_leap_side = 10
const wallride_speed_necessary = 2
const wallride_leap_height = 14
const wallride_leap_side = 8
var since_on_wall = 0 var since_on_wall = 0
var last_wall_normal = Vector3() var last_wall_normal = Vector3()
@ -16,25 +15,38 @@ func control_player(state):
func wallride(state): func wallride(state):
var ray = get_node("Ray") var ray = get_node("Ray")
var vel = get_linear_velocity()
var vel = state.get_linear_velocity()
# If our feet aren't touching, but we are colliding, we are wall-riding # If our feet aren't touching, but we are colliding, we are wall-riding
if !ray.is_colliding() and get_colliding_bodies() and vel.length() > wallride_speed_necessary: if !ray.is_colliding() and get_colliding_bodies() and vel.length() > wallride_speed_necessary:
since_on_wall = 0
last_wall_normal = state.get_contact_local_normal()
last_wall_normal = state.get_contact_local_normal(0)
# Make sure it isn't the floor
if last_wall_normal.dot(Vector3(0,1,0)) < 0.95:
since_on_wall = 0
else: else:
since_on_wall += delta
since_on_wall += state.get_step()
debug_node.set_text(str(since_on_wall < wallride_forgiveness))
if since_on_wall < wallride_forgiveness: if since_on_wall < wallride_forgiveness:
var aim = get_node("Yaw").get_global_transform().basis
# Add zero gravity # Add zero gravity
set_gravity_scale(0) set_gravity_scale(0)
# Remove any momentum we may have
state.set_linear_velocity(Vector3(vel.x, 0, vel.z))
# Because 1/2 of our energy is wasted in the wall, get more forwards/backwards here:
var aim = get_node("Yaw").get_global_transform().basis
if Input.is_action_pressed("move_forwards"):
apply_impulse(Vector3(), -air_accel * aim[2] * get_mass())
if Input.is_action_pressed("move_backwards"):
apply_impulse(Vector3(), air_accel * aim[2] * get_mass())
# Allow jumping (for wall hopping!) # Allow jumping (for wall hopping!)
if Input.is_action_just_pressed("jump"): if Input.is_action_just_pressed("jump"):
var jump_impulse = -wallride_leap_side * last_wall_normal
var jump_impulse = wallride_leap_side * last_wall_normal
jump_impulse.y += wallride_leap_height jump_impulse.y += wallride_leap_height
state.apply_impulse(Vector3(), jump_impulse)
set_gravity_scale(1) # Jumping requires gravity
state.apply_impulse(Vector3(), jump_impulse * get_mass())
else: else:
# We need to return to falling (we aren't riding anymore) # We need to return to falling (we aren't riding anymore)
set_gravity_scale(1) set_gravity_scale(1)
state.integrate_forces()

+ 19
- 26
scripts/player.gd View File

@ -11,13 +11,14 @@ var pitch = 0
var timer = 0 var timer = 0
# Walking speed and jumping height are defined later. # Walking speed and jumping height are defined later.
var walk_speed = 3
var jump_speed = 15
const air_accel = .5
var walk_speed = 2
var jump_speed = 3
const air_accel = .6
var floor_friction = 0.92
var air_friction = 0.98
var health = 100 var health = 100
var stamina = 10000 var stamina = 10000
var ray_length = 10
var debug_node var debug_node
@ -69,11 +70,6 @@ slave func set_status(tf, lv, av):
set_angular_velocity(av) set_angular_velocity(av)
func control_player(state): func control_player(state):
# Default walk speed:
walk_speed = 5
# Default jump height:
jump_speed = 3
var aim = get_node("Yaw").get_global_transform().basis var aim = get_node("Yaw").get_global_transform().basis
@ -90,8 +86,6 @@ func control_player(state):
direction = direction.normalized() direction = direction.normalized()
var ray = get_node("Ray") var ray = get_node("Ray")
#print("---")
if ray.is_colliding(): if ray.is_colliding():
var up = state.get_total_gravity().normalized() var up = state.get_total_gravity().normalized()
@ -115,26 +109,25 @@ func control_player(state):
floor_velocity += tf.xform_inv(point) - point floor_velocity += tf.xform_inv(point) - point
yaw = fmod(yaw + rad2deg(floor_angular_vel.y) * state.get_step(), 360) yaw = fmod(yaw + rad2deg(floor_angular_vel.y) * state.get_step(), 360)
get_node("Yaw").set_rotation(Vector3(0, deg2rad(yaw), 0)) get_node("Yaw").set_rotation(Vector3(0, deg2rad(yaw), 0))
print("isRB||isSB")
var diff = floor_velocity + direction * walk_speed - state.get_linear_velocity()
var vertdiff = aim[1] * diff.dot(aim[1])
print("VD: " + str(vertdiff))
diff -= vertdiff
diff = diff.normalized() * clamp(diff.length(), 0, max_accel / state.get_step())
diff += vertdiff
print("D: " + str(diff))
apply_impulse(Vector3(), diff * get_mass())
var diff = floor_velocity + direction * walk_speed
state.apply_impulse(Vector3(), diff * get_mass())
var lin_v = state.get_linear_velocity()
lin_v.x *= floor_friction
lin_v.z *= floor_friction
state.set_linear_velocity(lin_v)
if Input.is_action_pressed("jump"): if Input.is_action_pressed("jump"):
apply_impulse(Vector3(), normal * jump_speed * get_mass())
state.apply_impulse(Vector3(), normal * jump_speed * get_mass())
else: else:
apply_impulse(Vector3(), direction * air_accel * get_mass())
print(get_translation())
print(state.get_linear_velocity())
state.apply_impulse(Vector3(), direction * air_accel * get_mass())
var lin_v = state.get_linear_velocity()
lin_v.x *= air_friction
lin_v.z *= air_friction
state.set_linear_velocity(lin_v)
# print(state.get_linear_velocity())
var vel = get_linear_velocity() var vel = get_linear_velocity()
debug_node.set_text("%8.f,%8.f,%8.f" % [vel.x, vel.y, vel.z]) debug_node.set_text("%8.f,%8.f,%8.f" % [vel.x, vel.y, vel.z])


Loading…
Cancel
Save