How can I convert mouse coordinates betwen different viewports size? (SOLVED)

This has been giving me trouble for a long time, but I cracked it recently:

Put this in your init(self) function:

window.set_listener(window_callback)

and then use this function to get new screen size when the window is resized:

local function window_callback(self, event, data)
    if event == window.WINDOW_EVENT_RESIZED then
     	screen_size.x, screen_size.y = data.width, data.height
 	end
end

This is what I have in the on_input() function which tracks the cursor:

local zoom = math.min(screen_size.x / 1280, screen_size.y / 1024)
local projected_width = screen_size.x / zoom
local projected_height = screen_size.y / zoom
local xoffset = -(projected_width - 1280) / 2
local yoffset = -(projected_height - 1024) / 2
local x = (action.x / 1280) * projected_width + xoffset
local y = (action.y / 1024) * projected_height + yoffset

Note that I have the default screen sizes hardcoded here (1280x1024), so you’ll probably want to change that.

x and y are the coordinates corresponding to the cursor position you see.

Note that:

  1. if the window gets resized on startup (say, the default resolution is bigger than what you’re using at that moment), the values are not going to be right until you resize the window manually. To solve that you need to send a message with the correct sizes from the render script at startup.
  2. I’m far from an expert. There might be a simpler solution. Or maybe there are some edge cases I’m not aware of, but this worked for me.

Cheers!

2 Likes