extends KinematicBody export var rot_chance = 5.0 export var rot_range = PI / 4.0 export var mov_chance = 5.0 export var mov_speed = 1.0 export var mov_length_min = 1.0 export var mov_length_max = 5.0 export var flap_chance = 5.0 export var squak_chance = 5.0 export var peck_chance = 5.0 onready var anim = $AnimationTree func roll_die(chance): return (randf() * 100) <= chance func _physics_process(delta): match anim.wings.get_current_node(): "IDLE": if roll_die(flap_chance): anim.wings.travel("FLAP") "FLAP": pass match anim.state.get_current_node(): "IDLE": state_idle(delta) "MOVING": state_moving(delta) "SQUACK": pass "PECK": pass func state_idle(delta): if roll_die(rot_chance): var ang = randf() * rot_range rotate(Vector3.UP, ang) if roll_die(mov_chance): anim.state.travel("MOVING") var dist = lerp(mov_length_min, mov_length_max, randf()) mov_lerp_pos = 0.0 mov_lerp_step = (mov_speed * delta) / dist var rotation = Transform(self.rotation, Vector3.ZERO) var forward = rotation * Vector3.FORWARD mov_lerp_start = translation mov_lerp_target = translation + (forward * dist) elif roll_die(squak_chance): anim.state.travel("SQUACK") elif roll_die(peck_chance): anim.state.travel("PECK") var mov_lerp_start = Vector3.ZERO var mov_lerp_target = Vector3.ZERO var mov_lerp_step = 0.0 var mov_lerp_pos = 0.0 func state_moving(_delta): if mov_lerp_pos >= 1.0: anim.state.travel("IDLE") return mov_lerp_pos += mov_lerp_step mov_lerp_pos = min(mov_lerp_pos, 1.0) var pos = lerp(mov_lerp_start, mov_lerp_target, mov_lerp_pos) pos = move_and_slide(pos - translation, Vector3.UP)