An Odopod Hack Days project that draws using simulated gravity forces, Orbit is a mobile web application using multi-touch events, canvas API and offline cache.
The blank canvas includes two gravity wells. To start drawing, add orbiters by tapping or swiping the screen. Try different directions and speeds to get different paths. For a single orbiter, points and lines are drawn along the path. Once there are two or more orbiters, lines and fills will be drawn between the different paths.
single orbiter (left) and multiple orbiters (right)
Settings are provided in the bottom left of the screen to pause the orbiters, turn different drawing layers on and off and to clear the drawing.
Try Orbit out for yourself.
Multiple canvases
Each layer in Orbit is rendered into a unique canvas. All together, there are five canvases. Using multiple canvases slows down the application; however, the ability to turn each layer on and off as the drawing progresses was important to me. Besides, even with five canvases, the application performs quite well.
different drawing layers within Orbit
If you find the performance too slow, here’s a tip: the application will continue to draw into hidden canvases, but since rendering the pixels to the screen is the primary performance bottleneck it will run much more quickly when one or more canvases are hidden (especially connections and fills).
Handling multiple touches
Handling the touch events is relatively straightforward. The browser provides events for touchstart, touchmove and touchend. Since any of the canvases can be hidden, I bound the events to each one of them.
The touch events include an identifier which I use to associate touchmove and touchend events with the original object created on touchstart. Once the touch has ended, it is important to clear the identifier from the object. This is because any future touchstart event can use the same identifier (this actually happens quite often).
On iOS devices the browser will generate events for multiple touches at a time but Android browsers currently only recognize a single touch at any time. This code works for both cases.
jQuery Mobile
jQuery Mobile is used to create the settings and the about screens as well as the settings UI elements. The mobile framework organizes application screens into pages and dialogs. I included all pages for Orbit within the index.html file.
For the settings, I use different controls based on the size of the screen. For tablets, I have settings open on the main drawing page, but switch to a dedicated page on smaller devices. At first I had all devices using a separate page, but switching between pages is cumbersome and on tablet screens, there is enough room for my options on the main screen.
iPad settings (left) and iPhone settings (right)
Incidentally, I used buttons with a non-breaking space as the text string rather than buttons without text because those buttons were too small to easily touch.
text buttons (left) and icon only buttons (right). icons alone are hare to tap.
Offline mode
The last thing I had time to tackle before Hack Days came to a close was to create a cache manifest, startup screen and application icon so that Orbit would work well offline. The one trick I had to work out here was how to provide startup screens appropriately sized for both the iPhone and iPad. In the end, I did this by rewriting the link tag using JavaScript.
add to homepage in mobile safari (left) and Orbit on iPad home page (right)
All-in-all I was impressed with the browser’s touch events and canvas performance.