Sunday, November 10, 2013

Android Rover Client Improvements

I've made a number of improvements to the rover's Android client over the last couple weeks. These were based on feedback from a friend who drove it.

We first set up my home router to pass connections from the internet on the rover's control ports to the rover on my home network. That enabled my friend to connect from him home and drive it around my house. Seeing him remotely control it from 40 miles away was great fun. He reported that the video worked well and the rover drove well, but the client had some issues with reliability and usability on his phone, which was a different screen resolution. He also recommended I switch to a horizontal orientation to maximize screen use, and let me tinker with his ARDrone, which has a pretty nice Android client.

I first corrected a reliability problem - since the control device sends a command, and then waits for a sensor value from the rover (currently signal strength on the rover), it's important to tell quickly when the rover is no longer responding. As on the server, I set a short timeout value on the client socket, which causes an exception to be thrown if the rover doesn't respond within 2 seconds. Upon that exception, the client goes into a loop trying to connect every 2 seconds. The rover is set to time out after a second, so it should recover and start to listen again on the control port within the 2 second window the client waits for.

With that in place, even on a fairly flaky network connection, the client will do it's best to reconnect to the rover. I also added an LED indicator and signal strength indicator so you could tell when the rover was approaching the edge of the range of the WIFI.

These indicators are ImageViews which switch between different images. All the artwork is modified from images on Open Clipart, which is a very cool resource for those of us with no artistic talent.

My buddy also recommended that the app confirm a press of the exit button, and to save the last IP that was used so that the user does not have to enter it each time. I did some reading and found the Android SharedPreferences feature, which is a dead easy way to save user preferences without messing with direct file IO.

At this point, it's pretty reliable. It's been driven over the Internet several times, including over a cellular 3G connection. Over high speed Internet connections at both ends, it's surprisingly smooth and responsive. Unsurprisingly, it noticeably lags over the cell network. A more efficient video encoding scheme, like H264, would undoubtedly improve that.

I'm pleased with the result. It's been a great way to learn some Android, and how to control something over a network.

In case it's helpful to someone, here's the code.