Back again fellow coders, to take a look at another framework in the web universe: AngularJS. AngularJS is a Javascript framework used to build web applications. In my previous post we learned about the front-end framework Bootstrap, which helps you pull all the HTML/Javascript/CSS pieces together to get a polished website in a short time. AngularJS has a lot of client-side coding involved, but is more about taking that web site and giving it some pizazz if you will, to make it into a web app that interacts with things like data on a web server. This is a simplistic description of these two frameworks but helps distinguish their core differences. In fact you often may see them used together. When I described Bootstrap I used a Lego analogy, and for AngularJS, I will continue along the “building” path to find a new analogy involving…Doozers!
The Goal
To learn about the AngularJS framework and put it into practice.
The Plan
Training is a must, so to pluralsite I did go. I completed a great beginner course called AngularJS: Get Started by Scott Allen. I would need to get a handle on how AngularJS fits into a website (make that a web app) and add a feature using it to my Daisy Plates Bootstrap Website. I would also reference trusty sites w3schools, stackoverflow and MDN among others listed throughout this article.
The Journey
First, what IS AngularJS and what does it have to do with Doozers?
Back in the 80s there was a great television show called Fraggle Rock, about colorful Muppet creatures who lived underground, ate radishes and basically enjoyed life. Also in this world were these little green characters called Doozers. Doozers loved to work all day building structures out of sticks made from radish dust. Then the Fraggles would come along and eat them, the structures that is! Doozers didn’t mind, it meant they could build more structures, which they loved doing!
AngularJS follows the MVC structure, or Model-View-Controller. I think one way you can understand MVC in the world of AngularJS is to reframe it in the world of Doozers. Let’s give this a try.
Start with a construction Doozer in her hard hat. We’ll call her the Controller. Her job is to first carry a radish stick from a big pile over to the building site. This big pile of radish sticks is the Model. Once at the building site, she places the radish stick in the correct position in the contstruction. After doing this for a while throughout the day, those radish sticks become a beautiful bridge, which is the View.
Lost yet? Basically, the idea behind MVC is that it separates out the data, perhaps in a file on a web server (Model) from the code that manipulates that data (Controller) from the HTML page that displays the data (View). This separation helps us keep our web apps more organized, allowing each part to do its job best, just like the Doozers do when they follow their building process. If the Doozer in our story arrived at the building site to find another Doozer placing doozer sticks on the bridge from underneath it for example, that could be confusing and not as efficient (and possibly not safe for that Doozer!). Or if Doozer brought her own homemade sticks with her to work and tried to assemble the bridge with them, that could lead to some confusion, or maybe disaster, too!
There are a few more concepts in the AngularJS MVC structure that we can include in our Doozer analogy. First of all, perhaps Doozer needs to understand the proper sticks to take from the pile, as there are different sizes. She may call on another Doozer (service) whose job is to understand these sorts of things. Then when Doozer is at the building site, she may not be exactly sure where to put the stick she’s carrying. Enter another Doozer wearing a visor (directive) whose job it is to communicate to our first Doozer where to place the stick. He does this via a headset (binding expression) that connects to our first Doozer. Then our Doozer uses her forklift (scope) to place that stick, without physically lifting the stick herself. See how the Model never touches the View directly, just through our Controller with the help of services, directives, binding expessions and scope. Getting the job done efficiently, just like the Doozers!
Oh, we almost forgot the most important part! A fraggle comes along and starts munching on the bridge the day it is finished! Just like a web user will enjoy the web app that AngularJS built when it launches.
Break it down…
Now that we understand the world of AngularJS (and Doozers!) a little better, on to the actual coding part!
I decided to build some functionality into the “The Daisy Special” popup. When a patron enters the Daisy Plates store, they will be able to select the button on the site via their phone or tablet and a random prize will display for them. We won’t worry now about those finer details like ensuring only one prize per person per day, only till supplies last etc. which could involve determining location to know we’re in the store, keeping track of stock in the model, etc. etc. Perhaps a future implementation could display a code to scan instead as well. For now, we’ll assume its a special day at Daisy Plates, and anyone who shows their random prize when they make a purchase at the counter gets the prize!
- A clean starting point: I made a copy of my Daisy Plates Bootstrap site and then downloaded the AngularJS Javascript file. I included this in my index.html page where the Daisy Special popup resides, similar to how I included the boostrap Javascript file.
- One step at a time: From that point on, it was a series of small steps:
- set up my model of data, based on the current prizes I had hard-coded in the faked Daisy Special popup. I really wanted to use a service in my little code sample, so with a little trial and error, I found I could use the $http service to access this data from a JSON file that sits with my other Javascripts called daily_special_data.js. On another level, this file could sit on any web server that would be set up to let me access that data.
- set up the view in index.html. This meant changing my onscreen wording some to simplify things and including all the little AngularJS bits to connect the view to the controller.
- apply the ng-app directive with the name of my AngularJS module (best to keep your code separated into modules, more separating for efficiency here) that will contain my controller, as well as ng-controller directive with the name of my controller that will be in the module to the Daisy Special div as attributes. They say “hi there, I’m going to use some AngularJS here to do some neat stuff.”
- add a couple of binding directives in the form of a word surrounded by {{ }} right in my HTML where I want to show the Daisy Special prize code and details.
- create my AngularJS module and controller, and register that controller in the module. This will be done in a separate Javascript file that I will call daisy_special.js and will include in index.html. The controller will pass in the scope, as $scope, i.e. the scope of our view that is evoking all this AngularJS goodness, and then the $http service that we want to use. Wrap this all in an IIFE which avoids creating our variables in the global namespace. Again more separating for efficiency, as global variables can cause hassle by being overwritten easily for example.
- lastly, popuplate my controller with some code to do the action. Evoke the $http service, which asks for what it wants from the controller, which in our case, is the data from our model, and it gets back a promise — toss in a new term for you! — to deliver that value to the service in the future. It delivers this value when it is ready via two event methods — another new term! — one that actually retrieves the data called onDaisySpecialComplete, and the other that handles if we have an error called onError. The successful event will have a little extra Javascript to create a random number. It then uses that number to select the prize from the data returned and bind it back in our HTML page via the scope.
Arrived at our destination!
It’s that simple, now every time the user of Daisy’s site clicks the Daisy Special button to show this popup, this AngularJS kicks into action and shows a random prize!
Here’s something cool!
This is my AngularJS module.
(function() { // create module var app = angular.module("getDaisySpecial", []); // controller var MainController = function($scope, $http) { // event methods var onDaisySpecialComplete = function (response) { var dataObj = response.data; var randomNum = parseInt(Math.random() * (dataObj.length - 0) + 0); // directive that writes to the model through the scope $scope.myprizecode = "Claim Code: " + dataObj[randomNum].id; $scope.myprize = dataObj[randomNum].special_deal; }; var onError = function (response) { // directive that writes to the model through the scope $scope.myprizecode = "Please try again later."; }; // service $http.get("js/daisy_special_data.js") .then(onDaisySpecialComplete, onError); }; // register controller in module app.controller("MainController", MainController); }());
Challenges…and how I overcame them!
Although I’ve been programming in Javascript for many a year, and had delved into MVC before with Java, it took a little time to get the various AngularJS concepts sorted. That’s the way with many web technologies though, the heart of things is still the same — HTML, Javascript, CSS — it’s just someone has come up with a new way to talk about it, to make it easier to connect the dots and to make those connected dots into bright constellations. The further I got into the course, and with more review, things started to connect. We just have to be patient with ourselves, mull things over, and eventually the concepts, sometimes in the form of Muppets, will come to us.
What was the most fun?
Building more understanding of what kinds of frameworks are out there. I love being able to hear a technology term and go ah, I know where that fits in the puzzle. It was fun adding a little interactivity to the Daisy Plates site as well. The first time the lightbulb went off for me to pursue coding was back in school, in the days of Basic programming, was when I was able to make a small function work, and then keep adding on to it. So sometimes the smallest functionality wins can brighten your day. I also got a new respect for this language I’ve been working with for a long time.
The Result
Here is a link to the latest Daisy Plates site, click on “The Daily Special” to see the AngularJS in action. Please check out the index.html, js/daisy_special.js and js/daisy_special_data.js to make the MVC connections.
Daisy Plates Bootstrap AngularJS Website
My final thought on AngularJS is that it is the starting point of something great for me in my web coding experience. A language I was most comfortable with, in an MVC environment, gets me excited to venture into similar technologies and beyond. Keep building your own coding technology puzzle too and until next time!