Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. Dismiss Notice

World mouse position in EditorWindow

Discussion in 'Editor & General Support' started by Fauvent, Mar 14, 2017.

  1. Fauvent

    Fauvent

    Joined:
    Sep 30, 2016
    Posts:
    5
    Hello,

    I don't seem to be able to find the world mouse position in an EditorWindow.
    Right now I feel like it is not possible at all... Here some things I tried but it always return the position at the center of the window.

    void OnSceneGUI(SceneView sceneView)
    {
    // Camera.
    Camera cam = sceneView.camera;
    if (cam == null)
    return;

    // Update mouse grid position.
    Event e = Event.current;
    Vector2 mousePosition = e.mousePosition;
    Vector3 mouseWorldPos = HandleUtility.GUIPointToWorldRay(mousePosition).origin;
    }

    OnSceneGUI and HandleUtility were not supported by EditorWindow so I had to add :

    SceneView.onSceneGUIDelegate += OnSceneGUI;

    To the enable call. and :

    SceneView.onSceneGUIDelegate -= OnSceneGUI;

    To the disable call. but still not success, it returns the center of the screen in world pos.

    Also tried to to use cam.ScreenToWorldPoint but no success... The Z was set to camera near clip plane in case someone ask.

    I also tried to make my own function to find the world position from the the screen space pos (between -1 and 1) but it does not work neither. It seems like the camera informations for the scene view (fov, near clip plane, matrix...) are wrong.

    private Vector3 CameraSpaceToWorldPosition(Vector2 cameraSpacePos, Camera camera)
    {
    float halfFov = camera.fieldOfView * .5f;

    float halfHeight = Mathf.Abs(Mathf.Tan(halfFov)) * camera.nearClipPlane;
    float halfWidth = halfHeight * camera.aspect;

    Vector3 localPos = new Vector3(halfWidth * cameraSpacePos.x, halfHeight * cameraSpacePos.y, camera.nearClipPlane);
    return camera.cameraToWorldMatrix * localPos;
    }

    By the way I am using unity 5.5.0f3, at the point I am thinking about using something else than EditorWindow since it seems the problem is coming from there. I have been able to get the mouse position from custom editors in the past.

    Thanks in advance.
     
    Lyrcaxis likes this.
  2. Fauvent

    Fauvent

    Joined:
    Sep 30, 2016
    Posts:
    5
    Tried to use :

    Vector3 mousePosition = Event.current.mousePosition;

    float mult = EditorGUIUtility.pixelsPerPoint;
    mousePosition.y = sceneView.camera.pixelHeight - mousePosition.y * mult;
    mousePosition.x *= mult;

    Ray ray = sceneView.camera.ScreenPointToRay(mousePosition);

    from https://github.com/slipster216/VertexPaint/blob/master/Editor/VertexPainterWindow_Painting.cs

    But still no success... I am starting to thing it mays be a bug of the 5.5.0f3 or because I am using two monitors...
     
    FlightOfOne and Lyrcaxis like this.
  3. Fauvent

    Fauvent

    Joined:
    Sep 30, 2016
    Posts:
    5
    Nevermind I am (of course) just an idiot.

    The world position was right but when I projected it on the plane of my grid I used the vector forward of the camera instead of the Mouse world pos - camera position.
     
    Lyrcaxis likes this.
  4. FlightOfOne

    FlightOfOne

    Joined:
    Aug 1, 2014
    Posts:
    659
    I used @Fauvent's and this is what I ended up with. Hope this helps the next person to find this thread!

    Code (CSharp):
    1. using UnityEngine;
    2.  
    3. #if UNITY_EDITOR
    4. using UnityEditor;
    5. /// <summary>
    6. ///
    7. /// </summary>
    8. [ExecuteInEditMode]
    9. public class ClickSpawn : MonoBehaviour
    10. {
    11.     private void OnEnable()
    12.     {
    13.         if (!Application.isEditor)
    14.         {
    15.             Destroy(this);
    16.         }
    17.         SceneView.onSceneGUIDelegate += OnScene;
    18.     }
    19.  
    20.     void OnScene(SceneView scene)
    21.     {
    22.         Event e = Event.current;
    23.  
    24.         if (e.type == EventType.MouseDown && e.button == 2)
    25.         {
    26.             Debug.Log("Middle Mouse was pressed");
    27.  
    28.             Vector3 mousePos = e.mousePosition;
    29.             float ppp = EditorGUIUtility.pixelsPerPoint;
    30.             mousePos.y = scene.camera.pixelHeight - mousePos.y * ppp;
    31.             mousePos.x *= ppp;
    32.  
    33.             Ray ray = scene.camera.ScreenPointToRay(mousePos);
    34.             RaycastHit hit;
    35.  
    36.             if (Physics.Raycast(ray, out hit))
    37.             {
    38.                 //Do something, ---Example---
    39.                 GameObject go = GameObject.CreatePrimitive(PrimitiveType.Cube);
    40.                 go.transform.position = hit.point;
    41.                 Debug.Log("Instantiated at " + hit.point);
    42.             }
    43.             e.Use();
    44.         }
    45.     }
    46. }
    47. #endif
     
    pyrypoikolainen likes this.
  5. ununion

    ununion

    Joined:
    Dec 2, 2018
    Posts:
    268
    i have to say thank you very much
     
  6. ycanatilgan

    ycanatilgan

    Joined:
    Aug 23, 2017
    Posts:
    30
    Very helpful!
     
    FlightOfOne likes this.
  7. KevinCastejon

    KevinCastejon

    Joined:
    Aug 10, 2021
    Posts:
    56
    I don't understand the answers, how it is done from an EditorWindow ? The OnScene message method is not available there.