Sharing Data Between Angular Components

Angular Programming Published on 25 February 2020

Sharing the data between the component is an important concept before making the First Angular project. In this topic, we learn four methods to share the data between the component. components basically are the basic building blocks for making the angular project and contain different relationship among them For example parent to child relationship, child to parent relationship and Sibling



Parent to Child: Sharing with @Input decorator:


This is the most commonly used method to send the data from the parent component to child component: In this method, we send the data from the p[arent component via template and get the data inside the child component via @input decorator in .ts file.


Example:


parent.component.ts


import { Component } from '@angular/core';

@Component({

selector: 'app-parent',

template: `

<app-child [dataSendToChild]="parentData"></app-child>

`, styleUrls: ['./parent.component.css']

}) export class ParentComponent{

parentData = "data send from the parent component"

constructor() { }

}


child.component.ts


import { Component, Input } from '@angular/core';

@Component({

selector: 'app-child',

template: `

{{ dataToSendChild }}

`, styleUrls: ['./child.component.css']

}) export class ChildComponent {

@Input() dataToSendChild: string;

constructor() { }

}

Child to Parent: Sharing Data with ViewChild


@ViewChild decorator gives access to the use of the methods and properties of child component into the parent component. Child component data would not available inside the parent component until the child component has not been initialized. This means we need to implement the ngAfterViewInit life cycle hook method to receive the data from the child component.


Example:


parent.component.ts


import { Component, ViewChild, AfterViewInit } from '@angular/core';

import { ChildComponent } from "../child/child.component";

@Component({

selector: 'app-parent',

template: `

{{ childData}}

<app-child></app-child>

`, styleUrls: ['./parent.component.css']

}) export class ParentComponent implements AfterViewInit {

@ViewChild(ChildComponent) ChildComponent;

constructor() { }

childData:string;

ngAfterViewInit() {

this.childData = this.ChildComponent.data

} }


child.component.ts


import { Component} from '@angular/core';

@Component({

selector: 'app-child',

template: ``,

styleUrls: ['./child.component.css']

}) export class ChildComponent {

data = Send data from the child';

constructor() { }

}


Child to Parent: Sharing Data with Output() and


EventEmitter


Another way to send the data from child to parent component with @Output() and EventEmitter. In this method, we emit the data from the child component and get the data with the help of @Output() inside the parent component. This method basically used to send the data on a particular event For example button click.


Example :


In this example, we make a button inside the child component. when anyone clicks on the button then we make a function that triggers click on the button and emit data inside the button click method with the help of EventEmitter and get the emitted data inside the parent component with @Output().


Parent.component.ts


import { Component } from '@angular/core';

@Component({

selector: 'app-parent',

template: `

{{childData}}

<app-child (dataEventEmitter)="receiveData($event)"></app-child>`,

styleUrls: ['./parent.component.css']

}) export class ParentComponent {

constructor() { }

childData:string;

receiveData($event) {

this.childData = $event

} }


Child.component.ts


import { Component, Output, EventEmitter } from '@angular/core';

@Component({

selector: 'app-child',

template: `

<button (click)="sendData()">click for data send</button>

`, styleUrls: ['./child.component.css']

}) export class ChildComponent {

data: string = "data send from the child component"

@Output() dataEventEmitter= new EventEmitter<string>();

constructor() { }

sendData() {

this.sendEventEmitter.emit(this.data)

} }


Unrelated(No Relationship) Components: Sharing Data


with Service class


When you want to send the data between the component they have no relation between them like siblings. In this case, we make a service that is globally accessible and inject inside the component constructor in which you want to send the data. If you want your data should be sync then you can RxJS BehaviorSubject.


sharedata.service.ts


import { Injectable } from '@angular/core';

import { BehaviorSubject } from 'rxjs';

@Injectable()

export class ShareDataService {

private dataSource = new BehaviorSubject('default data send');

currentData = this.dataSource.asObservable();

constructor() { }

changeData(data: string) {

this.dataSource.next(data)

} }


Parent.component.ts


import { Component, OnInit } from '@angular/core';

import { ShareDataService } from "../sharedata.service";

@Component({

selector: 'app-parent',

template: `

{{data}}

`, styleUrls: ['./sibling.component.css']

}) export class ParentComponent implements OnInit {

data:string;

constructor(private service: ShareDataService) { }

ngOnInit() {

this.service.currentData.subscribe(response => this.data =response)

} }


Sibling.component.ts


import { Component, OnInit } from '@angular/core';

import { ShareDataService } from "../sharedata.service";

@Component({

selector: 'app-sibling',

template: `

{{data}}

<button (click)="change()">New Data</button>

`, styleUrls: ['./sibling.component.css']

}) export class SiblingComponent implements OnInit {

data:string;

constructor(private service: shareDataService) { }

ngOnInit() {

this.data.currentData.subscribe(res => this.data =res)

} chnage() {

this.service.changeData("Data from the sibling")

} }