Event Binding in Angular 2

Event Binding in Angular 2

No TL;DR Required 🙂

In my previous post I mentioned some of the many differences in Angular 2 from what we have grown used to in Angular 1.x. We covered property binding and how Angular is now binding directly to the DOM Object’s properties, and as a result of this we have been able to get rid of dozens of directives that come out of the box with Angular 1.x.

Some examples of directives we gave were ngShow, ngHref, etc. These old attribute directives were examples of one way and two way binding in Angular 1.x. In Angular 1.x we also have method binding. For this post we will focus on ngClick. In Angular 1.x ngClick is used to associate a function with an event on a DOM element.

Event Binding in Angular 2

Event Binding in Angular 2 is our replacement to this method binding via attribute directives in Angular 1.x.

As mentioned in the previous post the DOM API offers us access to several things. One of those things are events. Some example of DOM API events are click, focus, and blur.

Syntax

So Angular 2 has given us some syntax to use to bind to the DOM API Events.

1
2
3
4
5
//old
<div ng-click="myAction()"></div>
//new
<div (click)="myAction()"></div>
<div on-click="myAction()"></div>

So rather than the ngClick directive of Angular 1.x you can use Event Binding in Angular 2 to bond directly to the DOM API Event.

Event Binding in Angular 2 can still be done in a variety of ways. You can use the parentheses syntax, (click), to bind to an event or use the on- preface to bind to an event in a way that you would be more used to in Angular 1.x

Keep in mind that Angular 2 is completely built on components, below is an example of Event Binding in Angular 2 in ES5, TypeScript, and ES6.

ES5 HTML

1
2
3
4
5
6
7
8
9
10
<!DOCTYPE html>
<html>
<head>
  <script src="https://code.angularjs.org/2.0.0-alpha.22/angular2.sfx.dev.js"></script>
  <script src="app.js"></script>
</head>
<body>
  <demo></demo>
</body>
</html>

ES5 JavaScript

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
//app.js
function Demo(){
    var demo = this;
    demo.message = "Hello World";
    demo.myAction = function(){
        console.info('It Worked!');
    };
}
Demo.annotations = [
    new angular.ComponentAnnotation({
        selector: "demo"
    }),
    new angular.ViewAnnotation({
        template: '<div (click)="myAction()">{{message}}</div>'
    })
];
document.addEventListener("DOMContentLoaded", function(){
    angular.bootstrap(Demo);
})

See a working fiddle:

TypeScript HTML

1
2
3
4
5
6
7
8
9
10
11
12
13
<!-- index.html -->
<html>
  <head>
    <script src="https://github.jspm.io/jmcriffey/bower-traceur-runtime@0.0.87/traceur-runtime.js"></script>
    <script src="https://jspm.io/system@0.16.js"></script>
    <script src="https://code.angularjs.org/2.0.0-alpha.28/angular2.dev.js"></script>
  </head>
  <body>
    <!-- The app component created in app.ts -->
    <demo></demo>
    <script>System.import('app');</script>
  </body>
</html>

TypeScript JavaScript

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
//app.ts
import {Component, View, bootstrap} from 'angular2/angular2';

// Annotation section
@Component({
  selector: 'demo'
})
@View({
  template: '<div (click)="myAction()">{{message}}</div>'
})
// Component controller
class MyAppComponent {
  message: string;
  myAction: any;
  constructor() {
    this.message = 'Hello World';
    this.myAction = function(){
      alert('It Worked');
    }
  }
}

bootstrap(MyAppComponent);

ES6 HTML

1
2
3
4
5
6
7
8
9
<!-- index.html -->
<html>
  <head>
    <!-- NOTE: Your ES6 will need to be compiled to ES5, you would include your compiled ES5 here -->
  </head>
  <body>
    <demo></demo>
  </body>
</html>

ES6 JavaScript

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
//app.js
import {Component, View, bootstrap} from "angular2/angular2";

@Component({
  selector : "demo"
})
@View({
  template: "<div (click)="myAction()">{{message}}"</div>
})
class Demo{
  demo = this;
  demo.message = 'Hello World';
  demo.myAction = alert('It Worked');
}

bootstrap(Demo);

Pro Tip: Learn ES6 Online

Angular 2 will work with ES5 but it is highly suggested to use either ES6 or more preferably TypeScript with Angular 2. The reason being that Angular 2 is designed for where JS is trending and its source code is written in TypeScript as well.

Check out EggHead IO for videos on ES6, Angular 2, and more.

6 thoughts on “Event Binding in Angular 2

  1. Peter Kassenaar

    I think there’s a small typo in your first codeblock:

    1
    <div ng-click="myAction"></div>

    should be:

    1
    <div ng-click="myAction()"></div>

    Otherwise a very useful article. Thanks for putting all kinds of coding style (ES6, TypeScript, etc). together!
    Best,
    Peter.

    Reply
  2. Alex

    Thanks!

    Can I use interpolation within event binding?

    I’m getting error “Got interpolation ({{}}) where expression was expected”

    Reply
  3. Alex

    Looks like the html didn’t get through in my question, so I’ll try again without tags:
    *ngFor=”#item of items
    somedomelementhere (click)=”foo(‘{{item.name}}’)

    Reply
    1. Jacob Post author

      What you would want to do here is

      somedomelementhere (click)=”foo(‘item.name’)

      Curly braces are not needed around item.name

      Hope this helps!

      Reply
  4. Vishal

    I’m not able to bind global variable.

    here my code.

    mxEvent.addListener(img, ‘click’,
    mxUtils.bind(this, function(evt:any) {
    this.enableRightSideBar = true;
    console.log(this.enableRightSideBar);
    }.bind(this))
    )

    console.log(this.enableRightSideBar, ‘this.enableRightSideBar’);
    Show me “true”, but it’s not reflected on html.

    Please help me.

    Reply

Leave a Reply

Your email address will not be published. Required fields are marked *