Hey guys,
I’ve just found significant issue where Input.mousePosition returns wrong value when running in fullscreen with aspect ratios different from native display aspect ratio.
I’ve already filed a bug report (case 715666) and I’m posting this here only to share temporary workaround which partially resolves this issue for me / to find a better solution for this issue together before we will get the proper fix from Unity Technologies.
Remaining issues:
- Fix doesn’t work when display resolution is not set to the native monitor resolution in Windows. (for example, when native display resolution is 1920x1080, windows resolution is set to 1280x800, game is launched with 1280x800)
- Behaviour is unknown on Mac OS X (probably there is no such issue on OS X). Currently I don’t have a Mac handy to check this.
So, add this script to your project and instead of Input.mousePosition - use InputEx.mousePosition:
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
static public class InputEx
{
static private bool initialized = false;
static private int frame = -1;
static private float monitorAspect = 1.77f;
static private Vector3 _mousePosition = new Vector3(0f, 0f, 0f);
static public Vector3 mousePosition
{
get
{
UpdateMousePosition();
return _mousePosition;
}
}
static private void Initialize()
{
if (initialized) { return; }
Resolution resolution = Screen.currentResolution;
Resolution[] resolutions = Screen.resolutions;
int maxWidth = resolution.width;
int maxHeight = resolution.height;
for (int i = 0, imax = resolutions.Length; i < imax; i++)
{
resolution = resolutions[i];
if (maxWidth < resolution.width) { maxWidth = resolution.width; }
if (maxHeight < resolution.height) { maxHeight = resolution.height; }
}
monitorAspect = (float)maxWidth / (float)maxHeight;
Debug.Log(string.Format("InputEx : maxWidth:{0}, maxHeight:{1}, monitorAspect:{2}", maxWidth, maxHeight, monitorAspect));
initialized = true;
}
static private void UpdateMousePosition()
{
if (frame == Time.frameCount) { return; }
frame = Time.frameCount;
Initialize();
_mousePosition = Input.mousePosition;
if (!Screen.fullScreen || monitorAspect == -1f) { return; }
float sw = Screen.width;
float sh = Screen.height;
float currentAspect = sw / sh;
if (currentAspect == -1f) { return; }
// HACK Workaround for Unity bug
if (monitorAspect > currentAspect)
{
float wrongWidth = sh * monitorAspect;
_mousePosition.x = Mathf.Round((_mousePosition.x / wrongWidth) * sw);
}
}
}