Godot Version
4.6
Question
Why is there so much jitter visible on the player in this?
Here are some notes and what I’ve already tried:
- physics interpolation is ON. the jitter goes away if it is off, but of course then the player and camera both move at a very visible 60hz, which doesn’t feel great.
- changing physics jitter fix doesn’t do much.
- both the player and camera target move in _physics_process, with the camera itself updating position by doing
global_transform = camera.target.get_global_transform_interpolated()during it’s _process. I previously tried moving the camera target in _process but the result was largely the same, with neither removing jitter. - both the camera and camera target have Top level on, so they don’t move when the parent characterbody3d moves.
- removing the lerped camera movement does not remove the jitter.
Scene structure
Scripts
CameraTarget
extends Marker3D
@export var OFFSET := Vector3(0, 1, 6)
@export var CAMERA_SPEED := 5
@export var LOOKAROUND_RADIUS := 2
@export var MAX_DISTANCE:= 1
@onready var player = $".."
func _physics_process(delta: float) -> void:
var current_pos = global_position
var lookaround = Input.get_vector(
"look_left",
"look_right",
"look_down",
"look_up"
) * LOOKAROUND_RADIUS
var offset = Vector3(
OFFSET.x + lookaround.x,
OFFSET.y + lookaround.y,
OFFSET.z
)
var target = player.global_position + offset
target = current_pos.lerp(target, delta * CAMERA_SPEED)
global_position = target
Camera3D
extends Camera3D
@onready var camera_target: Marker3D = $"../CameraTarget"
func _process(_delta: float) -> void:
global_transform = camera_target.get_global_transform_interpolated()
Player
extends CharacterBody3D
const MAX_SPEED := 5;
const ACCELERATION := 100;
const JUMP_VELOCITY := 4;
var current_x_velocity: float
func _physics_process(delta: float) -> void:
var move_dir := Input.get_axis("move_left", "move_right");
var desired_x_velocity = move_dir * MAX_SPEED;
current_x_velocity = lerp(current_x_velocity, desired_x_velocity, ACCELERATION * delta)
var jump_modifier = 1;
# cut gravity in half if jump is held to allow higher jumps
if not is_on_floor() && velocity.y > 0 && Input.is_action_pressed("move_jump"):
jump_modifier = 0.5;
if Input.is_action_pressed("move_jump") && is_on_floor():
velocity.y = JUMP_VELOCITY;
velocity = Vector3(current_x_velocity, velocity.y, 0);
# apply gravity
velocity += get_gravity() * delta * jump_modifier;
move_and_slide();
