virtual joystick

I’m trying to create a virtual joystick using DragHandler, how do I make it functional? Because the X and Y directions are not correct, whenever the Vector moves diagonally, it follows my code:

using UnityEngine;
using System.Collections;
using UnityEngine.EventSystems; // Required when using event data

public class Joystick : MonoBehaviour, IDragHandler
{   
   
    public float vy;
    public float hx;
    public float velocidade=0.0f;
    public Transform player;
    

    Vector3 startPosition;

    void Start()
    {       
        startPosition = transform.position;

    }
    void Update()
    {           
        joy ();               
    }
    public void joy()
    {       
        hx = transform.position.x;
        vy  = transform.position.y;


        if (hx > 60.5) {
            player.Translate (Vector3.right * velocidade);
        }

        if (hx < 60.5)
        {
            player.Translate (Vector3.left * velocidade);

        }

        if (vy > 60.5)
        {
            player.Translate (Vector3.forward * velocidade);
            ;
        }

        if (vy < 60.5)
        {
            player.Translate (Vector3.back * velocidade);

        }
        if (hx == 60.5) {
            player.Translate (Vector3.zero );
        }
        if (vy == 60.5) {
            player.Translate (Vector3.zero );
        }

    }

public void OnDrag (PointerEventData eventData)
{
       
        transform.position = Input.mousePosition;

}

    public void clickup (bool up)
    {
       
        if (up == true) {
            transform.position = startPosition;
        }
    }
}

the main issue you are having is the all the if() statements. I’ll be posting some code here shortly

You still need to think about how to solve the diag issue. you had 6 IF() statements that could have true. i’ve lowered it to 2 IF() statements.
Your problem is. when you move the joystick up. you never move it directly up. it’s always moving up and over at the same time. It’s almost impossible to move it strait up with your finger or mouse. so both IF() statements are true, thouse moving it in a diag.

using UnityEngine;
using System.Collections;
using UnityEngine.EventSystems; // Required when using event data

public class Joystick : MonoBehaviour, IDragHandler
{

    public float vy;
    public float hx;
    public float velocidade = 0.0f;
    public Transform player;


    Vector3 startPosition;

    void Start()
    {
        startPosition = transform.position;

    }
    void Update()
    {
        joy();
    }

    public void joy()
    {
        hx = transform.position.x;
        vy = transform.position.y;
        //verify the hx and vy numbers (mine was 228.5 and 227.5)
        Debug.Log("hx = : " + hx + " : vy = : " + vy);

        //Statement 1 - The issue is that both IF() statements can be true at the same time
        //This is way you get diag movement
        if (hx == 60.5)
        {
            player.Translate(Vector3.zero);
        }else
        {
            if (hx > 60.5)
            {
                player.Translate(Vector3.right * velocidade);
            }
            else
            {
                player.Translate(Vector3.left * velocidade);
            }
        }


        //Statement 2 - The issue is that both IF() statements can be true at the same time
        //This is way you get diag movement
        if (vy == 60.5)
        {
            player.Translate(Vector3.zero);
        }else
        {
            if (vy > 60.5)
            {
                player.Translate(Vector3.up * velocidade);
            }
            else
            {
                player.Translate(Vector3.down * velocidade);
            }
        }

    }

    public void OnDrag(PointerEventData eventData)
    {

        transform.position = Input.mousePosition;

    }

    public void clickup(bool up)
    {
        //Debug.Log("clickup run");
        if (up == true)
        {
            transform.position = startPosition;
        }
    }
}

you can try to give yourself some wiggle room

//Statement 1 - The issue is that both IF() statments can be true at the same time
        //This is way you get diag movement
        if (hx == 60.5)
        {
            player.Translate(Vector3.zero);
        }else
        {
            if (hx > (60.5 * 1.1))
            {
                player.Translate(Vector3.right * velocidade);
            }
            else if (hx < (60.5 * 0.9))
            {
                player.Translate(Vector3.left * velocidade);
            }
        }


        //Statement 2 - The issue is that both IF() statments can be true at the same time
        //This is way you get diag movement
        if (vy == 60.5)
        {
            player.Translate(Vector3.zero);
        }else
        {
            if (vy > (60.5 * 1.1))
            {
                player.Translate(Vector3.up * velocidade);
            }
            else if (vy < (60.5 * 0.9))
            {
                player.Translate(Vector3.down * velocidade);
            }
        }
1 Like

While reinventing the wheel can help learn and allows a custom way of handling things, I suggest you use CNControls on the asset store, its free, and overall a pretty good asset to have for mobile. I’ve used several free options and even bought one joystick and mobile input solution, and CNControls is probably the best all around mobile joystick I’ve found so far. One nice thing it does, besides the usual dual joysticks and whatnot, is you can test in the editor with your mouse and it acts just like it would on mobile, which can be a mess to code in your own joystick scripting… so maybe check it out?

I didn’t make it or anything, just my preferred virtual joystick asset.

1 Like

but reinventing the wheel is fun

1 Like

True, I have written a couple joysticks in the past, but always got hung up when it came time to do in editor AND on device testing, and you end up buried in a huge pile of pre-processor directives or whatever they call those platform specific stuffs… and it turns into a big headache for me after that haha.

CNControls has a solid joystick that works fine for me on android, iOS, and tizen… windows phone… atari… :stuck_out_tongue:

1 Like

I understand, I was curious to learn and started from scratch, I wanted to know if it works with IDragHandler, thanks for the link, I’ll take a look.

Hehehe, that’s right I’m trying to learn so I started from scratch, I’m going to test your corrected code, and see the possibilities, I’m going to post here if it works out.

Worked friend thank you! I’m going to continue studying here, thanks!

Explain to me what happens here:
1 - // verify the hx and vy numbers (mine was 228.5 and 227.5)
2 -… if (hx> (60.5 * 1.1)) {
3 -…} else if (hx <(60.5 * 0.9)) {
You have limited the area. To start counting the numbers?

What’s his license, can I use it without paying, or do I have to buy it?

if (hx> (60.5 * 1.1)) {
} else if (hx <(60.5 * 0.9)) {

This creates a 1% Higher and 1% lower So the real number higher number is 66.55 and lower number is 54.45
your 0 line is 60.5. if the object moved above 66.55 then move the object. and same for move below. and move left or right. This allow for a strait up, strait down, strait left or right movement.

Great, thanks friend.

Hi everyone, the code worked, but when adding another touch button, the circle that is my analog, also accompanies the position of the 2nd touch on the screen, how do I differentiate, the area, or the touch so there is no interference?

Here is where things get complicated :smile:

Multi touch input is what you need, where it knows the difference between GetTouch(0) and GetTouch(1) or additional touches… and only lets them interact with things close to the touch, and not after interacting with other stuff… so on and so forth.

Again, you’d save yourself the headache if you just used CNControls joystick :stuck_out_tongue: , but if you are just doing this all to learn, then go ahead and look into enabling multitouch (I think its like Input.MultiTouchEnabled = true; or something) and then sort of “if(Input.TouchCount > 0) { for(int i = 0; i < Input.TouchCount; i++) { if(Input.GetTouch(i).position…” and so on…

Good luck!

1 Like

THX.

1 Like

Oh man, I just made this joy stick asset tester and was like, “It’s relevant, yay!” But it appears that I overlooked CNControls. I’ll have to get them in here ASAP. Thank you for opening my eyes!

1 Like

Haha no problem, I like that asset and use it in my current project, and so far so good, it should probably cost a couple bucks :stuck_out_tongue:

Hi with me brake the hinge joint has some example?

use UGUI ScrollView Create.Share with everyone~

public RectTransform rectT_Viewport;//
    public RectTransform rectT_Joy;//
    public int r_;
    void Start()
    {
        r_ = (int)rectT_Viewport.sizeDelta.x / 2;
    }
    public void On_Move(RectTransform rect_)
    {
        if (rect_.anchoredPosition.magnitude > r_)
        {//r_
            rect_.anchoredPosition = rect_.anchoredPosition.normalized * r_;
        }
    }

3018727--225465--JoyUse1.gif

3018727–225462–UguiJoy_ (1).unitypackage (410 KB)

1 Like