In this blog, we will see smart components and dumb components in Angular, why you should use this pattern in your app, and the execution or implementation of smart and dumb components. Angular has strong and extraordinary features because of the frequent and timely updates. To talk about Smart Components and Dumb Components, they do not have anything to do it with Angular, it is just an approach we can use in any framework or library like react, Vue, etc.
The component structure will look like the following:
We will divide our Chat component into three parts.
Dumb components are the components that does not have a bunch of long-lived states. It does not have access to services nor have stored data in a back-end, all kinds of things that actually keep the focus of the component on presentation. We can also call them Isolated Components or Pure Components. Dumb or child component is only showing the data got from Smart Component.
my-chat.service.ts
import { Injectable } from ‘@angular/core’;
import { UserMessage } from ‘src/app/mychat.model’;
import { YtChannel } from ‘src/app/yt-channel.model’;
@Injectable()
export class MyChatService {
private channelsDb: YtChannel[] = [
{ _id: ‘0’, name: ‘general’ },
{ _id: ‘1’, name: ‘channel1’ }
];
// fake database
private messagesDb: UserMessage[] = [
{ _id: ‘0’, YtchannelId: ‘0’, userId: ‘0’, userName: ‘Manoj’, content: ‘Hello!’, timestamp: new Date() },
{ _id: ‘1’, YtchannelId: ‘1’, userId: ‘0’, userName: ‘Ankit’, content: ‘Hi!’, timestamp: new Date() },
{ _id: ‘2’, YtchannelId: ‘0’, userId: ‘0’, userName: ‘Jignesh’, content: ‘Hi! Good Morning’, timestamp: new Date() }
];
channels: YtChannel[] = [];
messages: UserMessage[] = [];
channel: YtChannel;
getYtChannels(): void {
// fake API, get your ytchannel data from the database
this.channels = this.channelsDb;
this.channel = this.channels[0];
}
getYourMessages(channelName: string): void {
// fake API, get your message data from the database
let channelId = ”;
this.channelsDb.map(channel => {
if (channel.name === channelName) {
channelId = channel._id;
}
});
const messages = [];
this.messagesDb.map(message => {
if (message.YtchannelId === channelId) {
messages.push(message);
}
});
this.messages = messages;
}
selectYtChannel(channel: YtChannel): void {
this.channel = channel;
this.getYourMessages(channel.name);
}
sendYourMessage(channelId: string, messageContent: string): void {
const message = {
_id: String(this.messagesDb.length),
channelId,
userId: ‘0’,
userName: ‘Manoj’,
content: messageContent,
timestamp: new Date()
};
this.messages = […this.messages, message];
this.messages = […this.messages, message];
// fake API, write message data to the database
this.messagesDb = […this.messagesDb, message];
}
constructor() { }
}
my-chat-area-bottom.component.ts
import { Component, EventEmitter, Input, OnInit, Output } from ‘@angular/core’;
import { FormBuilder, FormGroup, Validators } from ‘@angular/forms’;
@Component({
selector: ‘app-my-chat-area-bottom’,
templateUrl: ‘./my-chat-area-bottom.component.html’,
styleUrls: [‘./my-chat-area-bottom.component.css’]
})
export class MyChatAreaBottomComponent implements OnInit {
@Input() ytChannelId: string;
@Output() sendYourMessage = new EventEmitter<any>();
messageForm: FormGroup;
constructor(
private fb: FormBuilder
) { }
ngOnInit() {
this.messageForm = this.fb.group({
message: [”, Validators.required]
});
}
onSendMessage() {
if (!this.messageForm.valid) return;
this.sendYourMessage.emit({ channelId: this.ytChannelId, messageContent: this.messageForm.value.message });
this.messageForm.reset();
}
}
my-chat-area-bottom.component.html
<div class=”wrapper”>
<form [formGroup]=”messageForm” (ngSubmit)=”onSendYourMessage()”>
<input formControlName=”message” placeholder=”Click on enter to send message” />
</form>
</div>
If you verify the above code snippet, there is nothing new excepting @input () and @output ().
@Input() ytChannelId: string;
@Output() sendYourMessage = new EventEmitter<any>();
ytChannelId and sendYourMessage are equivalent to the values
<my-chat-area-bottom>
[YtChannelId]=”mychatService.ytchannel?._id”
(sendYourMessage)=”onSendYourMessage($event)”>
</my-chat-area-bottom>
Now you need to be clear about how they equivalent to each other.
Observe that, sendYourMessage is an EventEmitter, which can help us to release the event to the parent component in our scenario, it excludes the event with an object to the parent component.
this.sendYourMessage.emit({ channelId: this.ytChannelId, messageContent: this.messageForm.value.message });
ytchannel-list-component.ts
import { Component, EventEmitter, Input, OnInit, Output } from ‘@angular/core’;
import { YtChannel } from ‘src/app/yt-channel.model’;
@Component({
selector: ‘app-ytchannel-list’,
templateUrl: ‘./ytchannel-list.component.html’,
styleUrls: [‘./ytchannel-list.component.css’]
})
export class YtchannelListComponent implements OnInit {
constructor() { }
@Input() channels: YtChannel[];
@Input() ytChannelId: string;
@Output() selectYtChannel = new EventEmitter<YtChannel>();
onSelectYtChannel(channel: YtChannel) {
this.selectYtChannel.emit(channel);
}
ngOnInit(): void {
}
}
ytchannel-list-component.html
<ul>
<li *ngFor=”let channel of channels” [ngClass]=”{‘selected’: ytchannel._id === ytChannelId}”
(click)=”onSelectYtChannel(channel)”>
{{channel.name}}
</li>
</ul>
my-chat-area-dialog-component.ts
import { Component, Input, OnInit } from ‘@angular/core’;
import { UserMessage } from ‘..//mychat.model’;
@Component({
selector: ‘app-my-chat-area-dialog’,
templateUrl: ‘./my-chat-area-dialog.component.html’,
styleUrls: [‘./my-chat-area-dialog.component.css’]
})
export class MyChatAreaDialogComponent implements OnInit {
@Input() messages: UserMessage[];
constructor() { }
ngOnInit(): void {
}
}
my-chat-area-dialog-component.html
<ul class=”wrapper”>
<li *ngFor=”let message of messages”>
<p><span class=”name”>{{message.userName}}</span> <span
class=”timestamp”>{{message.timestamp | calendar}}</span></p>
<p>{{message.content}}</p>
</li>
</ul>
my-chat.component.ts
import { Component, OnInit } from ‘@angular/core’;
import { MyChatService } from ‘src/app/my-chat.service’;
import { YtChannel } from ‘src/app/yt-channel.model’;
@Component({
selector: ‘app-my-chat’,
templateUrl: ‘./my-chat.component.html’,
styleUrls: [‘./my-chat.component.css’]
})
export class MyChatComponent implements OnInit {
constructor(
private mychatService: MyChatService
) { }
ngOnInit() {
this.mychatService.getYtChannels();
this.mychatService.getYourMessages(‘general’);
}
onSelectYtChannel(ytchannel: YtChannel) {
this.mychatService.selectYtChannel(ytchannel);
}
onSendYourMessage({ YtChannelId, messageContent }) {
this.mychatService.sendYourMessage(YtChannelId, messageContent);
}
}
my-chat.component.html
<div class=”left”>
<my-channel-list [ytchannels]=”mychatService.channels” [ytchannelId]=”mychatService.ytchannel?._id”
(selectYtChannel)=”onSelectYtChannel($event)”>
</my-channel-list>
</div>
<div class=”right”>
<my-chat-area-dialog [messages]=”mychatService.messages”>
</my-chat-area-dialog>
<my-chat-area-bottom [YtChannelId]=”mychatService.ytchannel?._id” (sendYourMessage)=”onSendYourMessage($event)”>
</my-chat-area-bottom>
</div>
Let we use <my-chat-area-bottom> to define how smart or parent component and dumb or child component communicate:
<my-chat-area-bottom>
[YtChannelId]=”mychatService.ytchannel?._id”
(sendYourMessage)=”onSendYourMessage($event)”>
</my-chat-area-bottom>
[YtChannelId]=”mychatService.ytchannel?._id”
(sendYourMessage)=”onSendYourMessage($event)”
Conclusion
In this blog, we have seen Angular Smart and Dumb Component Architecture in which we have defined the Smart and Dumb Component with the proper example and explanation of it. We have also seen the main benefits of using a Smart component.
Content marketing has a hidden tax. It's not the writing itself, it's everything that happens…
Most marketing teams aren't failing because they lack data. They're failing because they can't act…
Email marketing continues to be one of the most effective ways for businesses to communicate,…
Xerox first introduced it around the mid-1970s. The need came up because the management activities…
Investing in the forex market may look to be a dangerous game. With some worthwhile…
The coronavirus outbreak has drastically changed the way we live our lives. Yes, that's absolutely…