Model-View-Controller (MVC) with JavaScript

I like JavaScript because it is one of the most flexible languages in the world. It supports wide range of the programming styles and techniques, but such flexibility comes with danger - it is very easy for the JavaScript project to become a messy heap if the practices or design patterns are applied in a wrong way or inconsistently.

My goal for this article is to demonstrate how to apply the Model-View- Controller pattern while developing a simple JavaScript component. The component is a kind of the HTML ListBox (“select” HTML tag) control with an editable list of items: the user should be able to select and remove items and add new items into the list. The component will consist of three classes that corresponds to the parts of the Model-View-Controller design pattern.

I hope, this article will be a good reading for you, but it would be much better if you consider to run the examples and adapt them to you needs. I believe you have everything to create and run JavaScript programs: brains, hands, text editor, and an Internet Browser (Google Chrome, for example).

The Model-View-Controller pattern requires some description here. As you may know, the name of the pattern is based on the names of its main parts: Model, which stores an application data model; View, which renders Model for an appropriate representation; and Controller, which updates Model. Wikipedia defines typical components of the Model-View-Controller architecture as follows:

  • Model - The domain-specific representation of the information on which the application operates. The model is another name for the domain layer. Domain logic adds meaning to raw data (e.g., calculating if today is the user’s birthday, or the totals, taxes and shipping charges for shopping cart items).
  • View - Renders the model into a form suitable for interaction, typically a user interface element. MVC is often seen in web applications, where the view is the HTML page and the code which gathers dynamic data for the page.
  • Controller - Processes and responds to events, typically user actions, and invokes changes on the model and perhaps the view.

The data of the component is just a list of items, in which one particular item can be selected and deleted. So, the model of the component is very simple - it consists of an array and a selected item index; and here it is:

 * The Model. Model stores items and notifies
 * observers about changes.
function ListModel(items) {
    this._items = items;
    this._selectedIndex = -1;

    this.itemAdded = new Event(this);
    this.itemRemoved = new Event(this);
    this.selectedIndexChanged = new Event(this);

ListModel.prototype = {
    getItems : function () {
        return [].concat(this._items);

    addItem : function (item) {
        this.itemAdded.notify({ item : item });

    removeItemAt : function (index) {
        var item;

        item = this._items[index];
        this._items.splice(index, 1);
        this.itemRemoved.notify({ item : item });
        if (index === this._selectedIndex) {

    getSelectedIndex : function () {
        return this._selectedIndex;

    setSelectedIndex : function (index) {
        var previousIndex;

        previousIndex = this._selectedIndex;
        this._selectedIndex = index;
        this.selectedIndexChanged.notify({ previous : previousIndex });

Event is a simple class for implementing the Observer pattern:

function Event(sender) {
    this._sender = sender;
    this._listeners = [];

Event.prototype = {
    attach : function (listener) {
    notify : function (args) {
        var index;

        for (index = 0; index < this._listeners.length; index += 1) {
            this._listeners[index](this._sender, args);

The View class requires defining controls for interacting with. There are numerous alternatives of interface for the task, but I prefer a most simple one. I want my items to be in a Listbox control and two buttons below it: “plus” button for adding items and “minus” for removing selected item. The support for selecting an item is provided by Listbox’s native functionality. A View class is tightly bound with a Controller class, which “… handles the input event from the user interface, often via a registered handler or callback” (from

Here are the View and Controller classes:

 * The View. View presents the model and provides
 * the UI events. The controller is attached to these
 * events to handle the user interraction.
function ListView(model, elements) {
    this._model = model;
    this._elements = elements;

    this.listModified = new Event(this);
    this.addButtonClicked = new Event(this);
    this.delButtonClicked = new Event(this);

    var _this = this;

    // attach model listeners
    this._model.itemAdded.attach(function () {
    this._model.itemRemoved.attach(function () {

    // attach listeners to HTML controls
    this._elements.list.change(function (e) {
        _this.listModified.notify({ index : });
    }); () {
    }); () {

ListView.prototype = {
    show : function () {

    rebuildList : function () {
        var list, items, key;

        list = this._elements.list;

        items = this._model.getItems();
        for (key in items) {
            if (items.hasOwnProperty(key)) {
                list.append($('<option>' + items[key] + '</option>'));

 * The Controller. Controller responds to user actions and
 * invokes changes on the model.
function ListController(model, view) {
    this._model = model;
    this._view = view;

    var _this = this;

    this._view.listModified.attach(function (sender, args) {

    this._view.addButtonClicked.attach(function () {

    this._view.delButtonClicked.attach(function () {

ListController.prototype = {
    addItem : function () {
        var item = window.prompt('Add item:', '');
        if (item) {

    delItem : function () {
        var index;

        index = this._model.getSelectedIndex();
        if (index !== -1) {

    updateSelected : function (index) {

And of course, the Model, View, and Controller classes should be instantiated. The sample, which you can below, uses the following code to instantiate and configure the classes:

$(function () {
    var model = new ListModel(['PHP', 'JavaScript']),
        view = new ListView(model, {
            'list' : $('#list'), 
            'addButton' : $('#plusBtn'), 
            'delButton' : $('#minusBtn')
        controller = new ListController(model, view);;
<select id="list" size="10"></select>
<button id="plusBtn">  +  </button>
<button id="minusBtn">  -  </button>


There is also the JSFiddle:

And the UML diagram for those who are familiar with it: