Mouse position on Gride view

Is there any way to get the mouse position on the Grid view?
The “region_2d_to_location_3d” return a position that is parallel with view.
but i need a position like [x, y, 0]
Im working on an add-on for simulate 3Ds Max interface in Blender. in 3Ds Max every thing create on floor(grid) but for now Im not able to make the object on exact clicked point.

2 Likes

I wrote this script and I added comments to most of the lines to be easier to understand.
You can just place it in the script editor and start it. Then press F3 and search for “Get position on the grid”.
Run it and it should place an empty on the grid under the mouse cursor.

from bpy.types import Operator

import mathutils
from mathutils import Vector
from bpy_extras import view3d_utils


class GetPositionOnGrid(Operator):
    """Get a 3D position on the grid based on mouse cursor position"""
    
    bl_idname = "nevil.get_position_on_grid"
    bl_label = "Get position on the grid"
    
    # This function is just for testing
    def create_test_empty(self, context):
        '''Create an empty, link it to the scene and show the axis'''
        
        if bpy.data.objects.get("TestEmpty"):
            bpy.data.objects.remove(bpy.data.objects["TestEmpty"], do_unlink = True)
            
        manipulator_empty = bpy.data.objects.new("TestEmpty", None)
        scene_collection = context.layer_collection.collection
        scene_collection.objects.link(manipulator_empty)
        manipulator_empty.show_axis = True
        
        return manipulator_empty  
    
    def invoke (self, context, event):
        
        viewport_region = context.region
        viewport_region_data = context.space_data.region_3d
        viewport_matrix = viewport_region_data.view_matrix.inverted()
        
        # Shooting a ray from the camera, through the mouse cursor towards the grid with a length of 100000
        # If the camera is more than 100000 units away from the grid it won't detect a point
        ray_start = viewport_matrix.to_translation()
        ray_depth = viewport_matrix @ Vector((0,0,-100000))
        
        # Get the 3D vector position of the mouse
        ray_end = view3d_utils.region_2d_to_location_3d(viewport_region,viewport_region_data, (event.mouse_region_x, event.mouse_region_y), ray_depth )
        
        # A triangle on the grid plane. We use these 3 points to define a plane on the grid
        point_1 = Vector((0,0,0))
        point_2 = Vector((0,1,0))
        point_3 = Vector((1,0,0))
        
        # Create a 3D position on the grid under the mouse cursor using the triangle as a grid plane
        # and the ray cast from the camera
        position_on_grid = mathutils.geometry.intersect_ray_tri(point_1,point_2,point_3,ray_end,ray_start,False )
        
        # Create an empty for testing
        empty = self.create_test_empty(context)
        # Place the empty on the grid under the mouse cursor
        empty.location = position_on_grid
        
        return {'FINISHED'}

classes = (
    GetPositionOnGrid,
    )

register, unregister = bpy.utils.register_classes_factory(classes)

if __name__ == "__main__":
    register()
    

Your add-on looks very nice btw!

5 Likes

Thank you Oskar, this is clear and understandable and working perfectly. I update the function and result is perfect now.

1 Like

You’re welcome! I’m glad it worked! :slightly_smiling_face:
I was trying to do something similar last week and I had part of it done.

1 Like

Thanks a lot for this very useful function! I was wondering if this solution can be made to work in orthographic view as well. Looks like, in its current implementation, it works only for perspective view.

1 Like

An interesting idea. I will follow the addon. It will be great if all the functions work like in max.

1 Like

Hi Khemadeva

I have update this code to work on other views too. you can download BsMax and get the function from

“BsMax_2_80/Primitive/Primitive.py” search for “get_click_point_info(x, y, ctx)”

Codes are a little ugly :crazy_face: but works for now. I`ll clean them up soon as possible :wink:

2 Likes

Thank you Ghostil

I try to do my best, but I need support for report bugs and give me ideas to improve better. and share it, to other people interested and need it be able to find it easy.