Category Archives: Android

Multipart HTTP Post requests with Volley on Android

It’s been a little while since I’ve done any really serious Android development, but a couple of projects have brought me back to it.

Early on in one of those projects I had to make some HTTP requests, my first thought was to make use of the Apache HTTP Client classes as I had done many times before on Android. Which is why I was a little surprised when the usual ctrl-space didn’t auto complete any of the expected class names.

It turns out the classes were removed in Android 6.0 and the notice suggests using the HttpURLConnection class. A little bit more digging turned up a wrapper for this called Volley.

Volley is a wrapper round the HttpURLConnection class to provides a neat asynchronous interface that does IO in the background and then delivers results to the Main thread so UI updates can be done with out further faffing around switching threads. There is also a nice set of tutorials on the Android Developers pages.

The first few requests all worked fine, but there was one which was a little bit more tricky. The HTTP endpoint in question accepts a multipart-form payload. A bit of googling/searching on Stackoverflow turned up a number of approaches to this and best seamed to be documented in this gist

This was close to what I wanted but not quite what I needed so I have taken some of the core concepts and built my own MultipathRequest object.

...
MultipartRequest request = new MultipartRequest(url, headers, 
    new Response.Listener<NetworkResponse>() {
        @Override
        public void onResponse(NetworkResponse response) {
        ...
        }
    },
    new Response.ErrorListener() {
        @Override
        public void onErrorResponse(VolleyError error) {
        ...
        }
    });
    
request.addPart(new FormPart(fieldName,value));
request.addPart(new FilePart(fileFieldName, mimeType, fileName, data);

requestQueue.add(request);
...

I’ve stuck the code up on github here. You can include it in your Android Project by adding the following to the build.gradle in the root of the project:

allprojects {
  repositories {
    ...
    maven { url 'https://jitpack.io' }
  }
}

And then this to the dependencies section of the modules build.gradle:

dependencies {
  compile 'com.github.hardillb:MultiPartVolley:0.0.3'
}

Auto Launch Webpages full screen on Android

While waiting for Amazon to get round to reviewing my Node-RED Alexa Smart Home Skill I’ve needed something to hack on.

I’ve been keeping an eye on what folk have been doing with Node-RED Dashboard and a common use case keeps coming up. That is running the UI on a Android tablet mounted on a wall as a way to keep track of and control things around the house. This got me thinking about how to set something like this up.

Icon

For the best results you really want to run this totally full screen, there are ways to get this to happen with Chrome, but it’s a bit convoluted. Sure you can add it as a shortcut on the home screen but I thought there had to be a easier/better way.

So I started to have a bit of a play and came up with a new app. It’s basically just a full screen Activity with a WebView, with a few of extra features.

Settings
Settings
  • Set URL – Pick a URL to load when the phone boots, or the app is launched.
  • Launch on boot – The app can be configured to start up as soon as the phone finishes booting.
  • Take Screen Lock – This prevents the screen from powering off or locking so the page is always visible.

You can change the URL by swiping from the left hand edge of the screen, this will cause the action bar to appear, from this you can select “Settings”.

Set URL to Load
Set URL to Load

The app is in the Google Play store here, the code is on Github here

Physical Web Lightswitch

Physical Web Logo
As I’ve mentioned before I’ve been having a playing a bunch of WeMo kit and also looking at using Bluetooth LE and Physical Web beacons. I’ve been looking at putting the 2 together to solve a problem I’ve been having round the house. (Also one mentioned by somebody [@mattb I’m told by @knolleary], sorry can’t remember who, at this years ThingMonk)

Belkin ship a mobile phone app to control their products but it has a few drawbacks:
Belkin WeMo App

  1. Launching the app takes ages
  2. Vistors need to know what type of lights you own, then they have to install the right app
  3. You have to give visitors access to you Wifi
  4. Once you’ve granted access to the WiFi, Visitors are granted full control of your lights, including when no longer attached to the same network with no way to revoke access

(Having been reminded by @knolleary -> More of these types of problems discussed in @mattb’s Thingmonk talk at this year)

The Physical Web approach deals with the first 2 of these really nicely, a phone will detect the Eddystone beacon and offer a link to the control web page, so no app needed and no need to identify what type of devices you have, you just need to be close enough to it.

The second 2 problems are a little bit more tricky. Due to mitigation of some privacy problems at the moment to get the best out of a Physical Web URL it needs to be publicly accessible, this is because when a device detects a beacon it tries to access the URL in order to pull some summary/meta data to help with presenting it to the user. The problem with this is it exposes the devices IP address to the guys who deployed the beacon, which allows for the possibility of tracking that user. The workaround is that the Physical Web spec says that the URLs should be accessed by a proxy hence shielding the device from the URL, the problem is these proxies are all on the public internet and can only see public sites. But this does mean since it’s on the public internet you don’t need to give guest net access.

All this gets round problem number 3, but means that control for your living room lights needs to be publicly exposed to the internet. Which brings up nicely to problem 4, if it’s on the public internet how do you control who has access, once somebody has used the URL in the beacon it will be in their internet history and they can comeback and mess with your lights from home again.

You can add authentication to the URL, but a careful balance about how long any signed in session lasts will need to be struck as you don’t want to be flapping around in the dark trying to enter a password to turn the lights on. While this is big scary problem there is a potential solution to all that I’ll touch on at the end of this post.

There is one other problem, URLs broadcast via Eddystone beacons have to be less than 18 bytes long which is pretty short, while there are some encoding tricks for common start and end sections (e.g. ‘http://www.’ & ‘.com’) that reduce these sections to just 1 byte, that still doesn’t leave room for much more. You need to use a URL shortner to do anything major.

Trying things out

While thinking about all this I decided to spin up a little project (on github) to have a play. I took the core code from my Node-RED WeMo node and wrapped it up in a little web app along with the bleno and eddystone-beacon npm modules. I could have done this using Node-RED but I wanted to be able to support control via straight BLE as well.

The code uses discovery to find the configured light bulb or group of bulbs

wemo.start();

if (!wemo.get(deviceID)) {
  wemo.on('discovered', function(d){
    if (d === deviceID) {
      device = wemo.get(d);
      console.log("found light");
    }
  });
} else {
  device = wemo.get(deviceID);
  console.log("found light");
}

It then starts up an express js webserver and creates 2 routes, 1 to toggle on/off and one to set the brightness

app.post('/toggle/:on', function(req, res){
  console.log("toggle " + req.params.on);
  if (req.params.on === 'on') {
    wemo.setStatus(device,'10006',1);
  } else {
    wemo.setStatus(device,'10006',0);
  }
  res.send();
});

app.post('/dim/:range', function(req,res){
  console.log("dim " + req.params.range);
  wemo.setStatus(device,'10006,10008','1,' + req.params.range);
  res.send();
});

It also sets up a directory to load static content out of. Once that is all setup then it sets up the Eddystone beacon

eddystone.advertiseUrl(config.shortURL, {name: config.name});

Enabling Physical Web on You Phone

If you want to have a play yourselves there are a couple of approaches to enable Physical Web discovery on your phone. The first is a mobile app built by the physicalweb.org guys, it’s available for both Android and iOS. When you launch this app it will seek out any Eddystone beacons in range and display a list along with a summary

Recently Google announced that they were rolling Physical web capability into the their Chrome Web browser. At the moment it is only available in the beta release. You can down it on Android here and the this link has instructions for iOS. I have not tried iOS instructions as I don’t have a suitable device.

Once it’s been installed these instructions explain how to enable it.

Now we have a beacon and some way to detect it what does it look like

Discovered beacons

The Physical Web app has detected 2 beacons (actually they are both the same beacon, using both BLE and mDNS to broadcast the URL). Both beacon are on my private network at the moment so the proxy could not load any of the meta data to enrich the listing, it could also not find my private URL shortener http://s.loc. If I click on one of the beacons then it will take me to a page to control the light. At the moment the interface is purely functional.

Light interface

This is working nicely enough for now, but it needs to be made to look a bit nicer and could do with presenting what brightness level the bulb is currently set to.

Direct device communication

I mentioned earlier there was a possible solution for the public network access requirement and authentication. There is a working group developing a specification to allow web pages to interact with local BLE devices. The Web Bluetooth API Specification is not yet finished but an early version is baked into Chrome (you can enable it via these instructions). This is something I intend to play with because it solves the whole public facing site problem and how to stop guests keeping remote access to your lights. It doesn’t matter that you can download the control page if you still need to be physically close to the beacon to connect via BLE to control the lights.

I’ve added 2 BLE GATT characteristics to the beacon (1 for on/off and 1 for dimming) and when I get another couple of free hours I’m going to improve the webpage served up from the beacon to include this support. Once this works I can move the page to my public site and use a public URL shortener which should mean all the meta data will load properly.

All this also means that with the right cache headers the page only needs to be downloaded once and can then loaded directly from the on device cache in the future.

Android Wear after a week

It’s been a little over a week since I picked up a LG G Android Ware device to play with.

My initial impression seams to hold, it’s ok, but it’s not going to change my world.

We got hold of some Samsung G Lives this week so I’ve swapped to see if there is any difference between them.

Samsung Gear Live

The Samsung looks a bit better, but the out of the box experience was not as good, it wasn’t charged (unlike the LG), it needed updating as soon as it was started (the same as the LG) but it hid the update progress meter down in the settings so it wasn’t obvious that it was doing something when I powered it on. The charging cradle is a fiddly little thing to fit and feels really cheap compared to the really nice magnetic tray that came with the LG.

The only extra feature the Samsung has is a heart rate monitor built into the back of the watch. This is interesting but does require the watch to be warn tight round the wrist. I normally like to let my watches move around a bit so it’s taking a bit of getting used to and I’m not sure I’ll keep it that long. The only real use for the heart rate monitor is going to be during exercise, which is when I’m even more likely to want the device to be loose on the wrist.

Samsung Gear Live Charger

So far I’ve not been impressed enough to with the Android Wear devices to buy one for myself or even to borrow one from work to use for an extended period of time. I will keep an eye on the app developments to see if anybody can come up with a truly compelling use case for one. It will also be interesting to see if the Motorola Moto 360 is any different.

First Impressions – Android Wear – LG G Watch

One of the benefits of working for ETS is that we occasionally get hold of toys to play with, recently a box of LG G Watches turned up so I grabbed one to have a play with.

IMG_20140708_152939

IMG_20140708_152929

IMG_20140708_152924

Previously I’ve one of the first iteration of Android linked “smart watches”, namely the Sony Liveview. The first version of these really were not great, especially the fact that only the very edges of the screen were touch sensitive didn’t help interacting with them. And the strap wasn’t that comfy so all in all not a good experience.

The LG G seams much better out of the box, the whole screen is touch surface and it has a look and feel much closer to a modern digital watch. The set up process was relatively painless (once I’d overcome some local issues with the office wifi), there was the now usual immediate device update that all modern devices seam to suffer from, but it didn’t take that long.

So far I’ve just been wearing it in the office having it pop up new mail, sms and calendar notifications at the same time as my phone, but I’m out of the office with a research partner for the next 3 days so it will be interesting to see if it’s useful while I’m on the road. There seams to be a deep integration with Google Now which should be useful.

The biggest thing that will determine how useful the whole Android Wear idea is going to be battery life, I’ll keep an eye on it and see how long it lasts.

I also need to have a look at the API to see if I can come up with something fun to do with it and the sensors contained in the device. I do know that the notifications from Tracks2Miles are showing up.

Chromecast UK Launch and iPlayer support


I mentioned last year that I had managed to get somebody to bring me a Google Chromecast back from the US and I was pretty impressed with it.

Yesterday was the official UK launch and to go with it the BBC announced that the Android and iOS iPlayer applications would both be supporting the device. This is great news and really adds to the capability of the device.

Up until now I’ve mainly been using mine to watch a films and TV series I’ve bought from Google Play and to play my music through the TV + sounds system in my living room. But with iPlayer support I can see it getting a lot more use, as I tended to watch iPlayer content on my Nexus 7 which is ok, but a little bit small.

The iPlayer app just adds the little cast icon to the title bar of the app and if you connect to a Chromecast it sends the device rather than firing up the video app on the phone. The BBC seam to have done a decent first pass with a nice lock screen integration showing the program art. I gave it a test drive catching up on the last 2 episodes of Salamander that I had missed, the quality was great and playback was near instant (but that may be as much to do with my fibre broadband as anything else).

I’m even seriously considering buying my folks one so they can use iPlayer as the only time they’ve used it so far is when I’ve been back up home and plugged one of the laptops into the TV for them. Dad has an Android phone already and there was some talk of them getting a tablet for my niece to use when she visits.

The only problem I see with it is the price, at £30 it’s 3 times the cheapest price you can get a NOW TV Box for.

The only thing left if for me to finally get round to updating my MythTV setup so I can make use of the HLS support in the new version and write a Android app to display recorded shows via the Chromecast.

Google Chromecast

I managed to get my hands on a Google Chromecast at the weekend. Many thanks to Mike Carew for bringing one back from the US for me via Dale.

Having unpacked the stick I plugged it into my TV and plugged the usb cable in to power it. At first nothing happened and the little notification light on the device stayed red. but replugging the power cable it jumped into life. The instructions directing me to http://www.google.com/chromecast/setup, I had to do this in the Chrome browser and on my Windows laptop as there is no setup app for Linux at the moment (There is a config app for Android, but this is only available for US users at the moment)

When I got to the point where I had to configure which WiFi network the chromecast should connect to there was a problem as my router’s SSID was not showing in the list. It took a couple of minutes for me to remember that I had set my router to use channel 13 as it’s normally lightly used. The reason it is lightly used is because in the US you can only use channels up to 11. A quick change of channel later and the network showed up in the list.

The next part is the only bit that is not as slick as it should be. The Chromecast was fully configured but when I tried to use one of the apps (I’ll talk about those in a moment) it would not show a Chromecast available to send data to. The problem was that my router had done it’s usual trick of walling each of the separate WiFi device from each other, this feature can be called a few things but the most common seams to be apisolation. In a place with shared WiFi like a coffee shop or hotel this is good as it stops people snooping on or attacking your machine, in the home environment this may not be suitable and in this case very much unwanted. I had run into this problem before as one of my MythTV frontends is on WiFi and I had changed the settings to allow WiFi cross talking but the router seams to forget the setting pretty quickly, my usual trick was to reboot my router if I needed to log into it from my laptop to fix things. This was going to become a real issue with the Chromecast. After bit of digging I found a forum post about how to tweak the settings via the telnet interface so quickly ran up an expect script to do it when needed.

#!/usr/bin/expect

set timeout 20
set name SuperUser
set pass ###########

spawn telnet 192.168.1.254

expect "Username : "
send "$namer"
expect "Password : "
send "$passr"
expect "{SuperUser}=>"
send "wireless mssid ifconfig ssid_id=0 apisolation=disabledr"
expect "{SuperUser}=>"
send "saveallr"
expect "{SuperUser}=>"
send "exitr"

This gets called by the script I’ve got bound to a button on my remote driving LIRC that changes the input on my TV from RGB used for MythTV to the HDMI socket used by the Chromecast which ensures my network is always setup properly. I really shouldn’t have to do this but O2 Wifibox III I have is not the best.

Once I’d got all that out of the way time to start actually using this thing for what’s made for. Out of the box there is support for the Chromecast baked into the latest version of the Android YouTube app, Google Play Music, Google Play Movies and Netflix app. I don’t have a Netflix account at the moment so I tried out the other 3.

YouTube app

When the YouTube app finds a Chromecast on the local network it adds the little cast icon to the Action bar. When you tap on this it displays a pop-up to all you to select the Chromecast (if you have more than one on the network) and then rather than play the video on the devices screen they are played on the TV. Play/Pause and volume control are available on the device. One other really nice feature is that the Chromecast maintains a queue of videos to play so you can add to the queue from your phone while it’s playing the current video, in fact if you can do this from multiple devices at the same time. This means you can take it in turns with your mates to see who can find best cat video.

Google Play Movies
Much like YouTube Google Play movies lets you play content on the Chromecast. I had rented a copy of Mud the week before getting hold of my Chromecast so I watched this on the TV rather than on my Nexus 7. The only odd part was that I had downloaded a copy to the device and it would not let me watch it via the Chromecast without deleting the local copy.

Google Play Music
The music app works as expected, showing the cover art on the screen while it plays the tracks. Because it streams tracks directly from the cloud if you are working through a playlist and hit a track that you have added directly to the storage on the phone then it will refuse to play even if you have pushed a copy of the file to Google Music’s cloud storage.

Away from applications on your Android device there is a plugin for the Chrome browser which allows you to share the content of any tab on the large screen. I need to have a look at using this for giving HTML5 based presentations.

There is a API for interacting with the Chromecast and and I’m going to have a look at writing an app to push MythTV recordings so I can replace one of my MythTV frontends. First impressions of the API make me think this shouldn’t be too hard if I can set up the right transcoding.

Over all I’m pretty impressed with the Chromecast and I’m still debating if I should ask my folks to bring me another one back as they are out in the US at the moment.

developerWorks Days Zurich 2012

This week I had a day out of the office to go to Zurich to talk at this years IBM developerWorks Days. I had 2 sessions back to back in the mobile stream, the first an introduction to Android Development and the second on MQTT.

The slots were only 35mins long (well 45mins, but we had to leave 5 mins on each end to let people move round) so there was a limit to how much detail I could go into. With this in mind I decided the best way to give people a introduction to Android Development in that amount of time was to quickly walk through writing reasonably simple application. The application had to be at least somewhat practical, but also very simple so after a little bit of thinking about I settled on an app to download the latest image from the web comic XKCD. There are a number apps on Google Play that already do this (and a lot better) but it does show a little Activity GUI design. I got through about 95% of the app live on stage and only had to copy & paste the details for the onPostExecute method to clear the progress dialog and update the image in the last minute to get it to the point I could run it in the emulator.

Here are the slides for this session

And here is the Eclipse project for the Application I created live on stage:
http://www.hardill.me.uk/XKCD-demo-android-app.zip

The MQTT pitch was a little easier to set up, there is loads of great content on MQTT.org to use as a source and of course I remembered to include the section on the MQTT enabled mouse traps and twittering ferries from Andy Stanford-Clark.

Here are the slides for the MQTT session:

For the Demo I used the Javascript d3 topic tree viewer I blogged about last week and my Raspberry Pi running a Mosquitto broker and a little script to publish the core temperature, load and uptime values. The broker was also bridged to my home broker to show the feed from my weather centre and some other sensors.