Getting mouse coordinates on a World Space RectTransform?

Hi gang,
First post so let me know if theres any ediquette rules or otherwise I’m breaking :slight_smile:

Details of this are:

  • This is all based on the below tutorial for a non world space UI inventory.
  • I’m working on a 3d game with a first person perspective at the moment.
  • I’m trying to make a grid system that can be accessed anywhere in the world space.
  • There’s multiple grids, they can be detected via onpointerenter

The problem

  • Currently this script only works when inputs are coming from a 0,0 degree angles (so the camera is facing a specific angle). Anything else and the results are inaccurate
  • I think this is due to the script this is based on not being designed for 3d use. The mouseposition coordinates can get very high/low and thats one obvious cause to the inaccurate grid results

The code

public Vector2Int GetTileGridPosition (Vector2 mousePosition)
{
    var pos = mousePosition;
    Vector3 output = Vector2.zero;
    RectTransformUtility.ScreenPointToWorldPointInRectangle(this.rectTransform,pos,cam,out output);
      
    positionOnTheGrid.x = (output.x - ((rectTransform.position.x ) ));
    positionOnTheGrid.y = rectTransform.position.y - output.y;
    tileGridPosition.x = (int)Mathf.Abs((positionOnTheGrid.x/tileSizeWidth));
    tileGridPosition.y = (int)(positionOnTheGrid.y/tileSizeHeight);
    return tileGridPosition;
}

Example of method call
Debug.Log("This tha" + selectedItemGrid.GetTileGridPosition(Input.mousePosition));

Example of the script that detects grid via mouse enter

  private void Awake()
    {
        Cursor.visible = true;
        inventoryController = FindObjectOfType(typeof(InventoryController)) as InventoryController;
        itemGrid = GetComponent<ItemGrid>();
    }
  public void OnPointerEnter(PointerEventData eventData)
    {
        inventoryController.selectedItemGrid = itemGrid;
    }
    public void OnPointerExit(PointerEventData eventData)
    {
        inventoryController.selectedItemGrid = null;
    }

Example of a full script (attached to camera) calling on mouse position in grid

{
        if (selectedItemGrid == null) { return;}
         Debug.Log("Testing position " + selectedItemGrid.GetTileGridPosition(Input.mousePosition));
        if (Input.GetMouseButtonDown(0))
                  {
                  Vector2Int tileGridPosition = selectedItemGrid.GetTileGridPosition(Input.mousePosition);
                
                    if (itemModel == null)
                    {
                      itemModel = selectedItemGrid.PickUpItem( tileGridPosition.x, tileGridPosition.y);
                    }
                    else{
                    
                     bool complete = selectedItemGrid.PlaceItem(itemModel, tileGridPosition.x, tileGridPosition.y);
                     if (complete)
                     {
                       itemModel = null;
                     }
                    }
                  }
 
    }

Gamespace Examples
I also attached two examples of this happening in unity testing.

Attached are two images, rotation on the Y axis is the reference for both.
In the incorrect one the character is facing 90 degrees on the y axis and when the mouse enters square 4,4 it returns 0,3.
In the correct one the character is facing 20 degrees on the Y axis and the mouse when entered on the same 4, 4 square returns 3,3. This is the intended interaction.


To go from world space coordinates you would use the .WorldToScreenPoint() method on whatever Camera is viewing the world.