Search code examples
c#unity-game-enginesharpdxdirectinput

SharpDx in Unity3D - Buttons does not work anymore when click other window of editor


As you most probably know, Unity3D have terrible buil-in input system what is unable to change configuration runtime so i decised to write own input system based on SharpDX DirectInput. I know well directInput is not officialy recomendet but i like it for its ability to work with device of all kinds (Like Trust dual stick gamepad GTX 28 of mine. Originaly purchased for PSX emulation).

I using class below to representate button object

public class InputButton
{
    public JoystickOffset button;
    public Key key;
    public int pressValue;
    public int relaseValue;
    public bool isJoystick;
    public InputButton(JoystickOffset button, int pressValue, int relaseValue)
    {
        this.button = button;
        this.pressValue = pressValue;
        this.relaseValue = relaseValue;
        isJoystick = true;
    }
    public InputButton(Key key, int pressValue, int relaseValue)
    {
        this.key = key;
        this.pressValue = pressValue;
        this.relaseValue = relaseValue;
        isJoystick = false;
    }
}

Then i replace Unity's (pretty terrible method by the way) Input.GetKeyDown with my own (If you name class same as one of unity's classes you replace it. I know someone must not like use of static here but i see it very benefical)

public static bool GetKeyDown(InputButton button)
{
    bool pressed = false;
    keyboard.Poll();
    keyboardData = keyboard.GetBufferedData();
    if (button.isJoystick == false)
    {
        foreach (var state in keyboardData)
        {
            if (state.Key == button.key && state.Value == button.pressValue)
            {
                pressed = true;
            }
        }
    }
    return pressed;
}

But before everything i call Input.Initialize() from another class (during Awake()). it looks like this :

  public static void Initialize()
    {
        directInput = new DirectInput();
        var joystickGuid = Guid.Empty;
        foreach (var deviceInstance in directInput.GetDevices(SharpDX.DirectInput.DeviceType.Joystick, DeviceEnumerationFlags.AttachedOnly))
        {
            joystickGuid = deviceInstance.InstanceGuid;
        }
        if (joystickGuid == Guid.Empty)
        {
            foreach (var deviceInstance in directInput.GetDevices(SharpDX.DirectInput.DeviceType.Gamepad, DeviceEnumerationFlags.AttachedOnly))
            {
                joystickGuid = deviceInstance.InstanceGuid;
            }
        }
        if (joystickGuid != Guid.Empty)
        {
            joystick = new Joystick(directInput, joystickGuid);
            joystick.Properties.BufferSize = 128;
            joystick.Acquire();
        }
        keyboard = new Keyboard(directInput);
        keyboard.Properties.BufferSize = 128;
        keyboard.Acquire();
    }

Now to the problem. When i click to anything outside game window in the editor, keys does not respond anymore. I checked everything and both directInput and keyboard are still in variables. Most likely some problem with "Focus" of window because this problem looks like directInput instance or keyboard gets disconnected as soon as game window lost focus (focus is lost when window is not active window, active window is not "active" but so called "focused").

Do someone know why this happenig and how to repair it ?

EDIT : Looks like this problem is somehow connected to window(s). I have settings and i'm able to switch fullscreen runtime. As long as i'm in fullscreen it works fine but when i switch to window it stop working.

Thanks.

-Garrom


Solution

  • Now i see myself as very stupid person... Anyway i was right abou window focus. When game window lost focus it (somehow) break directInput. I solved this useing unity's callback OnApplicationFocus and re-Initialize (call Initialize(). See original question) every time game window gets focused.