Speed Up Your Ionic Application Using These Techniques

Written by on August 29, 2015

Speed Up Your Ionic Application Using These Techniques

This article is something I wanted to write in the last few months. After spending the previous few years developing hybrid mobile applications, I came to know a few tips and tricks to make them faster.

At this point, hybrid mobile development is still behind native applications. What we gain in code reusability we lose in app speed. Thankfully, we can mitigate this problem as much as possible.

Note: If this tutorial was helpful, you need further clarification, something is not working or you have a request for another Ionic post? Furthermore, leave me a comment below if you don't like something about this blog, if something is bugging you, don't like how I'm doing stuff here. Feel free to comment below, subscribe to my blog, mail me to dragan.gaic@gmail.com. Thanks and have a nice day!

Design Improvements

Less is More

Most of the times, mobile applications will work in an environment that’s connected to the internet. But that doesn’t mean it’s good to use external resources. Your future users may not have such a fast mobile access, and what looked like an ordinary application boot up for you may look like a slide show for them.

The most common example I know of is loading external Google Maps V3 framework JavaScript files.

Minify and Uglify Everything

Every file you initialize in your Ionic application will slightly decrease your application speed and performance. This problem becomes much more apparent if you’re using a large number of files.

Minification is a process where we’re removing unnecessary characters, like white space characters, new line characters, comments, and sometimes block delimiters, from our JavaScript and CSS files. Uglification goes a step further by replacing variable and function names with much shorter texts thus making them smaller and harder to read.

  • Always make sure you’re using minified versions of CSS and JS files, this process is reversible.
  • Uglification is also reversible but much harder to read.
  • If possible merge all nonessential files. Everything that is not essential for your initial application bootup.
  • Never use more than you need.
Optimize Images

Even compressed images can take a loot of space. No matter if you’re using JPEG or PNG images, compress them as humanly as possible. Use tools like compressor.io to achieve lossless compression.

For smaller images, logos, icons use CSS sprites. This is a technique of merging smaller images into one single large image and using them via CSS background position.

If you’re required to use real image tags instead of background-image CSS property, you can convert them into a BASE64 string representation and handle them like this:

<img width="16" height="16" src="data:image/gif;base64,R0lGODlhEAAQAMQAAO....." />

CSS approach:

image {
  background-image:url(data:image/gif;base64,R0lGODlhEAAQAMQAAOR...)
}
Fewer Images

If possible, instead of images, use CSS font icons, like Ionicons. Every image less will result in a shorter loding time.

Preload Images

Let’s say you were smart and images are packaged together with the application. When the images are displayed for the first time, there will be a visible pop effect (like they came out of nowhere). Thet’s why it’s important to preload images depending on an active view. Andrew McGivery has an excellent article on this topic: Preload images in Ionic using $ImageCacheFactory.

Move Everything To The Back

JavaScript initialization can significantly reduce initial application speed. To mitigate this, move every nonessential JS file to the bottom of your page. Just before end of BODY tag and(or) use the “async” and “defer” attributes if you can:

	<script type="text/javascript" src="some.js"></script>
</body>
</html>

You can test this approach until you find a perfect balance.

Fewer views/pages/elements/steps

Carefully design your application before you start coding and make it as minimal as you can.

  • Never use more pages than you need
  • Reuse your pages. For example if you’re creating a master-detail pattern view, don’t use a separate page for every element on a master page. This pattern should always have one master page and one detail page
  • Don’t use page elements if you don’t need them, like tabs or slide navigation
  • It’s much faster to generate new DOM content than manipulate existing one
  • If possible avoid direct DOM manipulation, it’s much better to create a custom directive
  • Avoid unnecessary scrolling and large pages, they will result in excessive memory use.
  • The most significant content must be available in the shortest number of steps and page retrievals

Last, but not least. Limit the usage of input boxes. No matter what mobile framework I was using, they would always misbehave in some way or another. Consider using any other form element instead, like selects, radio buttons, checkboxes, and other controls.

And FFS don’t autofocus input fields on page load, that’s the most stupid thing you can do. If you trigger focus event before a page is fully loaded, a software keyboard may cause a content jumping effect. Do this ONLY if you’re working on a chat application, in a proper AfterLoad event.

Don’t use unecesarry libraries

Please, don’t use something like jQuery just so you can use append function, learn a friking JavaScript.

CSS Improvements

Avoid pixels

And use percentages or ems instead. If you use pixels, what looks great on your phone may look too small or too large for some other devices. Even better, use Ionic grid system as much as possible.

No amimations > CSS animations > JavaScript animations

If possible don’t animate your content, or if you still need to use CSS animations over JavaScript animations. What may look like an excellent addition to your application may ruin a final look and feel.

Remember, animations are a resource and process heavy, especially to the Android environment. iOS behaves much better.

Use Hardware-Accelerated CSS

If you can’t work without animations, use hardware-accelerated CSS. It’s better to do this using smart device GPU than CPU. This way, the CPU can do other important tasks for us.

Keep it flat, Shadows are evil

Only thing worse then animations are shadows, opacity, and gradients. No matter what type, text shadows are as bad as box shadows. Both of them, including opacity, have a great impact on application performance. You can improve the FPS of your application by 50% just by using a simple flat design.

On the other hand, worst-case scenario, it’s better to use images that already include opacity and shadows than to add them via CSS.

Example, nothing killed jQuery Mobile as much as overuse of box shadows.

Avoid decorative CSS and content

No, your page should not look like a Christmas tree, less is more. More content will clutter your page and DOM, which will additionally slow down any future content generation.

Ionic Improvements

Learn AngularJS

Hell yeah, the best way to make your Ionic application faster is to learn how AngularJS works.

I would advise going the John Papa way, read John Papa Angular Style Guide. Once you master this, you can consider yourself an AngularJS developer.

View Caching

View caching is the second most important performance enhancement Ionic feature.

By default, views are cached to improve performance and Ionic will cache a maximum of 10 views. But it’s also important to understand how caching works. Each time you navigate away from a view it will go to cache and scope is disconnected. On the other hand, when navigating back in the history, the “forward” views are removed from the cache.

By why am I talking about caching if it works by default?

Sometimes is more important not to cache some views. Remember when I told you that it’s better to create a new DOM element(s) than to change existing one(s)? This perfectly translates to Master-Detail pattern where detail page almost always displays different content. It’s much better to create this content from the scratch than to modify the existing page.

Change number of cached pages like this:

$ionicConfigProvider.views.maxCache(0);

Configure it in the state provider:

$stateProvider.state('someState', {
   cache: false,
   url : '/someUrl',
   templateUrl : 'someTemplate.html'
})

Or via directive attribute:

<ion-view cache-view="false" view-title="Some Title!">

</ion-view>
Native View Transition Animations

By default, Ionic uses CSS-based view transitions. They will work great on stronger smartphones, just don’t use them on a non-flagship device.

We can play around this problem with Telerik Cordova Native Page Transition plugin. Though originally made for KendoUI, it will also work with Ionic.

The tutorial can be found here: Handling Native View Animations With Ionic Framework.

Use collection-repeat instead of ng-repeat

Collection-Repeat allows an app to show huge lists of items much more performantly than ng-repeat. Technically, it renders into the DOM only as many items as are currently visible. This is meant for those of you who like to go crazy using huge lists.

Unfortunately, depending on some elements, collection-repeat can additionally slow down your application. Plus you can’t combine it with native scrolling. Which brings us to…

<ion-content>
  <ion-item collection-repeat="item in items">
    {{item}}
  </ion-item>
</ion-content>
Native scrolling

Native scrolling is a rather new addition to Ionic Framework, currently only available to Android devices.

This feature provides a much better feeling than the classic JavaScript scrolling. Unfortunately, it’s not available to every platform, nor it works with every component (like previously mentioned collection-repeat).

Native scrolling can be enabled using overflow-scroll=’true’ on your ion-content or using the $ionicConfigProvider to set it globally in current versions of Ionic.

<ion-content overflow-scroll='true'>

</ion-content>
Pull-to-Refresh and Infinite Scroll

Another way to mitigate large list performance drop is to use Pull-to-Refresh and/or Infinite Scroll components.

The ionInfiniteScroll directive allows you to call a function whenever the user gets to the bottom of the page or near the bottom of the page. On the other hand, ion-refresher allows you to add pull-to-refresh to a scrollView.

Infinite scroll:

<ion-content ng-controller="MyController">
  <ion-list>
  ....
  ....
  </ion-list>

  <ion-infinite-scroll
    on-infinite="loadMore()"
    distance="1%">
  </ion-infinite-scroll>
</ion-content>

Pull-to-Refresh:

<ion-content ng-controller="MyController">
  <ion-refresher
    pulling-text="Pull to refresh..."
    on-refresh="doRefresh()">
  </ion-refresher>
  <ion-list>
    <ion-item ng-repeat="item in items"></ion-item>
  </ion-list>
</ion-content>
Crosswalk

Last year, people were looking at the Crosswalk like it was going to single-handedly save Android hybrid development. Some of them were right, older Android devices will perform better thanks to it, but you should also expect possible bugs and a lot bigger application.

On the other hand, you’re doing something wrong if you need Crosswalk to make your application usable.

Additional Steps

  • Test your application on older devices, thet’s the best way to detect current and posible future problems
Categories

10 thoughts on “Speed Up Your Ionic Application Using These Techniques”

  1. Every suggestion from this post is relevant. All the way from caching to optimizing images, these techniques cover most of the basic considerations you must have when developing for any deployment. Nice write up, thank you!

  2. Nice article, but I hope not useless because in the plugin’s homepage i read this “The plugin focuses on enterprise-only distribution and may not compliant with all public store vendors.”. Hmmm. Has someone try it with an apple “in the apple store” app ?

  3. Great article, it has saved me a lot of hours of research. But I did not understand something…

    I’m thinking on a simple Master-Detail app: one Master view and one Detail view. You said: “when navigating back in the history, the ‘forward’ views are removed from the cache”. However, you recommend to disable the cache for the Detail view. I think there’s no need to do that because “forward cache” is disabled by default. I’m right?

    • I meant that in a slightly different way, I’ll rewrite that part.

      Your’re correct, forward cache is disabled. But, depending on an application, sometimes you will not go back. Instead you may change page through side menu or top/bottom navigation depending on a platform. In lot of these cases you don’t want to return back at a detail view.

  4. Generally fine but I would advise testing pure ionic and then with crosswalk.

    On repeat collection you can build image grid with divs and wabt to put usernames, presence and index data plus a pull to refresh image capability then Crosswalks rendering much faster and silky smooth. You certainly will not be doing anything wrong adding crosswalk.

    Also javascript performance boosted by nearly several times. When you flip between the two and keep optimizing you notice the difference.

  5. Do you have an ionic application for Android that we can see in action, which has these techniques applied to them? That way we can compare it to our own application and see if the difference in speed and performance is noticeable enough to justify the time and resources necessary for these changes. Thank you so much. I really appreciate this article, and I’m going to change my mobile approach to use hybrid solutions.

Leave a Reply