Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

mat-step onclick event function

wondering if it is possible to have a click event for the mat-step button. For each mat-step button, I would like to add a (click) event which calls a method. In other words, the mat-step button acts like a regular button.

This is the mat-step: https://material.angular.io/components/stepper/overview

This is my code:

<mat-step>
<ng-template matStepLabel (click) = "createView()">Output</ng-template>
</mat-step>

I get this error:

Template parse errors: Event binding click not emitted by any directive on an embedded template. Make sure that the event name is spelled correctly and all directives are listed in the "@NgModule.declarations". ("eateView()" >Output-->

like image 350
dataviews Avatar asked Jul 12 '18 04:07

dataviews


3 Answers

So, I just ran into this problem and the easy fix is to wrap the actual content of the step label in a p tag and add the click event there. For your example, it'd be:

<mat-step>
  <ng-template matStepLabel>
    <p (click)="createView()">Output</p>
  </ng-template>
</mat-step>

Alternatively, and much more powerfully, you can hook into the selectionChange event in the parent stepper component like so:

<mat-horizontal-stepper (selectionChange)="selectionChange($event)">

The event emitted has the following properties: https://material.angular.io/cdk/stepper/api#StepperSelectionEvent

like image 158
Patrick Steger Avatar answered Oct 20 '22 17:10

Patrick Steger


After Step event. This was painful for me to figure out. When you land on the new step and you want to fire an event. Do the following.

Add (animationDone)

<mat-horizontal-stepper linear #stepper (animationDone)="selectionChange(stepper)">

This will fire after the step is finished. And will give you the index of the new step you are on!

like image 36
Crimson_Hawk Avatar answered Oct 20 '22 17:10

Crimson_Hawk


For those who also want to add click event listener to the stepper even if user click the current step (which won't trigger selectionChange event):

    ngAfterViewInit() {
        console.log('ngAfterViewInit is triggered');
        this.fadeOut = false;
        let elements = document.querySelectorAll('mat-step-header');
        console.log('elements: ', elements);
        if (elements) {
            elements.forEach((e, i) => {
                console.log('e', i, ': ', e);
                if (i === 0) {
                    this.ele0 = e;
                    this.click0 = e.addEventListener('click', () => this.function(i));
                }
                else if (i === 1) {
                    this.ele1 = e;
                    this.click1 = e.addEventListener('click', () => this.function(i));
                }
                else if (i === 2) {
                    this.ele2 = e;
                    this.click2 = e.addEventListener('click', () => this.function(i));
                }
            })
        }
    }

If you don't want to assign each listener to a unique value, you can just remove the if condition. But it is recommended as you can remove those listeners on destroy.

like image 1
Terry Windwalker Avatar answered Oct 20 '22 18:10

Terry Windwalker