Like it or not, Android version fragmentation is creating the new class of "IE6" browser for mobile development. With the broad majority (94%) of Android users still using a 2.x version of the platform (according to Google's own stats), Google has created a huge population of mobile users that have a crippled HTML5 browser.
The default Android 2.x browser lacks device orientation events. It lacks XHR2. It lacks Web Workers. HTML5 forms. Oh, and everything SVG!
Newer versions of Android (3+) improve the situation, but even in those cases the default Android browser leaves something to be desired. Google seems to know this, and they are actively developing Chrome for Android (yay!), but so far that's an Android 4+ exclusive.
As a developer targeting mobile HTML5 devices, you have two options for dealing with this Android situation:
Google may be able to make the hard sell and only support Android 4+, but most developers probably prefer to include the 94% of Android 2.x users in their target user base. That means we need to work around the problems.
When we set-out to build our data visualization tools for HTML5, we picked a combination of SVG and VML to power the Kendo UI DataViz rendering. SVG is a vector-based standard, broadly supported on all modern browsers, especially suited for interactive 2D rendering, and VML is a similar Microsoft technology that we use to support older versions of IE. Together, we can deliver richly interactive data viz that works just about everywhere.
Except Android 2.x.
As with most things in the modern web, though, there are always creative solutions for older browsers. By the end of this post, I'll show you how you can easily use Kendo UI DataViz (and SVG) on any version of Android, all the way back to Eclair (Android 2.1).
There are probably many creative ways you could technically solve the problem of SVG on old Android, but for the sake of this post, our available options are:
Unlike Apple's iOS, there are many different browsers (with different HTML/JS engines) available on Android. By simply installing one of these more capable mobile browsers, Android 2.x users can quickly gain native access to more HTML5 features (including SVG). Two popular choices to consider if you want native SVG support on Android 2.x:
Opera Mobile for Android (11.5.5)
Firefox for Android (10.0.1)
Both of these browsers are free, and both natively support SVG. Firefox will deliver the best native SVG experience (including animations), whereas Opera Mobile will properly render SVG, but won't preserve SVG scripting or animation.
So, solving the SVG problem on Android 2.x can be as easy as installing a new browser. Done and done.
BUT…you don't have control over your users' browsers, so let's look at another option.
Android's native browser may lack SVG, but it does support the HTML5 canvas element. That's good news. With the help of some crafty JavaScript, we can take any SVG, parse it, and then render the results to a canvas. The process may sacrifice some fidelity and interactivity that native SVG provides, but it will deliver a functional result.
There are (at least) two popular polyfills that I found to make the process of converting SVG to a Canvas surprisingly trivial:
These libraries are open source MIT (which means you can use them anywhere), and both can take SVG and spit-out a canvas rendering. By simply adding one of these JavaScript files to your project, you can easily swap-out the SVG with an identical canvas rendering when a browser lacking SVG visits your page.
Here's a basic example using the canvg polyfill that renders an SVG string on a HTML5 canvas (note: I've configured this demo to always replace SVG with canvas even if your browser natively supports SVG):
These polyfills are not "automatically" converting SVG to Canvas (though canvg can be used as a passive polyfill). Two or three lines of code is required for this approach. But that's a small price to pay to be able to support SVG-less browsers, like Android 2.x.
Now that we have a polyfill that can convert SVG to canvas, we have a way of making the Kendo UI DataViz charts work on all versions of Android. Here's the basic approach:
The code is dead simple. Assuming you have added a Kendo UI chart to your page and you're using the canvg polyfill, we can do this in less than 10 lines of code:
//Handle Android (or any non SVG browser, except old IE where we want to use VML) if (!Modernizr.svg && !supportsVML()) { //Get chart object and SVG var chartEle = $("#chart"),
chart = chartEle.data("kendoChart"), svg = chart.svg(); //Create a canvas var canvas = document.createElement("canvas"); canvas.setAttribute("style", "height:" + chartEle.height() + ";width:" + chartEle.width() + ";"); //Convert the SVG to canvas canvg(canvas, svg); //Remove the SVG/VML and show the canvas rendering chartEle.empty(); chartEle.append(canvas); }
BOOM! Presto. Do this, and your Kendo UI charts will be automatically converted from SVG to canvas on Eclair (2.1), Froyo (2.2), and Gingerbread (2.3). You can try this for yourself with the complete jsFiddle, where I've also added some code to let you toggle between different chart types (just so you can see the complete support for rendering different chart types). For those without Android devices handy, here are some "money shots":
Android 2.3.3 (Gingerbread - 59% of Android Market)
Android 2.2 (Froyo - 28% of Android Market)
Android 2.1 (Eclair - 7.6% of Android Market)
If you do have an Android 2.x device and want to test this outside of jsFiddle, I've also hosted this demo on htmlui.com via an easy to type Bitly link: http://bit.ly/KendoAndroidSVG (case sensitive!).
Of course, while this cool SVG polyfill gives us the ability to functionally support older versions of Android, we do lose some richness that native SVG offers:
That makes sense. We're rendering the SVG to a static Canvas bitmap, so without more custom code we only have a static view of the chart. But we do have a view of the chart! On Android 2.x, where native SVG is otherwise absent.
Finally, Android 2.1 seems to be a bit more temperamental than 2.2 and 2.3, producing inconsistent results in my tests. Fortunately, it's the oldest and least used 2.x version, so be sure to do some extra testing if 2.1 is an essential target for your app.
If you are using Kendo UI DataViz and you need to support Android 2.x, this simple technique can instantly extend the reach of your solution. By using a simple JavaScript polyfill and a few lines of code, you can render SVG-based charts (or any other SVG, for that matter) using the HTML5 canvas on browsers that lack native SVG support.
Of course, we hope the world moves beyond Android 2.x. Only 4.5% of today's Android users are on versions 3+, and just 1% use Google's latest Ice Cream Sandwich release. If Google fails to fix this problem, we may all soon be looking at Android 2.x with the same ire we've assigned to IE6 for years.
Todd Anglin is Vice President of Product at Progress. Todd is responsible for leading the teams at Progress focused on NativeScript, a modern cross-platform solution for building native mobile apps with JavaScript. Todd is an author and frequent speaker on web and mobile app development. Follow Todd @toddanglin for his latest writings and industry insights.