Object-Oriented Javascript (ES5 & ES6)


Object-Oriented Javascript

JavaScript is a powerful dynamic programming language that most of us developing web applications have used to implement client side functionality including asynchronous data transfer, browser event handling, dynamic HTML content and more. It's always been a bit "funny" so to speak because of some of it's quirks, ie. know when to use your === vs ==, be wary of the effects of variable and function hoisting, remember that scope is a little different then in languages like Java and C#, and more. JavaScript became an object-oriented language by way of the prototype mechanism as of the ECMAscript 5 standard (what we have now), however version 6 of the standard and JavaScript 2.0 is on the way in March of 2015 (latest specification date at the time of this article) and will become much more like some of the other object-oriented languages in common use such as C++, C# and Java.
Let's take a quick look at what we have now that enables object-oriented development and then what's on the way next year.

JavaScript: OO with ES5

The following is a small piece of a fictional charting library as an example, here's a demonstration of a base Chart class and a couple specialized classes that extend it's functionality.

Namespace

First things first, let's define a namespace for this library to avoid class (function) name collision called chartco:
var chartco = chartco || {};

Base Class - Chart

Now we'll define a base class that provides common functionality for charts of all types, including a function to set the background color and another to move it to a particular x,y coordinate on a page:
chartco.Chart = function() {
};

chartco.Chart.prototype.setBackgroundColor = function(r, g, b){
    console.debug("Setting chart background color to: r:" + r + ", g:" + g + ", b:", + b);
    // ...
};

chartco.Chart.prototype.moveTo = function(x, y){
    console.debug("Moving chart to position x:" + x + ",y:" + y);
    // ...
};

Child Class 1 - Bar Chart

First create a constructor that accepts the applicable parameters and sets the object properties, a title, width and height for the BarChart:
chartco.BarChart = function(title, width, height) {
this.title = title;
this.width = width;
this.height = height;
};
Note we have to specify that the prototype for the BarChart is the Chart base type, but the constructor should be that of the BarChart so we can identify it as such at runtime
chartco.BarChart.prototype = new chartco.Chart();
chartco.BarChart.constructor = chartco.BarChart;

Child Class 2 - Pie Chart

We'll repeat the same procedure for creating a PieChart class:
chartco.PieChart = function(title, radius) {
this.title = title;
this.radius = radius;
};
chartco.PieChart.prototype = new chartco.Chart(); chartco.PieChart.constructor = chartco.PieChart;

Testing it Out

Now we'll create a couple instances of the chart object and utilize the common base class functionality:
var ageGroupChart = new chartco.BarChart("Age Group", 300, 150);
var incomeChart = new chartco.PieChart("Spending Allocation", 200);
ageGroupChart.setBackgroundColor(255, 255, 255);
incomeChart.setBackgroundColor(0, 43, 54);
ageGroupChart.moveTo(200, 500);
incomeChart.moveTo(150, 300);

The Output

Setting chart background color to: r:255, g:255, b: 255
Setting chart background color to: r:0, g:43, b: 54
Moving chart to position x:200,y:500
Moving chart to position x:150,y:300
These are some of the basics, you can also create the equivalents of static members, private member variables, making "super" calls to the base class functionality and more. It's not quite the style of OO a developer who's worked with C#/C++/Java may expect but many of the language features are there to create such a system for a client site API or SPA.

JavaScript 2: OO with ES6

The ECMAScript 6 standard is due to be finished in March of 2015 as of the writing of this blog article, implementations of JavaScript 2 using the standard are already underway. It introduces concepts such as block level scoping with the let and const keywords, class definition using the class keyword, more traditional inheritance using extends, better for loop iteration, new collections, modules to enable a clean mechanism for using other JavaScript libraries with your own and so on.

Though the specification is not yet completed many browsers have partial implementations that you can play around with, as well there are several language transposition tools like Google's Tracuer and Microsoft's TypeScript that you can use to write code using the new language features (as closely as they can approximate them before the standard is finished) and generate compatible ES5 code that you can use today.
class Chart {
    constructor(title) {
        this[title] = title;                    
    }    

    moveTo(x, y) {
        this[x] = y;
        this[y] = y;
    }

    setBackgroundColor(r, g, b) {
        // ... 
    }
}
Now we can extend and create the BarChart child class with the new inheritance syntax:
class BarChart extends Chart {
  constructor(title){
    super(title) 
  }
}
The language syntax is a bit more straight forward and succinct and should really empower developers to create client side functionality and reusable APIs in modules that "feel" more like a traditionally object oriented language. I think this is big step forward for the language and will aid in creating cleaner, more organized applications that are coded largely in JavaScript which is becoming the norm in today's web application oriented world.
For more information on the specification and tools available to try out (or use) the new syntax now check out the following resources:
ECMAScript 6 Draft Specification
Quick ES6 Spec Summary
ECMAScript 6 Browser Compatibility Table
traceur-compiler
MDN

Labels: , , , ,