When using UserInputService to detect mouse movement (see repro file), it will show the Y position of the mouse as much as 58 pixels less than it actually is (from my testing). Consequentially, when moving your mouse to the top of the screen, it will begin to show negative values.
I believe this is due to UserInputService not taking Core UI insets into account.
This happens in both Studio and live servers, although from my testing the effect is lessened in live servers (Up to 58 pixels off in studio and 36 in a live server)
Expected behavior:
I expect UserInputService to show the correct Y position of the mouse.
Actual behavior:
UserInputService shows an incorrect value by as much as 58 pixels less than the correct position
Workaround:
Manually add 58 to the Y position whenever using this method, but this is not idea.
Consistency:
100%
Repro:
The example in the file compares UserInputService to detecting a click with a TextButton. The TextButton shows the correct Y position, while UserInputService shows an incorrect Y position.
Instructions
Step 1. Download below file and play the game.
Step 2. Move your mouse around and click the left mouse button while looking at console output
UserInputService MouseMovement will say that the Y position of the mouse is 58 studs less than TextButton.MouseButton1Down says it is.
Step 3. Move mouse to top of screen; UserInputService will begin to show negative values as it does not take Core UI insets into account.
(In case anybody wanted to know where the numbers come from.)
I’m curious as to why this is, because it seems quite intentional from what I can tell. Maybe it’s some backwards-compatibility thing?
It definitely looks like it accounts for the Core UI insets, it just seems kind of weird what it’s actually doing with them, since I don’t know what world would want the top of the screen to be Y=-58 and not Y=0.
Roblox should honestly make an opt-in property in the workspace which disables all this inset mess. That means, no more inset with the mouse, AbsolutePosition, ScreenGuis, etc. Would help to make some of my math a bit simplier.
But yeah, this isnt a bug. It is intentional to be compatible with old systems.
We currently use 2 different coordinate systems (with different origins) for screen position APIs. Here’s a list of which coordinate system each of these APIs use:
The coordinate system for each viewport has its origin at the top left of the viewport, so you can see that the device safe viewport has a different origin than the Core UI safe viewport.
GuiButton.MouseButton1Down isn’t actually on the list, but it should be under “device safe viewport”. On the other hand, InputObject.Position uses the Core UI viewport. So this explains the discrepancy you noticed between the local positions in each coordinate system.
We unfortunately can’t change the coordinate systems each of these APIs use because we want to preserve backwards-compatibility with existing games.