Search Unity

Bug Setting position of UI with screen space camera canvas issues

Discussion in 'Scripting' started by Feral_Pug, Jul 18, 2021.

  1. Feral_Pug

    Feral_Pug

    Joined:
    Sep 29, 2019
    Posts:
    49
    I am making a drag and drop system and my ui is setup with a screen space camera canvas so that I can have all of the UI stuff far away from where the game is taking place. When setting an ui object's position to the mouse position I have to transform the screen point to a world point through the UI camera to get the right position. However the z component of the position always gets set to some crazy number like 97000. Even if I set its z to a value like 0 or 100 it still gets set to this crazy number of about 97000. The only way to fix this was to set the position to the transformed screenToWorldPoint and then set the LOCAL position of the UI element to be the localPosition and setting the local position z to 0.

    So I asking if this is a bug or is something going on that I am not realizing (probably the latter)?
     
  2. Kurt-Dekker

    Kurt-Dekker

    Joined:
    Mar 16, 2013
    Posts:
    38,674
    This doesn't sound quite right. Aren't you able to just do it with RectTransformUtility? The camera should not matter when going from mouse position to canvas position (unless obviously it is a world space canvas!)... but perhaps I'm not understanding your setup exactly.
     
  3. Feral_Pug

    Feral_Pug

    Joined:
    Sep 29, 2019
    Posts:
    49
    Hmm, I have never used the RectTransformUtility, that could maybe be a more straight forward of an approach. Yes, my canvas isn't in screen overlay mode, but in screen space camera. This way I can put all of my UI (including my canvas, eventsystem, and UICamera) objects as children of a single empty that is positioned for away from the scene origin e.g. -1000, 0, -1000. This way all of the UI stuff is out of the way from the rest of the objects, it just feels cleaner to me this way.

    When I tried to just use the raw input.MousePos for the position of the UI element, the position was super wrong, which lead me to transforming it with the camera being used for the screenspace camera on the canvas component. And after transforming, it works perfect except for the Z component, which lead me to my solution above of setting the local position. But I have no idea why and it just seems extra convoluted.
     
  4. Kurt-Dekker

    Kurt-Dekker

    Joined:
    Mar 16, 2013
    Posts:
    38,674
    Why not put the UI in another scene, additively loaded? I never want to look at UI when I'm working on my game. (Well, technically I never even want to look at UI period, but we'll leave that for now.) You can use singletons or ScriptableObjects to connect it all together.

    ALSO, speaking to your original question, I just verified that what I said was true by plucking a piece of stuff out of one of my games. See enclosed package. This is the codelet you want, which worked for me with a second "UI Camera" placed far away from the 3D action.

    Code (csharp):
    1. using System.Collections;
    2. using System.Collections.Generic;
    3. using UnityEngine;
    4. using UnityEngine.UI;
    5.  
    6. public class ScreenSpaceCameraMousePositioning : MonoBehaviour
    7. {
    8.     [Header( "WARNING: presumes Screen Space Canvas!")]
    9.     public Canvas MyCanvas;
    10.     public RectTransform Thingy;
    11.  
    12.     // since we assume it, just get it from the canvas;
    13.     // if this property comes back null, you failed to set a Canvas above.
    14.     Camera cam { get { return MyCanvas.worldCamera; } }
    15.  
    16.     void Update ()
    17.     {
    18.         if (Input.GetMouseButton(0))
    19.         {
    20.             var pos = Input.mousePosition;
    21.  
    22.             Vector3 output = Vector2.zero;
    23.  
    24.             RectTransformUtility.ScreenPointToWorldPointInRectangle(
    25.                 MyCanvas.GetComponent<RectTransform>(),
    26.                 pos,
    27.                 cam,
    28.                 out output);
    29.  
    30.             Thingy.position = output;
    31.         }  
    32.     }
    33. }
     

    Attached Files:

    Last edited: Nov 24, 2022
    kreso, sinakarimi0938 and Bauschen like this.
  5. Feral_Pug

    Feral_Pug

    Joined:
    Sep 29, 2019
    Posts:
    49
    Yeah, thanks for the script. That certainly is a lot cleaner. I'll definitely update my code to use the Utility class instead of my own implementation. I still don't totally understand why unity was just setting the z value of my rectTransform to a huge number though.
     
  6. Kurt-Dekker

    Kurt-Dekker

    Joined:
    Mar 16, 2013
    Posts:
    38,674
    If I had to guess it's because of the whacky scaling that happens to the canvas when in Screen Space Camera mode. Something is probably dividing by a weird tiny number... See the bottom here:

    Screen Shot 2021-07-18 at 2.21.51 PM.png
     
  7. Feral_Pug

    Feral_Pug

    Joined:
    Sep 29, 2019
    Posts:
    49
    Hmm, yeah the scale on the object does get all weird. That must be it then. Thanks for your help, it is appreciated.
     
    Kurt-Dekker likes this.
  8. Bauschen

    Bauschen

    Joined:
    Aug 27, 2015
    Posts:
    5
    Thank you lots for saving my sanity
     
    Kurt-Dekker likes this.