Getting a direction arrow to rotate on click

Hi, I’m new to Unity and I’m playing around with ways of getting user input.

My aim is to have an arrow rotate around an immobile ball (player) while left click is held down, and later I’d like to right click to hit the ball in the direction the arrow is pointing, but first:

I have a PointerRotator class which moves relative to the ball, and makes an arrow spin around it at a given speed . In the editor, I have this script applied to my Pointer GameObject referencing the Player GameObject.

public class PointerRotator : MonoBehaviour {

    public GameObject player;
    private float speed = 0;
    private Vector3 offset;

    void Start()
    {
        offset = transform.position - player.transform.position;
    }

    void LateUpdate ()
    {
        transform.Rotate(new Vector3(0, 30, 0) * speed * Time.deltaTime);
        transform.position = player.transform.position + offset;
    }

    public void setSpeed(int x)
    {
        speed = (float)x;
    }

    public float getDirection()
    {
        return this.transform.eulerAngles.y;
    }
}

Now, my PlayerController Class, which is applied to my Player GameObject, and in the Editor references my Pointer GameObject as prot .

public class PlayerController : MonoBehaviour {

    public Rigidbody rb;
    public PointerRotator prot;
    private float direction = 0;

    void Start ()
    {
        rb = GetComponent<Rigidbody>();
        prot = GetComponent<PointerRotator>();
    }
    
    private void FixedUpdate()
    {
        if (rb.velocity.magnitude > 0.1)
        {
            prot.setSpeed(0);
        }
        else
        {
            while (Input.GetMouseButtonDown(0) == true)
            {
                prot.setSpeed(10);
                direction = prot.getDirection();
            }
            prot.setSpeed(0);
        }
    }
}

Obviously the ball cannot move yet as I haven’t implemented any way of it doing so. My issue is that when I press down my left mouse button the Pointer doesn’t start rotating. I have a feeling I’m missing some sort of referencing, but I’m not sure.

I’m not getting any errors in the editor (other than PlayerController.direction not being used), and the references during runtime are as I set them.

Any help would be much appreciated. Thank you in advance!

You have to remove the private keyword from FixedUpdate in PlayerController.cs. But wait don’t do it just yet! Otherwise it will be CTRL-ALT_DELETE for you.

Lines 21 -25 of PlayerController.cs.

A while loop is not suitable here. The while loop executes because the mouse button went down in this frame. It will never register that the mosuebutton was released that would require another frame, but you are stuck in this one. So you are spinning your wheels. Setting prot.speed to ten and returning it’s direction (the same direction) over and over again at high speeds. For forever… not really but you can either wait to see if your memory gets full or you can force quit the app.

switch while to if.

change prot.setSpeed(0); to

if ( Input.GetMouseButtonUp(0) )
{
    prot.setSpeed(0);
}

Otherwise right after you set it to ten you set it right to 0 and it will again never move.

Thank you @Jwizard93! Worked great. Need to get into the per-frame-update mindset.

For posterity, this is the correct FixedUpdate method that allows the Pointer to rotate only on mouse button held down:

    void FixedUpdate()
    {
        if (rb.velocity.magnitude > 1)
        {
            prot.setSpeed(0);
        }
        else
        {
            // set arrow pointer active
            if (Input.GetMouseButton(0) == true)
            {
                // activate rotating arrow
                prot.setSpeed(10);

                // update direction
                direction = prot.getDirection();
            }
            else
            {
                // stop rotating arrow if button not pressed
                prot.setSpeed(0);
            }
        }