JSApps 101: AngularJS In A Nutshell

Introduction

Moving on with the topic, in the previous part of this series, we discussed about that interesting new tendency to let the browser do all the user interface heavy-lifting on the client-side, since it is such a good guy. Of course, this involves a LOT of JavaScript going on, since it is the only language the browser understands besides HTML.

We all know how complex and crazy things can get when you involve JavaScript in the picture. The language is usually seen as over-complicated, it used to be hard to debug, learning curve is steep as hell and it can get confusing quickly; also, there used to be a lack of tools and IDEs with strong support for its development just sums up for bad reputation.

However, fear not! After this article, you will have a solid base on how you can turn the fiendish JavaScript you have known for years from a simple DOM traversal helper to a whole reliable application development framework with the aid of AngularJS; man, now THAT’S a catchy name.

What In The World Is AngularJS?

AngularJS is a JavaScript library that allows you to implement the Model-view-controller pattern (in some sort of way) at a client-side level (dude, the browser). Why is this? Because you have two options in life:

  • Option A    You implement a +1000 lines JavaScript source file with a bunch of code that not only is in charge of handling manipulation of the HTML structure and creation of UI components, but also handles all of the data validation and display logic of it, all of this while your fellow teammates start hating the guts out of you.
  • Option B    You be a good developer, who cares about separation of concerns, and split all those tasks in several components where each is in charge of a single thing; those written in separate files for your code maintainability’s sake, while making a lot of friends in the process.

In the good old days, option A was “kind” of affordable (heavy quotations), since JavaScript was used for simple things like adding and removing elements from the HTML structure, changing colors and such. But when we talk about implementing a client application only using JavaScript, option A starts struggling. Mainly because we are not only moving HTML elements around, animating stuff and other user interface tasks; but also performing data validation, error handling and server communications in the client-side.

Of course, option B is the way to go. Since there is a ton of things going on in the browser, we need a way to create components that handle each task separately. This is known as the Separation of Concerns principle, or SOC; which states that your code has to be split in several parts, handling a single task each, orchestrated in order to achieve a common good. And this is where AngularJS shines. It allows you to:

  • Organize your client-side code in a Model-view-controller fashion, so you have separate components where each handles a different task in the logic stack: from user input to server data posting (Don’t worry, we’ll get on this later on.)
  • Live template processing and data-binding; more specifically: munch a template, bind it to specific data coming from the server or anywhere else and then produce a valid HTML piece that can be displayed in the browser.
  • Creation of re-usable user interface components.
  • Implementation of advanced patterns, like dependency injection; which is tied to…
  • Ability to implement unit tests for the JavaScript code.

Client-side Model-View-Whatever

We all know Model-View-Controller (MVC from now on) was conceived for a good reason: Roles and responsibilities matters. It was designed as a practical way to separate all of the front-end logic into three interconnected parts, so code having to do with how data is displayed is clearly separated from the code that validates, stores and retrieves that data. Also, it was thought with unit testing in mind. MVC Flow Now, MVC is commonly used server-side; think of ASP.NET MVC or Spring MVC, where you have a class representing the “controller”, which fetches data into “models” and then binds them to a template producing a “view” in the form of an HTML document, which is returned to the browser for display on the user screen. Remember, each time we talk about MVC, we are generally referring to the Presentation Layer of an application.

Now, why go crazy and MVC-fy my JavaScript code? Well, because what’s trendy right now are dynamic web interfaces where pretty much everything is asynchronous, little post-backs are done to the server unless really necessary and you have complex UI components like pop-ups, multi-level grids and others living on the screen (think of Facebook, for example). The only way to do this is delegate the browser (through JavaScript) with the user-interface composition, interaction between all of the components and lastly fetching and posting data back and forth from the server. You really, really NEED a way to achieve law and order so the client-side code does not become an uncontrollable mess.

OK, enough talk already. Let’s dive into how to implement a simple application using AngularJS.

Hello, Angular

Consider the classic “To-do List” example. We want a screen that displays a list of items to be completed; also we need to show a mini-form that allows us to enter and add new items to the list. Here is how it should look: To-do List UI So, in order to get this done, we need to complete some steps:

  • Create the HTML document which will be representing our view.
  • Include the AngularJS library in the HTML document so we can start creating controllers that will handle behavior of the user interface.
  • Create and include a JavaScript file where we are going to create our application object (wait for it) and define some controllers.
  • Add scope (almost there…) variables and functions that will be bound to the view through special AngularJS HTML attributes.

Basic View Markup

Let’s start this in a natural way: let’s create the user interface first. We will create a file called todolist.html and we will add the following HTML to it:
ANGJS SNIP1
Now, nothing fancy right there; we just included the AngularJS library at line 8 and another file at line 9, which we will create in a moment. However, just notice the structure of the document: We have an UL element which will represent our list of to-do items and then a couple input controls so we can add new items to the list. It does not have any information on it for now, but eventually it will… And it will be awesome.

Let’s leave this code as it is for now, let’s move to the app.js file which has all the fun going on.

Adding Logic: The Controller

Just by looking at the previous HTML document, you will realize that there are two things we need regarding to view state data:

  • An array to store the to-do items to be displayed in the UL element at line 13.
  • A function to add new items when I click the Add button at line 15.

Simple, right? Well, let’s create a new file called app.js and add the following code; I’ll explain it later:

ANGJS SNIP2

First things first: let’s take a look at line 1. Before we start building controllers that handle UI logic, we need to create what is known as an AngularJS application module; this is done by calling the angular.module() function and passing it the module name, which returns the created module. This object will later be used as a container where you will store all of the controllers belonging to this particular JS App.

The variable angular is available after we included the AngularJS library in our HTML document at line 8.

After we create the application object, we can start creating controllers; being done in line 3 through the controller() function, which is now callable from the application module we created in line 1. This function takes two arguments: the name of the controller and a callback function that will be responsible of initializing the controller and which will be called each time a controller is instantiated by AngularJS. AngularJS also passes a special variable to that function called $scope; everything that is added to the $scope variable during controller initialization, will be accessible to the view for data binding; better said: it represents what the view can see.

The rest of the lines are quite self-explanatory:

  • Lines 7 to 11 adds a pre-initialized array of to-do items to the scope, that will be used as storage for new items. It represents the items that will be displayed in the empty UL element we have right now.
  • Line 13 declares a variable that will hold the description of new items to be added after the Add button is clicked.
  • Lines 17 to 21 define a function that will add new items to the to-do items array; this should be called each time the Add button is clicked.

Binding The View

Now that we have AngularJS, the application module and the to-do list controller, we are ready to start binding HTML elements in the view to the scope. But before that, we need to change our <html> tag a little and add some special AngularJS attributes:

ANGJS SNIP3

Notice the ng-app attribute we added to the <html> tag; this is your first contact with one of the several directives that are part of the AngularJS data binding framework.

Directives are simply HTML element markers that are to be processed by the data binding engine. What does ng-app do? Well, it tells AngularJS which application module it should use for this HTML document; you might notice we specified ToDoListApp, which is the one we created in out app.js file at line 1.

After we associate our HTML document with the ToDoListApp, second step is to specify a controller for our view; this is done through the ng-controller directive. The ng-controller directive assigns a controller to a section of the HTML document; in other words, this is how we tell Angular where a view starts and when it ends.

Anyways, modify the <body> tag so it looks like this:

SNIP4

Same with the ng-app directive, the previous code tells AngularJS that everything inside the <body> tag will be governed by the ToDoListController, which we created in our app.js file at line 3.

Now we are ready to start binding elements to members added to the $scope variable during the ToDoListController controller initialization.

The ng-repeat Directive

Let’s start with the empty UL list element. In this case we want to create a new child LI element per item that is contained in the to-do items array. Let’s use the ng-repeat directive for this matter; add the following code inside the UL tags:

ANGJS SNIP5

OK, hold on tight. The ng-repeat directive will repeat an element per item in an array used as data source; the quoted value represents the iterator expression, which defines the array to be iterated and an alias used to refer the current item being iterated.

In this case, we specified that it should repeat the LI element for all of the items in the items array defined in the $scope variable from line 7 through 11 in the app.js file.

Lastly, inside the LI tags we define an Angular template, which is an expression enclosed in double curly braces that will be compiled dynamically during run-time. In this case, the template is extracting a member named desc from each item and is going to display its value inside the LI tags being repeated.

Go ahead, save your files and open todolist.html in your preferred browser; you will see how the list gets filled. Awesome stuff, huh?

The ng-model Directive

Next in our list is the ng-model directive, which is used to bind the value of an input element, a text box, text area, option list, etc.; to a variable of the $scope. But before I give you more talk, change the input element at line 15:

ANGJS SNIP6

Binding the value of an element means that each time the value of the input element changes, the variable specified in the ng-model directive will change with that value.

AngularJS enables two-way binding by default, meaning that if the value of the variable the input element is bound to changes, the change will be reflected in the input element on screen. This is the true magic of AngularJS: You can change the value of elements displayed on screen just by modifying values of the $scope variable; no need of selectors, no need to access the DOM from JavaScript, no need of extra code.

In this case, the input element has been bound to the newItemDescription variable of the $scope, defined at line 13 of the app.js file. Each time the value of the input element changes, the variable at the scope will be updated and viceversa.

The ng-click Directive

What if I want to do something when I click that? For that, AngularJS provides a bunch of event handler directives. These directives can be used to invoke functions defined on the $scope each time the user performs an action over an element.

The only one we are going to use for this example is the ng-click, which handles the user click on a button or input element; the expression it takes is basically the code to be executed on each click. In our case, we will modify the button element at line 15 and add the following directive:

ANGJS SNIP7

If you look closely, we are telling AngularJS to call the addItem function defined in the $scope. If you see the code of that function from line 17 to 21, you will see that it adds a new item to the to-do list array, based on the value of the newItemDescription variable.

If you save your files and open todolist.html, you will see how the list is automatically updated each time you enter a new description in the text box and click on Add.

Your HTML document is dynamic and alive. How cool is that?

What Kind Of Sorcery Is This!?

OK, I must tell you that all of this does not happen through magic. AngularJS is what’s called an unobtrusive library; which means that everything happens automatically as soon as the library finishes loading.

At the very beginning, when the HTML document finished loading, AngularJS crawls through HTML document structure looking for ng-app directives which tells it that something has to be done there. After all of the directives have been found, the marked elements are processed separately: elements are bound to controllers and templates are compiled.

The $scope variable lifetime is automatically handled by AngularJS, each time something happens on-screen, it is notified and performs anything that has to be done to ensure the controller and view are synced; from updating values in the $scope bound to a particular element to refreshing an element or template. This is done through the implementation of some sort of the observable pattern that allows AngularJS to react to changes on elements and the $scope itself.

Conclusion

Woah! That was a bunch of stuff to digest. Hopefully, you will make sense out of it with some practice. Of course those three directives are not everything that there is on AngularJS; for a complete list on all of the possible directives you can use out-of-the-box, take a look here.

Have in mind that you can also extend the library with custom directives, but that is an advanced topic we might cover in a future article.

AngularJS is not everything there is about JS Apps, this was a very basic introduction and I want you to have knowledge you can use in real life, so we will be learning how to build more complex JS Apps in my next article. Topics to be covered will be:

  • Creating custom Angular directives.
  • Complex user interfaces (windows, redirection and data validation.)
  • RequireJS for on-demand asynchronous JavaScript files loading.

Hope that sounds exciting enough for you. Stay tuned! 😀

Source Code

Further Reading

6 Days with Windows Phone

Disclaimer: What follows is my personal opinion, it does not reflect Informatech’s position necessarily. Though I’ve tried to be as unbiased as possible, it will undoubtedly reflect my views.

A friend upgrades to a Lumia 920 and a Lumia 900 is left orphaned.

With a Galaxy Nexus experiment going on since Oct 2012, and waiting for Apple’s comeback iOS 7 (plus whatever they introduce later this year), I dive in for a week to see how the Windows Phone 7.8 experience stacks up.

Clarifications

I hail from a background of Apple devices, at least for a couple of years now (I had Nokia smartphones before). I’ve been exploring Android, if anything because as a developer it’s unforgivable not to have any experience in it, but customizability is not something that drives my purchases.

Beyond specific OS choices, I believe in finished, polished products. I dislike having to hack or otherwise mod my devices. Yep, that includes spending hours tweaking and configuring.

I like my stuff to just work, with minimal fuss. Things can be technologically interesting, but in a device I want a product. That said, let’s delve in.

The Experience

2013-06-10 10.54.522013-06-10 10.55.03

What do I usually do in a smartphone (that will thus dictate the experience on Windows Phone)? Pretty much WhatsApp, Facebook, push Gmail, push Google Contacts, camera, and Dropbox auto photo uploads. Yes, other things matter, but that’s what realistically I use most of the time, and will be the scope of this review.

So let’s not waste too much time discussing setup (which is generally polished), suffice it to say that of the above:

  • WhatsApp and Facebook were installed from the Marketplace.
  • Camera is good, but there is no official Dropbox support. I routed around this by enabling SkyDrive auto uploads, so no biggie.
  • When setting up the Google account, we hit our first snag. Because Google discontinued ActiveSync, the only straightforward choice is IMAP setup just for email, no calendar or contacts. Fortunately you can add Gmail as an Exchange server manually through the end of July. This worked OK, but the contact import was kinda crappy (ie. contacts with multiple numbers, just had the first imported).

Once everything was working, it took me about a day to get used to the concept of Live Tiles. That is the driver of the Windows Phone UI, where you’ll launch apps, get notifications, and see periodic content changes of relevant content. The idea is novel and elegantly implemented, and after months on Android, it made me feel that special care had been taken in the consistency and polish of the interface. Both were very much welcome.

In full day-to-day usage, the UI shines, though where I felt the most joy was in the touch keyboard. It is absolutely a pleasure to use (no gestures or swipes, straight taps), and by far it’s the best of any smartphone that I’ve used.

The camera was another pleasant surprise. The capture and photo browser were excellent, behold:

WP_000006

The multitasking also requires a bit of getting used to, as a long press of the back key will allow you to get an open app list, however it will not let you kill any. You have to jump in, and continually press back until you exit.

To finish off the “stock” functionality, the People hub was generally useful (even though the Google contacts were indeed not wholly sync’d). It gave quick access to recent contacts, and integrated well with social networks.

Even though Facebook is integrated in, the way to properly see your Newsfeed is through the standalone app. Which sadly is not developed by FB, and is quite honestly sub par to similar offerings on iOS and Android.

WhatsApp was a similar story, the implementation is not up to par with the other platforms, and more annoyingly it activated the music controls and gobbled battery. As a workaround, you have to download a separate app that kills the music controls, and run it periodically. The app also seemed to implode under heavily used group chats.

Even with the mediocrity of third-party apps, I can honestly say the OS is pleasant to use, and the tiles are colorful and attractive. So rounding out:

Pros

  • Superb interface, extremely polished.
  • Quite simply the best touch keyboard I’ve ever used, on any smartphone.
  • Integration between social networks and contacts is almost seamless.
  • Excellent camera.
  • Lumia hardware is very capable and attractive.
  • Integration with Microsoft services is predictably good.

Cons

  • Synchronization with Google services is poor (especially now that ActiveSync was retired).
  • App selection and most importantly, quality, is low, low, low. Years behind iOS and Android.
  • WhatsApp drains the battery, and requires “Stop the Music” to kill it every once in a while.
  • Multitasking does not allow you close the application from the app list (WP 7.8?)
  • Lack of a centralized notification area is confusing.

Conclusion

If you’re a Hotmail user, and you live your life in Exchange and Microsoft Office, Windows Phone is a natural fit. The Lumia hardware is capable and attractive, the UI is very polished, and if you can live with the poor app selection and quality, you’ll enjoy it.

However if you use Google services, and have gotten used to the abundance of other app stores, the UI may not compensate the tradeoffs for functionality you would have to give up. In the future this may change, but at present it’s too much to take.

BackCountry Hackathon 2012: Informatech Wins API Category

A little late to be sure but no less significant, given that I wanted to write about this at the same time.

On September 22-23, Adriana Jara, Johan Rodríguez and myself participated in the first-ever BackCountry Hackathon 2012. Here we are at the beginning of the event.

What we did

Adriana had the fantastic idea of using the competition APIs to build a comment and review search engine, and thus Community Mining was born.

The APIs gave us data in JSON, so using a proxy webserver we queried the data and in JavaScript analyzed, graphed, and displayed the results.

Our tech stack included:

  • Tomcat 7
  • jQuery & jQuery UI
  • YUI Grids
  • Raphaël Vector Library
  • Lots of JavaScript code

We completed the main feature set about an hour before the deadline, and our app proudly ran in desktop, smartphone and tablet browsers.

What does it look like? Well here you go:

What was learned

Speaking from a strictly personal perspective, I have to say that after the rush of more than 36 hours of work, and the pride of feeling “I still got it”, wore off. The main takeaway was: you have to choose your team well.

Your teammates must be talented. Sometimes, less people is actually better, as it allows easier coordination (that was the case here). And very importantly you have to trust the people next to you not to blow up when the stress is high. Adriana and Johan certainly fit the bill.

All in all good fun.

– Michael Holst

New Hackathon Challenge: Desarrollando América 2012

Well, we have signed up to carry the Informatech banner once again at a hackathon.

This time it will be at the Latin America-wide Desarrollando América Latina 2012.

Participants

From Informatech we will have: Adriana JaraJohan Rodríguez, André Curione and myself.

Joining us will be Eliécer Leitón from BackCountry, and our social and analysis liaison Cecilia Salazar.

We’ll be developing a native Android application and reporting Dec. 1-2 from the hackathon.

– Michael Holst

Linux on Palm -really?

Do you remember that nice small gadget called the Palm Pilot that everybody wanted desperately and made you look so cool just a few bunch of years ago? I bet you even have one in your drawer but are just too embarrassed to take it out and show it alongside your friend’s shinny new smartphones.

But I’m diverting. Have you considered the fact that those once cool little machines may be capable of running something else than the now dreadful PalmOS? Why on earth would you want Linux on that thing anyway? Well, why not?

As it turned out to be, I found that from a learning perspective, trying to fit a standard Linux Kernel into a Palm is just what the Geek Doctor prescribed, not to mention that by doing it you do are entitled to show off your Palm and brag about it with your smartphone friends, how about that for a spin?

So I figured out that having nothing better to do on a Saturday night I might just as well write about my little Linux and Palm – Frankenstein project. What do you know, I can even put a few words the Android topic as well if it suits.

What do you need to put Linux in your Palm?

Fortunately, it has been done before by a couple of ex PalmOS developers in search of redemption from working so many years with such a hideous thing (PalmOS, that is). So you may want to check a site called Hack&Dev. There’s a nice working version of it for the Palm TX, but of course if we stop there that wouldn’t be fun and we will spoil Christmas too soon.

So where to start? Well we need to follow some sort of steps like the following:

  1. Get a Palm. Seriously. Using Palm simulators is cheating on yourself. I have a Palm TX so I got started with that, not that I need another one though.
  2. Decide how you want to boot the Linux image once you have it. Basically, PCs have Master Boot Records, and embedded devices have Bootloaders. Palms come with a ROM image with everything in it, including a Bootloader. So if you want to override what’s in the Palm, you’ll need a way to rewrite the ROM and of course you need to backup your current one if you ever want to get your old PalmOS back (say when you bragged enough). There’s a nice alternative though, most of the latest Palm devices (latest I mean from 2003 up) have external memory card support (SD, Memory Stick, etc). I found we can use a PalmOS program that will act as a Bootloader using an image that could be stored in your SD card. Pretty convenient huh? Now we can keep the PalmOS ROM and test out our awesome Linux images using only our external card. If we screw up, just reboot and Palm OS will rise form the dead again. The best PalmOS Bootloader program I’ve seen is called Cocoboot, so google it.
  3. Now that we have a safe way to test stuff, we need to build the stuff. This is where I guess 90% of the readers will close the webpage, not because you can’t do it, but because it is way too tedious. Here’s where the research efforts are spent. You’ll need to:
  4. Learn how the Linux system boots. There are lots of internet articles on this topic, but in short, learn that the Bootloader loads the Kernel, the Kernel mounts the root filesystem, the Kernel then calls the init() function to perform (amongst other things) hardware specific setup, then the devices mount, Kernel space ends and User space takes over to initialize any juicy stuff you want to put in there like GUI systems, services, etc.
  5. Learn where to get the code you need. Believe or not, there are specific Embedded Linux Distributions for a lot of popular hardware architectures besides the x86 family. So the job is pretty much done in terms of drivers, Memory Management and Core/Cache logic, etc. Specifically, there’s one distribution targeted at the ARM processor used by our beloved Palms. So the basic chipset is already coded for Linux when it comes to hardware. The tough part would be to plug in specific drivers for WiFi and other stuff that are not contemplated by the core distribution archives.
  6. Setup a Tool-Chain. A Tool-chain is the whole set of tools (libraries, compilers, linkers, assemblers, debuggers, profilers and even development environments) that enables you to start with your Linux code and eventually get your binary images that run in the target device (the Palm in our case). Keep in mind that you will need to compile/link/package binary code that doesn’t run in the machine that you compile it (unless you dare to install the Tool-Chain in the Palm itself, in which case please write a Blog about it). I recommend using Linux as the host machine where you will setup your Tool-Chain, being my personal taste Ubuntu, though Fedora works too (how cool is that, Linux to build Linux …). Unless you are a real Linux evangelist, try using the GUI/Desktop versions of Linux and avoid the command line as much as you can. You will have to face it eventually so why make yourself miserable form the beginning. Also, I have good news for you, Eclipse has already developed a nice way to work with Tool-chains and it should be very easy for almost everyone to setup one using Eclipse.
  7. Dig in for drivers. You eventually will want to use your Palm’s Bluetooth, audio, etc. Most of them require drivers that are available already over the internet (except WiFi, darn!!). So search for those and hook them up to your project if needed. They will be regular Lunix MODs so it is not hard to plug them in if they are already compiled for the ARM architecture. I know, I know, this is the toughest part, so you migh just as well skip it. After all, showing off a command line driven Linux in your Palm is also going to be cool. But at least, get the driver for a virtual keyboard, unless your Palm has a physical one already, you will not get pass by the login screen (no it will not be cool to stop here, I can code a fake login screen in PalmOS, so no cheating).
  8. Compile/Link and package the Kernel. This step is as simple as that. You will get one nice image file. The good thing about the Cocoboot Bootloader, is that it knows how to read compressed image files so you may also create a compressed binary Kernel image file, though it doesn’t really matter from a non Geek perspective.
  9. Package the filesystems with libraries and tools. Once you package the Kernel, you get to decide if you will include additional libraries and stuff. Well all this extra stuff needs an extra filesystem (virtual hard drive if you may). So you just package the compiled versions of your libraries, shells, games, etc, in this image that the Kernel should be able to mount as an additional filesystem within the already mounted root filesystem, in the good’ol Linux way.
  10. Test it. Now it’s the time to copy your stuff into your SD card and test it (if you didn’t wipe the Palm’s ROM, in which case you’ll need to flash the ROM with your Bootloader, Kernel and additional filesystems, probably as a single flashimage as most manufacturer’s do.). You will probably hang the Palm the first time (or 100 times). Just be sure to include all the nice Linux logs stdout to the terminal screen so that you may see what needs to be fixed. In my case the drivers I got and all the code was so nicely developed in the ARM Embedded distribution that the only place I got stuck was at the login screen (remember the virtual keyboard I talked about?). Later I used a nice Linux library from the OPI distribution so my Linux got graphical!.

Are you an expert already? Well I guess this is not the 48 hour development endeavor one of my colleagues was blogging about the other day (probably more like a 48 day thing), but I hope at least I gave you the very high level picture of what it takes to totally waste your valuable free time in the name of pure techie style -sugar highs.

Next step: Android (but that my friends, is another story …)

If you are at least a bit intrigued after reading this blog (assuming you really did read it), my mission is accomplished an I can happily say my weekend had a purpose.

May the fork() be with you.