Search Unity

  1. Megacity Metro Demo now available. Download now.
    Dismiss Notice
  2. Unity support for visionOS is now available. Learn more in our blog post.
    Dismiss Notice

InControl - input and cross platform controller support for Unity, made easy!

Discussion in 'Assets and Asset Store' started by pbhogan, Jul 18, 2014.

  1. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    Unfortunately, this isn't a built-in feature. However, it would not be hard to implement a custom binding source yourself.

    Honestly, if you copied DeviceBindingSource and called it something else it would take only very minor modifications to add a second InputControlType parameter. I wouldn't modify the original, just for the sake of maintenance for yourself going forward and it has other ties in the code for listening for user bindings, but since it's a toggle in your settings and you're presumably manually adding the binding it should be simple and you can also strip out anything to do with saving or loading the binding, unless you really want to add that.

    AddBinding can take any BindingSource as a parameter, so once you have your custom one just call Fire.AddBinding( new MyCustomDeviceBindingSource( InputControlType.Action1, InputControlType.Action2 ) );

    For a more convoluted example, I've got an experimental ComboBindingSource (download here: https://www.dropbox.com/s/grz0ntddqu9vojt/ComboBindingSource.cs?dl=0) which does a whole lot more than you need, but allows combining keyboard, mouse and device controls into a single binding.
     
    hododoho likes this.
  2. Zebbi

    Zebbi

    Joined:
    Jan 17, 2017
    Posts:
    521
    Is it possible to use InControl to override the eventsystem raycast coordinates and change them before the mouse clicks are interpreted? I'm having an issue with a custom viewport scaler that needs all mouse-clicks to be *1.2, at present the raycast positions are incorrect and need adjusting before the click and button hover takes place:
    Raycast positions:

    UI hovers:


    Is it possible with this asset to manipulate the eventsystem coordinates before the clicks or hover highlights take place?
     
  3. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    Nope, InControl definitely won't help you with this. It's interaction with the UI event system is pretty basic, just to feed in directional navigation, as well as submit and cancel events.

    Depending on what version of Unity you're using, you may be able to use BaseInputModule.inputOverride (https://docs.unity3d.com/ScriptReference/EventSystems.BaseInputModule-inputOverride.html) to insert an override that reports a scaled mouse position to the event system (probably via overriding GetAxisRaw on BaseInput https://docs.unity3d.com/ScriptReference/EventSystems.BaseInput.html). I've never tried this (I think this override feature is new) but it might do the trick. I'm not sure which version of Unity they added this on... might be 2018.3

    If you're using an older version, you'll probably have to subclass StandaloneInputModule and do some hack to modify the mouse event data before it's processed.
     
    Zebbi likes this.
  4. Zebbi

    Zebbi

    Joined:
    Jan 17, 2017
    Posts:
    521
    Thanks for the suggestions, I'll look into them! Merry Christmas to you!
     
  5. NeatWolf

    NeatWolf

    Joined:
    Sep 27, 2013
    Posts:
    924
    Hi there!
    (Patrick, I sent a second email but probably got lost in the process, so I'm also asking publicly since I believe it's trivial :) )

    Question: What's the most direct way to get the absolute current position of the touch inside the window/rect specified by the TouchTrackControl? (which, of course may or may not be full screen, or just a scaled part of it?)

    Details:
    I believe I'm struggling for something which probably is so obvious that I can't see it.

    I mapped a TouchTrackControl to the LeftStick. Everything works fine with a workaround, but it's definitely ugly.

    I'd love to get, in -1 to 1 range, raw or not, the exact current position of the LeftStick (a Vector2 possibly).

    Doesn't matter how I fiddled, but Value, X, Y, almost everything seems to return the current delta. Or a percentage, in a very indirect way, getting back to the touch.

    I believe it should be a single one line of code, but the more I get into the code, everything seems to be returning a delta.
    Even getting a value in a range to remap onto another would do (using Lerp or InverseLerp).


    Could you please help me or provide a hint in the right direction?
    I don't think getting up to the Touch.position is the way to go, seems too "low level" (and prone to errors with scaling and offsetting according the rect) and not in line with the level of abstraction provided by InControl.

    I'm pretty sure there's some direct way to do it, but I'm pretty new with using InControl and I'm a bit lost.

    Thanks!
    Alex
     
  6. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    Hey Alex,

    Sorry for missing your e-mail. You're not missing anything—it's not what the control does. It's all about giving the movement delta. I'm not sure why you wouldn't just be using TouchStickControl for this, but I'm sure you have a reason. :)

    All that said, it's fairly easy to modify. Just replace this method in TouchTrackControl.cs:

    Code (CSharp):
    1.  
    2. public override void SubmitControlState( ulong updateTick, float deltaTime )
    3. {
    4.     if (currentTouch == null)
    5.     {
    6.         SubmitRawAnalogValue( target, Vector2.zero, updateTick, deltaTime );
    7.     }
    8.     else
    9.     {
    10.         var worldPoint = TouchManager.ScreenToWorldPoint( currentTouch.position );
    11.         var x = Mathf.Clamp01( Mathf.InverseLerp( worldActiveArea.min.x, worldActiveArea.max.x, worldPoint.x ) );
    12.         var y = Mathf.Clamp01( Mathf.InverseLerp( worldActiveArea.min.y, worldActiveArea.max.y, worldPoint.y ) );
    13.         var value = new Vector2( x - 0.5f, y - 0.5f ) * 2.0f;
    14.         SubmitRawAnalogValue( target, value, updateTick, deltaTime );
    15.     }
    16.  
    17.     // var delta = thisPosition - lastPosition;
    18.     // SubmitRawAnalogValue( target, delta * scale, updateTick, deltaTime );
    19.     lastPosition = thisPosition;
    20.  
    21.     SubmitButtonState( tapTarget, fireButtonTarget, updateTick, deltaTime );
    22.     fireButtonTarget = false;
    23. }
    24.  
    Now LeftStick.Vector will be in the range [(-1,-1) .. (+1, +1)] for the touch in the control active area.

    The control could actually be simplified further since some of the other math it is doing isn't used now. And you could make your own control (just duplicate and rename TouchTrackControl). There's nothing particularly special about it other than it's a component on a gameobject child of InControl/TouchManager gameobject. You'd probably need to duplicate TouchTrackControlEditor too.
     
    RemDust and NeatWolf like this.
  7. NeatWolf

    NeatWolf

    Joined:
    Sep 27, 2013
    Posts:
    924
    Thank you so much Patrick! :)

    So it was intendedly missing, my solution was similar, but way less elegant since I'm still prototyping :p

    I actually extended the TouchTrackControl class... but had some troubles doing it: most of the fields were private and not protected, and some useful fields were not exposed.
    So I had to edit the source files... which is... a bit suboptimal when a new update comes out :)

    I'd rather extend the class rather than duplicating it.

    Could you please enforce extensibility on next release, making most of the private fields protected, and most of the methods overridable - where appropriate, of course?

    That would help a lot, in the long run, and derived classes would be a little more maintainable :)

    Thanks again for the help (I was also considering to use a draggable Stick, I'm trying to find the sweetest spot for my needs:) )

    Best,
    Alex
     
    Last edited: Dec 28, 2018
  8. pixilestudios

    pixilestudios

    Joined:
    Apr 5, 2014
    Posts:
    10
    Hi there! The plugin has been working great so far, but I am having a strange issue with one user. His game crashes on startup with:
    ERROR: SymGetSymFromAddr64, GetLastError: 'Attempt to access invalid address.' (Address: 00007FFF2F4C22B3)
    0x00007FFF2F4C22B3 (InControlNative) (function-name not available)
    0x00007FFF48103034 (KERNEL32) BaseThreadInitThunk
    0x00007FFF4A2C3691 (ntdll) RtlUserThreadStart
    (from output_log.txt)

    I am using InControl 1.7.1 with Unity 2017.3.0f3. Unfortunately I can't symbolicate his .dmp file because I don't have the InControl PDB file. Maybe you can?
    When I got him to remove the InControlNative.dll from the game folder, the game worked for him. So something must be happening with it I guess? Their OS is Windows 10 (10.0.0) 64bit.

    Thanks.
     
  9. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    I've had an occasional report of this crash, but so far have been completely unable to reproduce or track this down. Symbolication attempts have failed for me too, possibly because it's a release build. Not to mention I've worked on the native input plugin since then so I don't have the original PDB anymore.

    If I gave you a debug build of the DLL along with the PDB file, do you think you could make a dev build of your game for the player? Do you think they would be willing to assist in trying to track this down?

    If so, please get in touch by e-mail and I'll get you the files: http://www.gallantgames.com/contact
     
  10. sdtr443w

    sdtr443w

    Joined:
    Nov 29, 2014
    Posts:
    23
    I'm trying to put some polish on controller bindings on the PC and I'm getting caught up on two-axis bindings. They're not included in CharacterActions.Actions so I never scoop them up in the binding GUI. Instead, I get their constituent parts, which include displaying the bindings for the individual +/- axes that make them up. I'm trying to clean this up and it looks like I have to hard-code it. I wanted to make sure this was correct.

    I'm assuming I will have to just filter out the component actions that make up the two-axis ones when I iterate the actions. Afterwards, I have to call out to my two-axis bindings directly instead of using CharacterActions.Actions, and map back directional pad and controls I get from the device to the appropriate stick or pad when remapping.

    There's some other goofy stuff I've done I'm hoping for correction or reinforcement. I have some "compound actions" I've created where they are defined by other bindings. Particularly, my GUI submit and cancel actions are based on existing bindings. So I had to do a whole thing to update them when their constituent bindings are redone, and I had to change their rules to allow more than one binding on any given controller at a time. I was wondering if there was something like this already built into InControl.

    A final thing: I am using an XBox One controller right now as a reference on my PC and I was getting Back and Start as the names for bindings to the Windows and Menu buttons. Is this expected? I am trying to map the buttons to icons so I had to add in those rules.
     
  11. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    Yup, pretty much the way to do it.

    Something that could help with the filtering is to make use of the UserData property on actions. You can store something on there that includes flags for hiding or other associations you may need.

    Not other than the various options in listen options that allow for duplicate bindings. Have a look at the BindingListenOptions class, and those can be set differently on each action instead of on the action set as a whole. There are so many different setups for controls in games I took the approach of trying to provide the building blocks and hooks to accomplish whatever you need instead of trying to cover every scenario with a shortcut. A combination of custom listen options and hooking into the callbacks during the listen process to add any additional custom logic should enable you to do almost anything you need. It's pretty much expected that you use these callbacks even if just for UI updates.

    I'm going to venture a guess that you have XInput enabled, in which case InControl doesn't know the exact controller type, only that it's an XInput compatible device. Microsoft's API provides no further information, and in their API they refer to those buttons as "Back" and "Start". I still recommend sticking with XInput anyway. It's just generally more reliable.
     
  12. ChillyMcChill

    ChillyMcChill

    Joined:
    Nov 17, 2016
    Posts:
    57
    Has anyone used this with PSvita?

    I am not sure how I would get it working
     
  13. joaobsneto

    joaobsneto

    Joined:
    Dec 10, 2009
    Posts:
    152
    How can I get a consistent device name or enum type to know if players are using keyboard, Xbox One Controller, PS3 Controller or a generic one? The InputDevice returns very inconsistent results in name value and I can't find any other field that might give this information.
     
  14. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    You can use the DeviceStyle property on InputDevice (and also LastDeviceStyle on PlayerActionSet and PlayerAction) which will give you an indication of what kind of controller it is. There’s also a DeviceClass property which, currently, is almost always going to be controller, but in the future could support other hardware types.

    Keyboard mappings only work on PlayerActionSet (keyboard and mouse are not currently instances of InputDevice in the devices list), so you can find out what kind of input was used using the LastInputType property on both PlayerActionSet and PlayerAction. It returns one of the BindingSourceType enum. http://www.gallantgames.com/pages/incontrol-bindings-faq
     
    joaobsneto likes this.
  15. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    It's been a few years since I've heard of anyone using InControl on PS Vita, but last I heard it was working. There is a mapping profile for basic input on the Vita, so it should just show up like any other controller. If it's not working for you, I'd recommend building the TestInputManager scene for device to get some kind of idea of what's going on. It may be that the mapping profile needs some adjustment.
     
  16. sdtr443w

    sdtr443w

    Joined:
    Nov 29, 2014
    Posts:
    23
    Okay good to know. I did have the native input enabled and XInput enabled beyond that. I should probably put a comment in my source.

    I've moved on to the next frontier. I disabled the XBCD device profile I created for this other old original xbox controller I was using* so I could get the generic buttons (Button0... Analog0...) and test binding with them. This is just covering my butt on the PC if somebody plugs in God-knows-what. I have a whole thing set up that searches inputs for component directions in a two-axis action. So I have left, right, up, down detected and whether they were detected by going positive or negative--if they were analog. The problem is about plumbing. I don't know how to bag that all up and assign it to a PlayerTwoAxisAction. How do I close that loop?

    *by the way, I had sent an email asking if you wanted that profile and another one for an fairly ubiquitous--albiet old--Playstation-to-PC USB adapter. I'm testing with that, an original xbox controller, and an original Microsoft XBox One controller.
     
  17. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    I feel like you might be trying to duplicate existing features? Binding controls on unknown/unmapped controllers is supported. You just need to explicitly enable it in the listen options (see IncludeUnknownControllers, and potentially IncludeNonStandardControls).

    If you still want to do it manually, you don't assign directly to the PlayerTwoAxisAction, rather you assign bindings to the four component directional actions that it references.

    Sure, feel free to send me profiles. I don't mind including them as long as they don't conflict with existing profiles.
     
  18. sdtr443w

    sdtr443w

    Joined:
    Nov 29, 2014
    Posts:
    23
    Okay I think I can poke at that. I didn't know to look for those listening options and I just kind of threw my arms up with PlayerTwoAxisAction didn't have anything to work with. I had already created a new class that exposed the component actions so I could inspect them, so I can try to work off of that instead.
     
  19. sdtr443w

    sdtr443w

    Joined:
    Nov 29, 2014
    Posts:
    23
    I think I have it mostly working. What caught me off-guard was the device type for this controller changed from InputDeviceClass.Controller to InputDeviceClass.Unknown. I had a diagnostic routine trying to grab the controller to poll the controls and show me what's going on while binding was running. There are still a few pecularities; I should probably test if I'm getting a previously-bound component in case they slip their finger while going through the directions, and something is causing me to have to double-do my first binding in the series. It's still probably something I did but I need to check it.

    Edit: I think the issue with having to press the first binding down twice has to do with the nature of unknown devices. I believe that InControl waits until one button is pressed before it formally starts using the device. So the first button I'm pressing is being gobbled up for that. It's only an issue because my test scene right now just has this dialog coming up immediately; more practically, it will buried under the main menu and the user will have fiddled with the controller before getting this far.

    (Even more practical: they'll use a controller from this decade and never run into this corner case I'm worrying over lol)
     
    Last edited: Jan 25, 2019
  20. joaobsneto

    joaobsneto

    Joined:
    Dec 10, 2009
    Posts:
    152
    Hi,

    I'm making an user interface for input customization. I'm using sprites to represent each button. How is the easiest way to get a reliable information about the input binding? I suppose that I should cast the the BindingSource to DeviceBindingSource and get the InputControlType enum data for controllers and cast BindingSource to KeyBinding and get Key from the GetKey Method for the keyboard. Is that right?
    In the bindings example you can start listening input, but when I press Shift it waits for another key for key combination. How can I listen for shift only? And how can I listen for a specific device?

    Thanks!
     
  21. MetaMythril

    MetaMythril

    Joined:
    May 5, 2010
    Posts:
    150
    Any luck with this? I've had a user run into this as well. With InControl 1.7.1 on Unity 2018.2.7f1

     
  22. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    Pretty much. There's a bit of example code here: http://www.gallantgames.com/pages/incontrol-bindings-faq

    Set IncludeModifiersAsFirstClassKeys = true on the listen options.
     
    joaobsneto likes this.
  23. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    We ran into a dead end. The debug build didn't crash, so there was no way to symbolicate.

    You could try the latest beta, available here: http://www.gallantgames.com/downloads

    That includes release DLLs though. If you want to try the debug DLLs for the native plugin, e-mail me and I'll send them to you.
     
  24. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    Oh, I should mention, another user ran into a crash on startup and it turned out to be a cheap USB pedal that was plugged in, so perhaps ask the user to check if it's a specific device causing it.

    For what it's worth, I've been trying to reproduce the crash with the same pedal on my PC with no luck so far.
     
  25. hododoho

    hododoho

    Joined:
    Oct 9, 2017
    Posts:
    12
    Hello, are there any plans to officially support JoyCons for the Nintendo Switch?
     
  26. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    They work on Nintendo Switch when doing Switch development with the official SDK and an additional plugin that can be requested by licensed Nintendo Switch developers:
    https://developer.nintendo.com/group/development/getting-started/g1kr9vj6/middleware/incontrol

    However, Joy-con do not work properly with desktop systems. They do pair, but behave erratically and as I recall not all input works properly. They are console controllers, not intended to be used with PC/Mac and so cannot be easily supported for that. I believe there's a few third-party drivers out there that may make them appears as XInput or standard desktop controllers, so you could look into that, but I can't speak to their reliability or safety.
     
    hododoho likes this.
  27. IndieMarc

    IndieMarc

    Joined:
    Jan 16, 2017
    Posts:
    183
    There seems to be some errors with the XBOX 360 controllers on Windows 10. Same controllers on mac seems to work but on windows its wrong.

    The two triggers return the same value. So device.LeftTrigger.WasPressed will return true if you also press the right trigger. Which is wrong when you want to use both.

    I fixed it by implementing my own code for just the triggers. But that doesn't tell me if it will work or not with other devices/platforms. The reason I use this plugin is that I don't have all the controllers/platforms in the world.

    But at the moment its not working with windows + xbox 360 which is not like it was something super rare.

    I think the fix is to use AXIS 9 and AXIS 10 instead of AXIS 3 which reads both trigger. The code of InControl probably check axis 3 but it needs to be fixed to have different input for different triggers.

    Thanks!

    Edit: This is my fix BTW
     

    Attached Files:

    Last edited: Mar 9, 2019
  28. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    This is a known issue and will be addressed in the next update. You can download the latest beta here: http://www.gallantgames.com/downloads after creating an account and adding your Asset Store InControl invoice number.
     
  29. SimplePanda

    SimplePanda

    Joined:
    Feb 10, 2019
    Posts:
    3
    Greetings; I'm not sure if this is a known issue / has a workaround but try as I might I can't find anything to point me in the right direction here. Short of just reading through the InControl code to find a solution, does anyone know if there is a workaround to InControl Touch and the Post Processing v2 package seemingly not working together?

    As soon as I have a Post Processing layer on my Main Camera the InControl Touch controls (buttons, sticks) simply disappear. I've checked layering, volume attachments, etc and I can't see anything obvious. It feels like it's maybe a depth or culling issue of some kind?

    Any ideas? Perhaps @pbhogan might shed some insight? :)
     
  30. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    I tried reproducing this by creating a new project in Unity 2018.3.9f1, importing InControl 1.7.3 (latest, though it shouldn't matter) and the Post Processing 2.1.4 package. I opened the "TouchControls" example and set up a post processing layer on the main camera, post processing volume and a post processing profile with a couple of effects to make sure it's working. All the controls still show.

    So, either I missed something or it's specific to your project. But if you want to send me a minimal project with just InControl, the Post Processing package and what ever else is necessary to demonstrates the issue, I'll be happy to dig into it for you.

    A wild guess is you might try creating a new layer and moving all the touch controls to that instead of using the UI layer, which InControl uses by default. Don't forget to change the Controls Layer in the Touch Manager, and your main camera layer mask to match. It wouldn't surprise me too much if Post Processing does something specific with that layer since it's usually used for Unity UI components.
     
    SimplePanda likes this.
  31. SimplePanda

    SimplePanda

    Joined:
    Feb 10, 2019
    Posts:
    3
    If it's not too much trouble, do you still see the touch controls when you build out and run it on an iOS device? I can see them when I play my demo in Editor, but they only disappear when they actually boot up on hardware (any iOS device I have for testing ).

    Also, even on iOS hardware the touch controls work as expected. It's just that the visual indicators (button graphic or stick graphics) aren't drawing.

    So it seems to be a difference between Editor and Hardware.
     
  32. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    Well... it certainly seems like a weird Post Processing bug. After a bit of experimentation, I found that simply setting the Touch Camera clear setting to "Depth Only" instead of "Don't Clear" caused it to work. It's nothing special to InControl it seems. I was able to reproduce it simply with two cameras and a sprite, built for iOS.

    I'll probably try to set up something I can submit to the PP2 project as an issue. Digging through their issues, there's all kinds of similar glitches. Not sure PP2 is ready for production yet.
     
    SimplePanda likes this.
  33. SimplePanda

    SimplePanda

    Joined:
    Feb 10, 2019
    Posts:
    3
    Aww! Bummed to know it's a bug but happy to know there's a fix, that I wasn't manufacturing something specific to my project, and that there may be a solution path through the PP2 side.

    Thanks for the help and thanks for InControl. :)
     
  34. hododoho

    hododoho

    Joined:
    Oct 9, 2017
    Posts:
    12
    Hiya, I just updated from 1.5 to 1.7 and seem to be running into some issues with controller identification.

    Previously, I was relying on PlayerAction.Device.DeviceStyle, and was getting stuff like InputDeviceStyle.XboxOne or InputDeviceStyle.PlayStation4 back. I've tried switching to both PlayerAction.LastDeviceStyle and PlayerAction.ActiveDevice.DeviceStyle, and both of these seem to be returning nothing but InputDeviceStyle.Unknown. Might you have any thoughts or suggestions on how to fix the issue?

    Edit: Think I figured it out. Was using stuff in an OnActiveDeviceChanged hook, but ActiveDevice hadn't changed yet. Guess I need to use the handler's parameter instead. Why is Device changed from being public? To avoid confusion with ActiveDevice?

    Edit2: Upon further inspection, it looks like LastDeviceStyle never seems to get updated, even though the device passed into the OnActiveDeviceChanged hook has the correct DeviceStyle information.
     
    Last edited: Apr 23, 2019
  35. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    I'm not sure PlayerAction.Device was ever anything but internal -- if it was, it was by mistake as it's not intended for public querying. Although, it's hard to remember back to version 1.5 so maybe it was. :) PlayerActionSet.ActiveDevice and PlayerAction.ActiveDevice would serve that purpose today. The latter was added in 1.6.9 so perhaps that's when PlayerAction.Device was made internal if it was public.

    PlayerActionSet.Device is public, but it's purpose is to restrict the action set to a single device, similar to using
    IncludeDevices and/or ExcludeDevices. And that would be more for a multiplayer scenario where you have a bunch of action sets.

    PlayerAction.LastDeviceStyle does update, but only if one of the controls bound to the action gives input. Same goes for PlayerActionSet.LastDeviceStyle if one of its actions updates. So, for example, if you don't have the right bumper bound on the action PlayerAction.LastDeviceStyle will not change if you press it. And if none of the actions change, PlayerActionSet.LastDeviceStyle will not change.

    PlayerActionSet.ActiveDevice and PlayerAction.ActiveDevice work the same way. They only change if the device gives input through a binding to one of the actions on an action set or the action, respectively.

    If what you're looking for is getting the style of the last device to give input regardless of bindings, then use InputManager.ActiveDevice.DeviceStyle

    InputManager.OnActiveDeviceChanged does fire after InputManager.ActiveDevice and PlayerActionSets / PlayerActions have updated. So possibly what you were seeing was simply the PlayerAction.ActiveDevice not having changed at all due to the control pressed not being a binding as described above.

    So to be clear, it's entirely possible for InputManager.ActiveDevice and PlayerActionSet.ActiveDevice to not be the same, for multiple reasons: the device not being one of the included devices on the action set or the control pressed not being a binding on the action / action set.

    Sorry to be so verbose, but the bindings API and concept of active devices is actually quite a complex subject overall. An additional consideration, for example, is multiple controllers could give input at the same time. Incidentally, InputManager.ActiveDevices (plural) gives you all of these for a given tick. InputManager.ActiveDevice is one of those with some "sticky" behavior to make sure it doesn't switch unnecessarily if it's still referring to an active device.
     
    hododoho likes this.
  36. hododoho

    hododoho

    Joined:
    Oct 9, 2017
    Posts:
    12
    Thanks so much for the explanations! Makes a lot of sense, and InputManager.ActiveDevice is definitely what I wanted all along. Also was definitely looking at a PlayerAction that hadn't been pressed at all yet, didn't realize that its LastDeviceStyle was specifically tied to it being used as an action. Super helpful info!
     
  37. joaobsneto

    joaobsneto

    Joined:
    Dec 10, 2009
    Posts:
    152
    I did some tests with IL2CPP and now I'm getting this error even when I use Mono. It seems it's not loading the dll of XInput. The build process is not copying the file to this folder. It does not even have a "Mono" folder, just Managed.


    Code (CSharp):
    1. Fallback handler could not load library C:/Projetos/JoshJourneyGame/Builds/build_8/JoshJourney_Data/Mono/XInputInterface32
    2. Fallback handler could not load library C:/Projetos/JoshJourneyGame/Builds/build_8/JoshJourney_Data/Mono/XInputInterface32.dll
    3. Fallback handler could not load library C:/Projetos/JoshJourneyGame/Builds/build_8/JoshJourney_Data/Mono/XInputInterface32
    4. Fallback handler could not load library C:/Projetos/JoshJourneyGame/Builds/build_8/JoshJourney_Data/Mono/libXInputInterface32
    5. Fallback handler could not load library C:/Projetos/JoshJourneyGame/Builds/build_8/JoshJourney_Data/Mono/libXInputInterface32.dll
    6. Fallback handler could not load library C:/Projetos/JoshJourneyGame/Builds/build_8/JoshJourney_Data/Mono/libXInputInterface32
    7. ArgumentNullException: Value cannot be null.
    8. Parameter name: type
    9.   at System.Activator.CreateInstance (System.Type type, System.Boolean nonPublic) [0x00003] in <9229fee076854c3bae71b15fb8601b84>:0
    10.   at System.Activator.CreateInstance (System.Type type) [0x00000] in <9229fee076854c3bae71b15fb8601b84>:0
    11.   at InControl.UnityInputDeviceManager.AddSystemDeviceProfiles () [0x00011] in C:\Projetos\JoshJourneyGame\Assets\InControl\Source\Unity\ .cs:269
    12.   at InControl.UnityInputDeviceManager..ctor () [0x00030] in C:\Projetos\JoshJourneyGame\Assets\InControl\Source\Unity\UnityInputDeviceManager.cs:25
    13.   at (wrapper managed-to-native) System.Reflection.MonoCMethod.InternalInvoke(System.Reflection.MonoCMethod,object,object[],System.Exception&)
    14.   at System.Reflection.MonoCMethod.InternalInvoke (System.Object obj, System.Object[] parameters) [0x00002] in <9229fee076854c3bae71b15fb8601b84>:0
    15. Rethrow as TargetInvocationException: Exception has been thrown by the target of an invocation.
    16.   at System.Reflection.MonoCMethod.InternalInvoke (System.Object obj, System.Object[] parameters) [0x00014] in <9229fee076854c3bae71b15fb8601b84>:0
    17.   at System.RuntimeType.CreateInstanceMono (System.Boolean nonPublic) [0x000a8] in <9229fee076854c3bae71b15fb8601b84>:0
    18.   at System.RuntimeType.CreateInstanceSlow (System.Boolean publicOnly, System.Boolean skipCheckThis, System.Boolean fillCache, System.Threading.StackCrawlMark& stackMark) [0x00009] in <9229fee076854c3bae71b15fb8601b84>:0
    19.   at System.RuntimeType.CreateInstanceDefaultCtor (System.Boolean publicOnly, System.Boolean skipCheckThis, System.Boolean fillCache, System.Threading.StackCrawlMark& stackMark) [0x00027] in <9229fee076854c3bae71b15fb8601b84>:0
    20.   at System.Activator.CreateInstance[T] () [0x00015] in <9229fee076854c3bae71b15fb8601b84>:0
    21.   at InControl.InputManager.AddDeviceManager[T] () [0x00001] in C:\Projetos\JoshJourneyGame\Assets\InControl\Source\InputManager.cs:435
    22.   at InControl.InputManager.SetupInternal () [0x00114] in C:\Projetos\JoshJourneyGame\Assets\InControl\Source\InputManager.cs:202
    23.   at InControl.InControlManager.OnEnable () [0x0009b] in C:\Projetos\JoshJourneyGame\Assets\InControl\Source\Components\InControlManager.cs:61
    24. (Filename: <9229fee076854c3bae71b15fb8601b84> Line: 0)
     
  38. joaobsneto

    joaobsneto

    Joined:
    Dec 10, 2009
    Posts:
    152
    I found the bug. It was the API Stripping Level on High. I changed to low and it worked.
     
  39. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    Okay, good to know. There's an attribute that prevents stripping out I might be able to use to prevent that from happening. I know something similar also happens with device profiles, so until that's addressed, full API stripping isn't going to work. I'd imagine it's going to be a problem with a lot of assets though... basically any time code isn't explicitly referenced (which happens a lot with reflection or dynamic type instantiation) there's going to be a problem with automated code stripping.
     
    joaobsneto likes this.
  40. frankadimcosta

    frankadimcosta

    Joined:
    Jan 14, 2015
    Posts:
    203
    Hi, i have a question about the rumble. Can I use it in a windows store building ?
    It's seems no possible, but ... any plan to support it ?
    TNX !
     
  41. Deleted User

    Deleted User

    Guest

    Hello, I was wondering why 'DontDestroyOnLoad' is marked on by default. I need to turn it off, and would like to be aware of the consequences.
     
  42. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    As far as I know rumble works in UWP builds as it uses Microsoft's Windows.Gaming.Input framework for controller support. Outside of that InControl needs to use XInput for rumble to work on Windows which I'm not sure is supported in Windows Store apps. Note, rumble only works with Xbox 360 and Xbox One controllers and XInput compatible clones. No other controllers currently support rumble on Windows.
     
  43. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    It's enabled by default because it's the most often used scenario and in general it's better to have InControl persist through scene changes otherwise it has to do a full teardown and setup on every scene change. InControl also prevents a duplicate from loading if there's one in the target scene, so it's generally a safe option. If you want to turn it off, go right ahead. All it's doing is calling Unity's Object.DontDestroyOnLoad on the manager component (https://docs.unity3d.com/2019.1/Documentation/ScriptReference/Object.DontDestroyOnLoad.html) and if you turn it off, it won't call it.
     
  44. binster

    binster

    Joined:
    Oct 16, 2012
    Posts:
    13
    Hello! I just upgraded Unity from 2018.2.18 to 2019.3.0a3 and I'm getting an error with InControl - primarily being that the "using UnityEngine.EventSystems;" line in InControlInputModule.cs is unable to find a match - and looking through the autocomplete in VS there's only a UnityEngine.Events namespace that looks close, but it doesn't provide the same methods (such as PointerInputModule).

    I expect this isn't a bug with InControl, but I've tried a number of things to fix the problem and I'm stuck. I deleted the InControl folders from the Project and reimported, I deleted the .sln and .csproj files to force an assembly rebuild... no progress.

    I hope that you can help me fix whatever problem I caused by upgrading Unity! :(

    EDIT - for reference, I tried reimporting all assets as per this thread, that didn't work either. https://forum.unity.com/threads/uni...tsystem-missing-reference-in-pc-build.392044/

    EDIT 2 : There's also this, but I'm not sure what to do with this baffling new information... https://stackoverflow.com/questions...hen-compiling-this-assembly/30731370#30731370
     
    Last edited: May 26, 2019
  45. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    I will for sure look into this and try to have a fix out in the next update if necessary. However, typically InControl is only upgraded to work with whatever the current beta version is somewhere near the end of the beta cycle as the beta tends to have several changes before release. With an alpha it's far worse. It may just be a bug or temporary oversight on Unity's part.

    As tempting as it is to try out new features, the alphas and betas are primarily intended testing, or maybe prototypes. I wouldn't use the beta versions of Unity for an actual project, especially not one with third-party code assets, much less the alpha version.

    I'd strongly recommend just keeping your project upgraded to whatever the latest stable version of Unity is (currently 2019.1.4f)
     
    binster and Willbkool_FPCS like this.
  46. binster

    binster

    Joined:
    Oct 16, 2012
    Posts:
    13
    Thanks, and I think you're right. I was too eager for the new LWRP changes - I'll just go ahead a downgrade to 2019.1.4f.

    EDIT - To confirm, that's solved the problem. I am a confirmed overeager doofus. :)
     
    Last edited: May 27, 2019
  47. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    Okay, so looking into this it appears that Unity uGUI has been moved to the Package Manager and out of the standard Unity library. It's installed by default in Unity 2019.3, but since packages are in their own assembly definitions, the InControl assembly doesn't know about it by default. The fix is fairly simple. Just add the Unity.ugui assembly to the InControl assembly definition as a reference.

    This gets rid of the error, but no guarantees on anything else working. :)
     
  48. Vagabond_

    Vagabond_

    Joined:
    Aug 26, 2014
    Posts:
    1,148
    Hi @pbhogan , is there a way to know if the currently bind control to an action is a stick or a button.
    What i want it to be able to use a custom smooth function in case some buttons are set to an action instead of the analog sticks which provide smooth values and the buttons are snapping to -1 and 1, so i need so use another value then based on that ?

    NOTE : I am not sure if i ask correctly as i am trying to integrate InControl since a couple of days and currently learning how to work with it !
     
  49. snugsound

    snugsound

    Joined:
    Mar 9, 2014
    Posts:
    17
    Hey Patrick, I'm trying to upgrade to the latest version for the "Android offscreen touch" fix, however, when I do so, I receive errors such as the following:

    Assets/InControl/Source/Touch/Editor/TouchButtonControlEditor.cs(12,29): error CS0234: The type or namespace name `EditorTextures' does not exist in the namespace `InControl.Internal'. Are you missing an assembly reference?


    To my recollection, I've not moved any of the InControl scripts around. Any ideas? I'm running Unity 2018.4.1f1.
     
  50. pbhogan

    pbhogan

    Joined:
    Aug 17, 2012
    Posts:
    377
    A few scripts had to move around at some point in a recent update. Most likely you just need to delete the InControl folder entirely before importing. Unfortunately Unity doesn't do this for you even though it really should.

    InControl also supports assembly definitions now, so if you get another error after doing all that and it seems like your code can't see InControl and you're using an assembly definition for your code, then you'll need to reference InControl's assembly in there.