Detemining if the user is using the keyboard or pointer input

I’m struggling to get current button focus and highlight to stay in-sync.

I have a couple of layouts, one is deactivated. I use a button to activate it and deactivate the current one.
The problem is when I go back and re-activate the original layout the button I clicked on is in a highlighted state except it is not actually the selected item, according to the EventSystem.

I’ve track this down to a problem when switching between mouse and keyboard. It seems that a button remembers it’s selected state even though the EventSystem has a different selected object.

This seems to be a combination of problems with the StandaloneInputModule and Selectable classes. I’ve run a script attached to my UI button and inspected some of the hidden parameters. There is a property called m_CurrentInputMode. This is either set to ‘Buttons’ or ‘Mouse’ depending on if I’m using the keyboard or mouse. However it’s private and there doesn’t seem to be anyway for me to find out what sort of input is being used. A ‘Selectable’ object has a private property called ‘hasSelection’. If this is true and I activate the layer it will always cause the object to go into a highlighted state.

I sort of have a work around for this situation by looping through all the Selectable objects on a layer and call OnDeselect() when I enable the layer. This seems to set the ‘hasSelection’ bool to false. I can select the correct button using the EventSystem. However I can only do this part if the user is using a keyboard, which I can’t find out as the m_CurrentInputMode is private.

The best idea I have so far is to implement by own version of StandaloneInputModule but that seems a bit excessive.

Has the C# source code for the new UI system been released yet? I can always get this and try and track down what the problem may be.

There is some code here that describes the input modules:
https://gist.github.com/stramit

As to your problem I would need to have a closer look at what you are doing (code side) but it might be a corner case we didn’t anticipate.

I’ve attached a example project that demos the issues.

There is a signal script, called ActiveScreen.cs, attached to each GameObject that acts as a screen.

In the OnEnable() method I’ve put in 3 separate #defines to enable default behaviour and a few workarounds I’ve tried.

At the top of the script there are some repro steps so you can see the various issues and you can turn on one #define at a time to see the different issues.

I can well understand why there maybe some edge cases in the UI system. I’ve built UI solutions myself over the last 15 years in this industry and there are always issues especially with input, focus and selection management.

I suppose this is a bit unfair of me to stress test the UI as it’s still only beta but from bitter experience I know where most of the pitfalls will be. I’ve had many games rejected for some TCR violation due to input issues. However any help is much appreciated. I constantly hear from fellow programmers that ‘UI is easy’. :frowning: Oh no it’s not.

The workaround test still won’t actually be acceptable for a final project. It does make it possible to control a UI via either mouse or keyboard, but you can switch between the two. Switching input method or having simultaneous controller and pointer input should be possible. Many PC games will allow a user to plug in a 360 controller and if you start pressing controller buttons the input device will swap without problems.

Also on consoles it is possible to use both a controller and pointer input (e.g. Kinect). What is even more complex is allowing multiple players to control the UI. This doesn’t happen very often but I have known it to occur in games where the players can simultaneously select from a grid of possible avatars. However that usually requires some custom coding. There does need we may need a way to trigger a highlight from code, or maybe we just trigger an animator from code.

I do have to add that the UI system so far is very good. It’s nice to see a distinction between a visual state like highlighted and which item is focused for input. So many UI systems I’ve worked on didn’t do this and that caused its own issues. Its good to see some thought has been put into the design.

Thanks for the help.

1746074–110308–UITest.zip (126 KB)

Hi,

Thanks for the nice example project. I can really see what you want to do now. I have made some changes to what we expose on the Event system to make this possible, but basically the idea is that just by activating a game object does not select the element, you need to mark it selected in the Event system. In your case you want to only do this if you are using Keyboard input.

So when the next version is available, something like this is what you want:

    public void SetSelectedIfUsingKeyboard (GameObject go)
    {
        if (EventSystemManager.currentSystem == null)        
            return;

        var standAlone = EventSystemManager.currentSystem.currentInputModule as StandaloneInputModule;
        if (standAlone == null)
            return;

        if (standAlone.inputMode != StandaloneInputModule.InputMode.Mouse)
            EventSystemManager.currentSystem.SetSelectedGameObject(go); 
    }

So disable one menu, enable second menu, then call the SetSelectedIfUsingKeyboard function.

1746925--110365--Screen Shot 2014-08-23 at 11.05.09 pm.png

Thanks for the great support. Looking forward to trying this out the next version.

I know this is a terrible necro, but is it possible, that this was deprecated? inputMode seems to no longer work.

in 5.3 (maybe before that) yes the obsolete message should have told you that :slight_smile: ““Mode is no longer needed on input module as it handles both mouse and keyboard simultaneously.””

Yeah, but how are we supposed to figure out which mode the user is using now? We don’t want to visually highlight a Selectable when we show a new screen. The screen transition example on the unity manual is actually using that method to determine this, which is now no longer possible.

I am wondering the same @phil-Unity

Also this official HOW-TO still uses the deprecated code: Redirecting to latest version of com.unity.ugui

Yeah. Same way I stumbled on it.

We should update that how to then. As for the proper new solution i dont really have one. The deprecation happened at different times and this case was missed. Could someone file a bug just describing the issue

I’ll set up a bug later today and post the number here. Question though: Are you considering a way to enable that functionality? A lot of flexible UIs would need to change their behavior based on the input method…

yea thinking of a way to enable it not 100% sure the best way atm though.

Any new thoughts on this?