Menu Close

Component communication with @Output


In this article we will learn about Component communication with @Output. @Output() marks a property in a child component as a doorway through which data can travel from the child to the parent. Please read my previous article Component communication with @Input.

We discussed our previous article about @Output properties Child to Parent Communication in Angular. Here we discuss about @Output examples.

Pass data from Child to parent component

There are three ways in which the parent component can interact with the child component

  • Parent listens for child event.
  • Uses Local Variable to access the child.
  • Uses a @ViewChild to get the reference to the child component.

Parent listens for child event

The Child Component exposes an EventEmitter Property. This Property is adorned with the @Output decorator. When Child Component needs to communicate with the parent it raises the event. The Parent Component listens to that event and reacts to it.

In this example we see when the child component button is clicked then parent component event is change.

@output-decorator

Component Communication with @Output

Child Component

  • Line no. 12- @Output used the event emitter.
  • Increment() and Decrement() function is ++ and — with emit the event that can use parent.
import { Component, EventEmitter, Input, OnInit, Output } from '@angular/core';

@Component({
  selector: 'app-child',
  inputs: ['count'],
  templateUrl: './child.component.html',
  styleUrls: ['./child.component.css']
})
export class ChildComponent implements OnInit {

  @Input() count: number | undefined;
  @Output() countChanged: EventEmitter<number> = new EventEmitter();
  constructor() { }

  ngOnInit(): void {
  }
  increment() {
    if (this.count!= undefined) {
      this.count++;
      this.countChanged.emit(this.count);
    }
  }
  decrement() {
    if (this.count!= undefined) {
      this.count--;
      this.countChanged.emit(this.count);
    }
  }
}

Child HTML Markup

<div class="mt-5">
    <p>This is Child Component</p>
    <button (click)="increment()">Increment</button>
    <button (click)="decrement()">decrement</button>
    <div>Current Child count is : {{ count}}</div>
</div>

Parent Component

  • The countChangedHandler($event) method accepts the $event argument. The data associated with event is now available to in the $event property
import { Component, OnInit } from '@angular/core';

@Component({
  selector: 'app-parent',
  templateUrl: './parent.component.html',
  styleUrls: ['./parent.component.css']
})
export class ParentComponent implements OnInit {

  constructor() { }
  Counter: number | undefined =5;
  ngOnInit(): void {
  }
 
  countChangedHandler(count: number) {
    this.Counter = count;
    console.log(count);
  }
}

Parent HTML Markup

  • The “countChanged” event is enclosed in Parentheses. It is then assigned to the method “countChangedHandler” in the component class. The syntax is similar to Event Binding
<p>This is Parent Component</p>
<p> current  Parent count is {{Counter}} </p>

<app-child [count]=Counter (countChanged)="countChangedHandler($event)"></app-child>

Parent uses local variable to access the Child in Template

Parent Template can access the child component properties and methods by creating the template reference variable.

Child Component

  • We removed all the @Input and @Output, child component count use Increment() and Decrement().
export class ChildComponent implements OnInit {
  count = 0;
  constructor() { }
  ngOnInit(): void {
  }
  increment() {
    this.count++;
  }
  decrement() {
    this.count--;
  }
}
<div class="mt-5">
    <p>This is Child Component</p>   
    <div>Current Child count is : {{ count}}</div>
</div>

Parent Component

  • We have created a local variable #child, on the tag . The “child” is called template reference variable, which now represents the child component.
  • The Template Reference variable is created, when you use # and attach it to a DOM element. You can then, use the variable to reference the DOM element in your Template
<p>This is Parent Component</p>
<p> current count is {{child.count}} </p>
 <button (click)="child.increment()">Increment</button>
 <button (click)="child.decrement()">decrement</button>
<app-child #child></app-child>

When you run the application and see the output like below.

local-variable-parent-child

The local variable approach is simple and easy, But it is limited because the parent-child must be done entirely within the parent template. The parent component itself has no access to the child.

You can’t use the local variable technique if an instance of the parent component class must read or write child component values or must call child component methods.

Parent uses a @ViewChild() to get reference to the Child Component

The @ViewChild decorator takes the name of the component/directive as its input. It is then used to decorate a property. The Angular then injects the reference of the component to the Property.

Injecting an instance of the child component into the parent as a @ViewChild is the another technique used by the parent to access the property and method of the child component.

On our next article we will learn about @ViewChild().

Conclusion

In this tutorial, we discuss about Component communication with @Output, here we explained how the parent can communicate with the child component. The Parent can subscribe to the events of the child component. It can use the Template local variable to access the properties and methods. We can also use @ViewChild decorator to inject the child component instance to the parent.

Leave behind your valuable queries, suggestions in the comment section below. Also, if you think this article help to you, do not forget to share this within your developer community. Happy Coding 🙂

Related Articles

Jayant Tripathy
Coder, Blogger, YouTuber

A passionate developer keep focus on learning and working on new technology.


Leave a Reply

Your email address will not be published.