Life Dial Status Update

Giant Growth

Life Dial has been doing rather well since I launched it on the android market. So well in fact that it just passed Omnivore in active downloads despite the fact that the latter has been out since February.

I don’t think that Life Dial has an objectively larger audience than Omnivore, and I haven’t publicized one more than the other either. So why the large uptake? Continue reading

Mucha-Inspired Webcomic Prints

I’m a big fan of both Questionable Content and Dresden Codak. I got to meet the creators in person back in May when I attended TCAFand while I was there I picked up a couple of signed prints. Earlier this month I finally got around to taking the prints down to a local framing shop where they mounted them for me. Now I have them on my walls, and they look gorgeous. Here are some pics:

Both these prints are available online:

Sticking it Old School

Here’s a shot from our team’s first monthly planning session last week, courtesy of Joey1. Even though we have a huge amount of technology at our disposal, sticking post-its on the wall was the perfect way to prioritize our tasks for the next four weeks. Of course the first thing we did after this picture was taken was put the items into Basecamp, but physically writing everything out made it really easy to fiddle with priorities and add new items without worrying about squashing anyone else’s ‘edits’.

We totally stole this idea from BarCamp‘s scheduling sessions. I’ve never had the opportunity to go to an unconference,  but from our own little experiment I can definitely see how this bottom-up approach to planning and organization has been a success there.

  1. Specifics have been blurred out to protect our seekrit plans!

Nerf Warfare

There is an arms race at our office. This is my contribution (Click for full version).

Apparently it’s suitable for children over the age of 8, but I doubt an 8-year-old would be able to even lift it. It has a tripod and thanks to the position of my desk I can cover the door to the lobby from my seat.

Introducing: Life Dial

My latest project is now available for download: Life Dial.

Life Dial is a simple companion app for Magic: The Gathering players that tracks your remaining life as well as poison counters. It uses a dial control as the input for changing the life and poison totals, which I believe to be more usable than a slider, +/- buttons, or swipes/flings. All changes are made in a single gesture whether large or small. Big changes can be quickly approximated with fast rotations, but fine adjustments can still be made by simply slowing down.

The UI is as simple as I could make it. Life and Poison totals are displayed at the top left and top right respectively, and an extra gesture total appears to help you keep track of the current change you’re making. The menu button reveals a reset function that sets the totals back to the standard 20/0. I’m very happy with it as it stands, but I have plans to add a few extra features to track stats in special game-types such as Commander.

Life Dial on the Android Market

(This post is also available on Inflatable Apps)

The Flying Developer is a Street Fighter

One of the popular ways to unwind at the office is a quick round or two of Street Fighter IV on our XBox 360. Street Fighter is serious business at Shopify, we have fight sticks and everything. Unfortunately for me, most people have been playing it for way too long and trounce me every time I play. To rectify this, I’ve bought my own copy of the game to play on evenings and weekends.

Learning the basics of a new video game is a lot like learning a new programming framework. In fact, getting to grips with Street Fighter has been a lot like my experience learning Rails. Rails is all about ‘convention over configuration’, and SF is no different. Special moves vary between characters, but there are common themes that run through the controls: Moves requiring you to swing the thumbstick in quarter-circles, half-circles and zig-zags are everywhere. Even if you’ve never played a character before you can usually guess one or two of their moves based on these conventions.fKnowing these gives you a good head-start and provides a base for developing more complex strategies. Further down the line, mastering these shapes results in the ability to pull of crazy combos. I’m not at that stage yet.

If you want to get really good (just as in software development) you need to do more than just fiddle around. After playing with a few of the characters I decided to do some background reading. Unfortunately the second-hand copy of SF I bought only came with a French manual, so I picked up a strategy guide from Chapters and got reading. Beyond the basic ‘punch and kick til the opponent stops moving’, there’s definitely an underlying framework that can be learned and taken advantage of. Once again, the parallels with programming are apparent. Moves all belong to one of several primative types, and characters can be classified by their play-style.

Speaking of playing styles, watching people play is an interesting experience. There are two dominant schools that I’ve observed. The aim of the first seems to be to press buttons as fast as possible, and the second instead values frugality. It’s funny to watch the two battle it out, one person tapping buttons at machine gun speed, while the other seems to move in slow motion by comparison. I’m not sure which is the ‘better’ method, and I suspect at this stage that there are characters that cater to each.

After playing about 6 hours of the game over the last two weekends, I’m pleased to say that I managed to beat the game’s arcade mode. Online play is still looking pretty scary, so I think I’ll test my mettle against my co-workers over the next few days and see if my research and practice stands up to human opposition.

How To Write an Android App That I’ll Use

Last week, Mark Jaquith posted an article entitled ‘How to write a WordPress plugin that I’ll use‘. It occurred to me that a similar document about Android apps would be a useful and fun thing to write. A lot of his points carry over, but there are some Android-specific points that I’d like to expand upon.

Use shared functionality, use shared data

One of my favourite things about Android is the ability to re-use functionality from other apps. Some of these are no-brainers: If you need the user to select a picture, use ACTION_PICK. Email? Use ACTION_SEND. This extends beyond the standard system intents. OpenIntents has a whole slew of intents that you can use to accomplish any number of tasks. Before you write a given feature into your app, go there and see if someone has already done it. You’ll save time, effort, and won’t have to maintain the extra code. As a concrete example, Omnivore uses Zebra Crossing’s barcode scanning intent to read barcodes.

Share your functionality, share your data

My first point wouldn’t be possible if developers didn’t make their features available for reuse in the first place. You should do this. Take a look to see if your app performs a function that has an existing intent and if there isn’t one, create it yourself. Omnivore doesn’t do this yet, but eventually I want other apps to be able to access the food list for other purposes (e.g. creating shopping lists, finding recipes).

Don’t ask for unnecessary permissions

I was once in the market for a chess clock app. The most popular one at the time asked for both internet and location permissions. Sorry, what? How are either of those going to improve the application for me, the user. Advertising doesn’t count as a valid reason for including a permission by the way. I’m fine with apps that make calls to ad-servers on the back of legitimate internet access, but including permissions for the sole purpose of showing ads isn’t on.

Use Android UI/UX conventions

When I press the menu button in an app and nothing happens, I get sad. Similarly, whenever I see an iPhone-esque back button in the top left I shake my head in disappointment. Users (myself included) expect certain things to function certain ways. Imagine installing a desktop app that didn’t use the default keyboard shortcuts for copy/paste, undo/redo or save/load. Everything still works, but it feels out of place and wrong.

Testing Webhooks

Webhooks are an emerging feature in many great APIs. They allow you (or rather, your applications) to avoid polling a service for data by pushing events to you as they happen. However, this aspect makes them tricky to test outside of a production-ready environment. Fortunately, there is a really simle method that makes consuming webhooks in a development environment a breeze.

The Problem

Whereas most API calls are initiated by your application, webhooks originate from the API provider’s own servers. Because of this role reversal, an app’s testing environment must be publicly accessible if webhooks are being used and tested. One solution is to use a free hosting solution such as a single Heroku dyno or App Engine to temporarily run the app while you test. I did this for a while but it didn’t suit my iterative development process as every time I made a change I had to re-deploy the app. So how does one test features that require a publically visible server from behind a firewall or network gateway?

The Solution

Enter localtunnel. Localtunnel is a free service that creates an SSH tunnel from your machine to the outside world using a custom url on their site. All this is done behind the scenes by a Ruby gem so you don’t know the first thing about SSH in order to get it working. Here’s how you set it up:

Prerequisites: You’ll need ruby and rubygems installed to take advantage of localtunnel.

  1. Open a console and install the localtunnel gem:
    gem install localtunnel
  2. If you don’t have one, set up a public/private keypair. On Linux or Mac, open a terminal and run
    ssh-keygen

    Accept all the defaults. On Windows it’s a bit trickier but your best bet is to install PuTTY and follow the instructions here: http://kb.siteground.com/article/How_to_generate_an_SSH_key_on_Windows_using_PuTTY.html

  3. The first time you run localtunnel you’ll need to tell it about your public key, followed by the port you wish to forward:
    localtunnel -k ~/.ssh/id_rsa.pub 3000
  4. Each subsequent time you can  just specify the port you wish to expose to the outside world:
    localtunnel 3000
  5. Copy the url that is returned into your app as the base for your webhook handler addresses:
    Port 3000 is now publicly accessible from
    http://44ea.localtunnel.com ...
  6. Register your webhooks with the service you’re using.

That’s it! You can now test webhooks or other push features to your heart’s content. When you’re done, just terminate the localtunnel process to close the connection1.

  1. The one downside is that the address localtunnel provides changes each time you run it, so don’t rely on it staying the same between sessions.