Search Unity

New Input System conversion from Old Input System. I need help.

Discussion in 'Input System' started by LiefLayer, Apr 10, 2021.

  1. LiefLayer

    LiefLayer

    Joined:
    Jan 6, 2013
    Posts:
    65
    Ok I really tried to understand the new Input system but I really find it difficult to migrate my code to this new system.
    I don't want to change everything in my code. Since I made a rebind custom system I should only need to change one class and nothing else. But I think the new Input system works in a really different (and confusing way) because I cannot adapt anything.

    My main problems:
    1. I have two json where I save my current bindings the first is
    Code (CSharp):
    1. {"axis":["VerticalJoy","HorizontalJoy","VerticalJoy2","HorizontalJoy2","Mouse X","Mouse Y","Mouse ScrollWheel"]}
    the second one is:
    Code (CSharp):
    1. {"buttons":["W","S","A","D","Space","Escape","LeftShift","Mouse0","Mouse1","JoystickButton0","JoystickButton7","I","JoystickButton6"]}
    In my code I convert my second one to a Dictionary
    Code (CSharp):
    1. private static Dictionary<string, KeyCode> inputs = new Dictionary<string, KeyCode>();
    2. private string[] inputList = { "VerticalUp", "VerticalDown", "HorizontalLeft", "HorizontalRight",
    3.                                     "Jump", "Cancel", "Walk", "MouseClick", "MouseRightClick", "JumpJoy",
    4.                                     "CancelJoy", "Inventary", "InventaryJoy" };
    5.  
    6. SetInput(inputList[j], (KeyCode) System.Enum.Parse(typeof(KeyCode), loadConfirmA[j]));
    7.  
    8. SetInput
    9. inputs[keyName] = input;
    10.  
    with this kind of code I associate string to a KeyCode... After that I just call MyClass.GetKey(KeyCode) and I return if that KeyCode was pressed
    Code (CSharp):
    1.  
    2. public static bool GetKey(KeyCode code) {
    3.         return Input.GetKey(code);
    4.     }
    5.  
    6.     public static bool GetKeyDown(KeyCode code) {
    7.         return Input.GetKeyDown(code);
    8.     }
    9.     public static bool GetKeyDown(String code) {
    10.         return Input.GetKeyDown(code);
    11.     }
    12.  
    13.     public static bool GetKeyUp(KeyCode code) {
    14.         return Input.GetKeyUp(code);
    15.     }
    16.  
    How can I convert Input.GetKey(KeyCode) in the new Input System?
    the only example in the migration guide use spacekey as an example... Is there any KeyCode type (like an Enum) that I can use?
    How can I pass "Space" and "JoystickButton0" and get true if they are pressed?
    Should I make a custom Enum? Is there a way to do it fast?
    And how can I bind that to something like
    ((KeyControl)Keyboard.current["space"]).isPressed
    ?
    I have an idea... but I need to convert "Space" to "space" (and know how everything should be converted) and also I need to know how to do a Keyboard.current["JoystickButton0"] without using Joystick.current (why there is no generic current input to get every input?).

    2. A lot more problems for the axis, right now I mapped multiple joystick for standard joystick
    Code (CSharp):
    1.  
    2. private static Dictionary<string, string> joypad = new Dictionary<string, string>();
    3. private string[] inputAxisList = { "JoyVertical", "JoyHorizontal", "JoyVertical2", "JoyHorizontal2",
    4.                                     "XMouse", "YMouse", "ScrollWheel" };
    5. SetJoypad(inputAxisList[j], loadConfirmA[j]);
    6. //on android I do:
    7. SetJoypad("JoyVertical", "VerticalJoy3Android");
    8. SetJoypad("JoyHorizontal", "HorizontalJoy3Android");
    9. //on pc I do:
    10. SetJoypad("JoyVertical", "VerticalJoy");
    11. SetJoypad("JoyHorizontal", "HorizontalJoy");
    12.  
    13. //VerticalJoy, HorizontalJoy, VerticalJoy3Android, HorizontalJoy3Android are mapped on the old Input Mapper
    14.  
    with
    GetJoypad("JoyVertical") I get the current vertical joypad mapped.
    after that I just pass it to
    Code (CSharp):
    1.  
    2. public static float GetAxis(string axis) {
    3.         return Input.GetAxis(axis);
    4.     }
    5.  
    to get x and y value of that axis

    again the migration manual does not help at all
    I'm ok with making a new mapping Unity side but why
    public InputAction fireAction;
    void Awake()
    {
    fireAction.performed += ctx => Fire();
    }

    void Fire()
    {
    //...
    }

    I don't really understand how to translate that in my own code. Should I make a List of InputAction? And also a list of action performed... and how can I know if axis x or y return a value?

    3.
    UnityEngine.Input.mousePosition
    Use Mouse.current.position.ReadValue().

    NOTE: Mouse simulation from touch is not implemented yet.

    so... how can I get the touch position too? I need both since my game is both desktop and mobile.

    4. Finally my code to rebind
    Code (CSharp):
    1.  
    2. foreach (KeyCode kcode in Enum.GetValues(typeof(KeyCode))) {
    3.                     if (InputMapperSystem.GetKey(kcode)) {
    4.                         if (!inputs.ContainsValue(kcode)) {
    5.                             SetInput(singleInput, kcode);
    6.                             List<string> temp = new List<string>();
    7.                             foreach (KeyCode key in inputs.Values) {
    8.                                 temp.Add(key.ToString());
    9.                             }
    10.                             //save to json
    11.                         }
    12.                         singleInput = "";
    13.                         takeInput = false;
    14.                         break;
    15.                     }
    16.                 }
    17.  
    I undestand that the new Input system is just different, but I don't really want to change my code too much.
    Is there any way around this kind of things?
    I don't really want my code to became obsolete and I know they will remove the old input system sooner or later... But how can I fix my code without make the input system from zero?
     
  2. LiefLayer

    LiefLayer

    Joined:
    Jan 6, 2013
    Posts:
    65
    PS. I tried to use both system (thank god you can).
    I tried by using Key instead of KeyCode.
    It's not working for
    "Mouse0","Mouse1","JoystickButton0","JoystickButton7","I","JoystickButton6"
    it only works for keyboard key (and that already suck... so if I want to use that I need to create a new Enum with the missing keys and switch case on them and I don't really want to do that since I want my user to be able to rebind Mouse0 to anything not just MouseClick).
    Not only that... I can say something like this
    if (Keyboard.current.anyKey.isPressed) {
    }
    but there is no way to print what Key was pressed so no way to implement rebind just in the code.

    Mouse.current.position.ReadValue() works as expected but it still get value even on touchscreen (wrong values) and Touchscreen.current.primaryTouch.position.ReadValue() does not work at all.

    I still need to try the axis part... but for what I can see here if unity deprecate the old input system I can only trash my old system and avoid rebinding... the InputSystemUIInputModule (that I use for the menu) works like a charm (that's the only good part... and the default input is already good)... I can still make a rebind system based on that component (much smaller with just keyboard buttons rebindings).
    I just wish they keep the old input system until they implement everything I need to upgrade without problems.

    Right now I think the new input system is not easy to use like the old one and not easy to upgrade at all.

    PS. The doc say they will try to mantain both system (the old one will maybe translate to the new engine but it should be invisible to me)... If that is the case I don't really know if I will use the new input system again. At least not in this game (my implementation is already completed). Both I'll keep that in mind for the future.
     
    Last edited: Apr 10, 2021
  3. AcidArrow

    AcidArrow

    Joined:
    May 20, 2010
    Posts:
    11,755
    Maintain? The only thing they do for the input manager is occasionally break stuff (in LTS even), and the new input system already seems abandoned (last actual release was a year ago?), presumably in favor of some DOTS version of the same package, which will hopefully be ready in time for my grandchildren to be able to use in their games.

    In any case, if you have set up your game to work properly with the old Input Manager, why are you looking to migrate to the new Input System?
     
  4. LiefLayer

    LiefLayer

    Joined:
    Jan 6, 2013
    Posts:
    65
    Well. That actually sad. Make a new Input system is actually a good idea (to make the old one any good I had to rewrite a lot of stuff... it was not easy to make a rebind system and it cannot know what device input you use without an input from that device). But I actually wish they would update the old input system with a new backend instead of making something incompatible that they abandoned.

    I usually try to update my code with every realease of Unity because:
    - I don't want my code to became obsolete and not be able to keep unity updated with new stuff.
    - I usually like the new stuff and I want to try them. For example I used the NavMeshComponents and it was a good thing I was able to do that because it was great for a thing I wanted to do in my game.

    And the input system is a big thing in any game so keep it updated is important to be able to maintain the code.
    But now I understand that the new Input system just is not ready... and if it is not ready and they will not deprecate the old input system I will not need to use it.

    It will still be interesting to know if there is any workaround the stuff I said in my first post. I will try everything again in the future just to understand if it can be done.