Angular @input, @output & EventEmitter

In this guide let us learn how to make use of @input, @output & EventEmitter in Angular. We use these decorators to pass data from parent to child component & vice versa. @Input defines the input property in the component, which the parent component can set. The @output defines the output property (event), which we raise in the child component using the EventEmitter. The parent listens to these events.

@input, @output & Eventemitter

@input

Input decorator marks the property as the input property. I.e it can receive data from the parent component. The parent component uses the property binding to bind it to a component property. Whenever the value in the parent component changes angular updates the value in the child component.

Example

Consider the following component class

We have Input decorator on the customer property. The component expects that the parent component will supply its value.

The parent component supplies the customer object using the property binding syntax. We add a square bracket around the customer property. Assign template expression (selectedCustomer) to it, which is a property in the parent component.

@output

Output decorates the property as the output property. We initialize it as an EventEmitter. The child component raises the event and passes the data as the argument to the event. The parent component listens to events using event binding and reads the data.

Example

The customerChange is the Output property and is of type EventEmitter.

In the parent component, we subscribe to the event using the event binding syntax. Use the () around the event name (customerChange) and assign a template statement (update($event)) to it. It receives the data in the $event argument.

Remember you must use the argument name as $event.

EventEmitter

EventEmitter is responsible for raising the event. The @output property normally is of type EventEmitter. The child component will use the emit() method to emit an event along with the data.

Now let us build an app to learn how to use Input, output & EventEmitter

@input, @output & Eventemitter Example

The app we build has two components. The parent component shows a list of customers. The user has the option to click on the edit button, which results in a child component displaying the customer form Once the user updates the records, the child component raises the event. The parent captures the event. The parent then updates the list with the new data.

Create a new application using the following command

Create the customerList & customerDetail components. Also, create the customer class

Customer

app.module.ts

The ngModel needs the FormsModule. Hence import it and add it in import metadata.

Child Component

The child component gets an instance of the customer in its input property customer. The parent needs to set it using the property binding

Users can edit the customer. Once finished they will click the update button. The update method raises the customerChange event. We pass the customer as the argument to the event. The parent component listens to the event and receives the data.

The following is the complete code of the CustomerDetailComponent.

'app-customer-detail' is the name of the selector for this component.

The customer property is the input property decorated with Input.

customerChange is decorated as the output property of type EventEmitter

Whenever the user updates the customer, we raise the event customerChange. We pass the updated customer as the argument to it.

The customer-detail.component.htmlis as follows.

The ngModel binds the customer to the input element. It is a two-way binding. The click event of the button is bound to update() method in the component.

Parent Component

The job of the parent component is to display a list of customers. When the user clicks on the edit button pass the selected customer to the child component. Then wait for the customerChange event. Update the customer’s list on receipt of data from the child.

The following is the customer-list.component.html

Use the ngFor directive to loop through the customer list and display the customer details.

The event binding to capture the click event. We pass the customer object to the showDetails method

app-customer-detail is the selector for the CustomerDetailComponent. We use the property binding to send the selectedCustomer to the child component. The child component raises the customerChange event, which we listen to using the event binding and call the update method.

Customer-list.component.ts

The component code of the parent component. It has two method showDetails & update

The showDetails method gets the customer as its argument. We clone it & assign it to selectedCustomer

Since the customer is an object it is Passed by Reference. When you make any modification to the customer it will also be reflected in the customer’s collection. We want the update the customer’s only when we get the data from the child. Hence we clone the customer and send it to the child component.

If you are passing primitive data types like numbers are Passed by Value.

Finally in the root component (i.e. app.component.html ) copy the following

Run the app

Angular @input, @output & EventEmitter Example

Notes on @Input & @Output

You can also pass the optional name

Input decorator allows us to pass an option name, which you can use it while binding in the parent

For Example

Intercept input property changes with a setter

You can also create a setter property

Subscribe to @Input changes using ngChanges

You can also subscribe to the changes using ngOnChanges life cycle hook.

EventEmitters are observable

EventEmitters are RxJs Subjects. Hence you can make use of RxJs operators to manipulate them. Read more about it from this link.

Pass by reference

The objects are passed by reference. Hence if you modify the object, you are updating the original object. The primitive data types like numbers are Passed by Value.

References

Summary

This article shows how to make use of Input, output & EventEmitter in Angular. We use them to communicate with parent & child components. The Child component defines the input & output property using @Input & @output decorators. The Parent sets the input property using property binding. The child component raises the event using EventEmitter whenever it wants to send data to the parent. The parent listens to output property using event binding.

15 thoughts on “Angular @input, @output & EventEmitter”

  1. Few things missed here.
    ng n c customerList use ng g c customerList.

    Also add in app.component.html.

    Ignore this error “ERROR TypeError: Cannot read property ‘customerNo’ of undefined”, once we start edit this will be cleared.

    Thanks

    1. You can get rid of the “ERROR TypeError:….” by defining a blank value for selectedCustomer in customer-list.component.ts. For example:
      ngOnInit() {

      let myCustomer = {customerNo:0, name:””,address:””,city:””,state:””,country:””};

      this.showDetails(myCustomer);
      }

      1. Sorry again, The reply editor won’t let me type angle brackets. So the let statement should be myCustomer = angleBracket Customer angleBracket{ customerNo:0, …etc.

Leave a Comment

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

This site uses Akismet to reduce spam. Learn how your comment data is processed.

Scroll to Top