Getting a jiggly camera with PS4 controller inputs

I’m fooling around with a PS4 controller and am throwing together a simple twin stick shooter.

I want the camera to move towards the direction the player is looking, but for whatever reason the thing ends up jiggling ever so slightly and I can not for the life of me understand why.

I attempted to add a threshold that it needed to pass before the camera would move, but it just seems to completely fail to do anything and I am straight up dumbfounded why.

Here’s my script:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class TestPlayer : MonoBehaviour
{
    public float movementSpeed;
    public float lookRange;
    public float lookSmooth;

    Vector3 movementDirection;
    Vector3 lookDirection;
    Vector3 cameraStartPosition;

    CharacterController myController;
    public Transform myCamera;

    public Transform target;

    // Start is called before the first frame update
    void Start()
    {
        myController = gameObject.GetComponent<CharacterController>();
        cameraStartPosition = myCamera.localPosition;
    }

    // Update is called once per frame
    void Update()
    {
        movementDirection = new Vector3(Input.GetAxis("P1LHor"), 0, Input.GetAxis("P1LVert") * -1);
        myController.Move(movementDirection * movementSpeed * Time.deltaTime);

        Vector3 lastLookDirection = lookDirection;

        lookDirection = new Vector3(Input.GetAxis("P1RHor"), 0, Input.GetAxis("P1RVert") * -1);
        lookDirection = lookDirection * lookRange;
        lookDirection += cameraStartPosition;

        if (Vector3.Distance(lookDirection, lastLookDirection) > lookSmooth){
            myCamera.localPosition = lookDirection;
        }

    }
}

The smoothing function works, but it causes the camera to jump around.

You’re gathering up raw joystick input at line 35.

Then you’re assigning that raw input to the camera’s position at line 40.

That’s exactly zero smoothing. That’s at least part of your jitter.

Instead of directly assigning it to the camera’s location, use either a move-to type construct, or else use Vector3.Lerp to move gradually to the new target.

I like Vector3.Lerp and use it like so:

const float Snappiness = 2.0f;

myCamera.localPosition = Vector3.Lerp( myCamera.localPosition, lookDirection, Snappiness * Time.deltaTime);

but feel free to smooth it however you like.

NOTE: before anyone howls that this is not how to use Vector3.Lerp, just know that I am aware of that; I am using it as a time-weighted low-pass filter, and that is what it is in the above construct.

2 Likes

That worked like a charm, thanks!

1 Like