Exception when calling OuyaController.getControllerByPlayerId before first axis event

Just sent this in as a bug, but I wanted to post in the forums to save people some headache as well. It seems like there's a NullPointerException in this method, so for now you might want to wrap calls to OuyaController.getControllerByPlayerId with try/catch blocks until it gets resolved.
Beast Boxing Turbo - OUYA Launch Title!

Comments

  • tacograveyardtacograveyard Posts: 18Member
    Are you sure this is the case? I use getControllerByPlayer and I have never received a NullPointerException even in game samples that never receive an axis event. The method will return a null if you call getControllerByPlayer and pass a player number for a player that is not currently active. If you call a method (like getButton) on the returned null, then you will receive a NullPointerException.
  • goodhustlegoodhustle Posts: 144Member
    Yes, this is a weird case that occurred only when calling getControllerByPlayer after devices were connected but before any input events have been handled by the OuyaController class (such as at application launch). I sent in a repro case to the OUYA team, and I've also changed my approach to not do things this way.
    Beast Boxing Turbo - OUYA Launch Title!
  • nicknick Posts: 186Member, Administrator, Team OUYA
    The way the current OuyaController class depends on the keyevents wouldn't work this way, but it should definitely not give you guys an NPE  [-X I'll log that as a bug to fix!
  • goodhustlegoodhustle Posts: 144Member
    Thanks @nick, it should already be in there, see ticket 1529. 
    Beast Boxing Turbo - OUYA Launch Title!
  • StretcherStretcher Posts: 6Member
    Thanks for the information, this caused quite a headache and a loss of time to me today.
  • goodhustlegoodhustle Posts: 144Member
    @Stretcher no problem! I am glad this post wasn't useless, I was beginning to think I was the only one getting this. Do you need more info on a workaround?
    Beast Boxing Turbo - OUYA Launch Title!
  • StretcherStretcher Posts: 6Member
    edited February 2013
    @goodhustle I would prefer this issue to be fixed in a next SDK update, but if you have any workaround, please feel free to share for anyone :-)
    Post edited by Stretcher on
  • goodhustlegoodhustle Posts: 144Member
    If you simply want to bypass the NPE's, just wrap those calls in try/catch blocks and tell your users to wiggle the controller in the first screen. :)

    I was able to get around it because I use a polling-based system for Unity to fetch current controller state at the beginning of every Unity frame. I keep controller state stored in a separate object for each controller, indexed by player number, and I use OuyaController to update the state when events occur. In my application, then I access the state objects directly to get current state instead of querying OuyaController directly. 

    It's a little complex, and I don't know if I would recommend it unless you want the entire polling-style mechanism. That being said, here are the java handlers in question: https://github.com/getluky/OuyaUnityBridge/blob/master/ExampleProject/Assets/Plugins/Android/src/OuyaUnityActivity.java#L567
    Beast Boxing Turbo - OUYA Launch Title!
  • BuddyBuddy Posts: 183Member
    edited February 2013
    Looking into this now, I think the problem you are seeing is that OuyaController::getAxisValue actually returns a Float object (which can be null).  So if you had a line like:
    float x = c.getAxisValue(OuyaController.AXIS_LS_X);

    Then it would NPE if getAxisValue returns null and it tries to auto-unbox into a float.

    This doesn't seem useful, so I'll change the declaration to:
    public float getAxisValue(int ouyaAxis);
    And have it return 0.0f if there's been no stick input yet.
    Cheers!
    Post edited by Buddy on
  • goodhustlegoodhustle Posts: 144Member
    Ah, makes sense. Thank you for looking into it, Buddy!
    Beast Boxing Turbo - OUYA Launch Title!
  • StretcherStretcher Posts: 6Member
    edited March 2013
    (Please delete this post, as it is not relevant anymore.)
    Post edited by Stretcher on
  • StretcherStretcher Posts: 6Member
    edited March 2013
    I can confirm that the issue is still not fixed as of ODK 1.0.0. To better show what's happening, I created a small and very simple Android project. Build it and run it on a real Ouya hardware. You can clearly see that if you don't touch anything in your controller, it will not be detected at start because getControllerByPlayer returns null. It becomes detected only when a motion event or a key press is handled.

    https://docs.google.com/file/d/0B2-p1Ue5YqnJblhxelJHT1FHVTQ/edit?usp=sharing (Press CTRL + S to save the zip archive and unzip it on your comptuer).
    Post edited by Stretcher on
  • paulscodepaulscode Posts: 37Member
    Not sure if it is related, but I was getting a NullPointerException from inside the ODK when calling OuyaController.getPlayerNumByDeviceId( int ) prior to any axis events.  I was able to correct the problem by making sure the call to OuyaController.init( Context ) was done first.
  • nicknick Posts: 186Member, Administrator, Team OUYA
    paulscode said:
    Not sure if it is related, but I was getting a NullPointerException from inside the ODK when calling OuyaController.getPlayerNumByDeviceId( int ) prior to any axis events.  I was able to correct the problem by making sure the call to OuyaController.init( Context ) was done first.
    Fixed the NPE on that one :) Just returns -1 now if not init-ed
  • WildsWilds Posts: 78Member
    Fixed it also for me!
Sign In or Register to comment.