- Hello World!
- Cordova Initialization
- Leveraging Cordova APIs
- Structuring Your Application's Code
- The Generated Web Application Files
- Responsive Design and Cordova
- Wrap-Up
Structuring Your Application’s Code
The way you structure the code for your web application is a matter of personal style, but for Cordova applications, and for some web applications, there may be a valid reason to use a particular approach. So far in this chapter I’ve set up my example applications so that everything, the HTML content as well as the JavaScript code, is in the same file. Additionally, I’ve broken things up a bit so the examples are simple and easy to read. There are a lot of things a developer can do to write more efficient and compact code—here I’ve deliberately not done them to make the examples as easy to read as possible.
A web developer will usually want to separate an application’s HTML from its JavaScript code. In the simple applications I’ve shown here, there’s not much of each, so it’s not a big deal. But for more complicated applications, when there’s a whole lot of code, separation of the two types of code can make the code easier to maintain and allow multiple developers to work on different parts of the application (UI versus application logic) separately.
There is, however, a Cordova-specific reason why you will likely want to do this. Remember how I explained earlier that the Cordova container needed to initialize itself? Well, if you think about an application that has several Cordova plugins added to it, it might take some time for the Cordova container to initialize itself, and for all of the plugins to initialize themselves as well. What I’ve found in many sophisticated Cordova applications is that large web applications and/or a bunch of plugins can cause a Cordova application to time out during initialization. It takes so long to load and initialize everything that the Cordova container thinks something’s wrong and fails with a timeout error. I’ve seen this happen most frequently with a large web application using jQuery Mobile.
So, what do you do to avoid this? You structure your web application projects so that the web content and the JavaScript code are separated, and then you take some extra steps to arrange the order in which things happen.
Another reason why you would want an application’s JavaScript code broken out into a separate file is to more easily support JavaScript debugging. Throughout the book I’ll show you many different tools you can use to test and debug your Cordova applications. What I found in my testing of these tools is that most of them are able to interact with an application’s JavaScript code only when the code is not embedded inside the application’s HTML content (the application’s index.html file, for example).
Listing 2.6 shows a simple application I’ve created that is structured a little differently from all of the other examples I’ve shown so far. In this example, two things are different: the application loads all of its JavaScript code after all of the application’s HTML has been defined, plus all of the application’s logic has been split out into a separate JavaScript file called index.js.
Listing 2.6 Hello World #6 Application index.html
<!DOCTYPE html> <html> <head> <title>Hello World #6</title> <meta charset="utf-8" /> <meta name="format-detection" content="telephone=no" /> <meta name="viewport" content="user-scalable=no, initial-scale=1, maximum-scale=1, minimum-scale=1, width=device-width, height=device-height" /> </head> <body> <header> <h1>Hello World #6</h1> </header> <p>This is a simple Cordova application.</p> <script src="cordova.js"></script> <script src="index.js"></script> </body> </html>
When the earlier example applications started up, the cordova.js file was loaded before much else happened on the page. If the cordova.js took a while to load, on a slower device, for example, it might delay the rendering of the page’s HTML content while it waited for the JavaScript to load. So, users of the application might see a blank page before the HTML displayed. If this was a large application, and several JavaScript files were being loaded, this might take some time, enough that the user would notice.
In the Hello World #6 application, all of the HTML loads within the browser context before the cordova.js file is loaded. If the index.js file were quite large, or I was loading jQuery Mobile and a bunch of other JavaScript stuff, the user would at least be looking at some sort of UI as the JavaScript was being loaded.
Listing 2.7 shows the application’s index.js. It contains all of the JavaScript code the application is using. In this example, the file defines a simple function that self-initializes when the file is loaded, adds the event listener for the deviceready event, and provides a function that is executed when the event fires.
Listing 2.7 Hello World #6 Application index.js
var cvaReady; var someOtherFunction = function () { if (cvaReady) { //do something } else { //tell the user why they can't do that } }; (function () { var onDeviceReady = function () { console.log("Entering onDeviceReady"); //Let the user know that the deviceReady event has fired navigator.notification.alert("Cordova is ready", null, "Device Ready", "Continue"); //Set the variable that lets other parts of the program //know that Cordova has initialized cvaReady = true; //=================================================== //Do whatever other stuff you want to do on startup //=================================================== console.log("Leaving onDeviceReady"); }; //add an event listener for the Cordova deviceReady event. document.addEventListener('deviceready', onDeviceReady, false); }());
I’ve added a new feature in this example as well, a cvaReady object that the application can use to tell whether the onDeviceReady function has executed. If you don’t want to wait to do everything until the deviceready event has fired, you can ignore it and check the cvaReady object as needed to see if you are able to do Cordova stuff. I know this is a clunky way to do this; I’m just trying to give you different options for your applications.
When you run into an issue where the Cordova container times out before loading all of your stuff, what some people recommend doing is setting up a timer in your deviceready event listener that waits a few seconds before loading a new page that then loads your application’s JavaScript files. This allows all of the Cordova initialization to complete before anything else is done by the application. This is supposedly one way people have gotten around timing issues with using jQuery Mobile with a large Cordova application, but I’ve never had the need to use this approach.