0

I have multiple <mat-button-toggle> elements generated in my app and I want always only one selected. The problem that I now have is, how to get the component reference to the last selected toggle-button when another toggle button is clicked.

I really searched quite a while but couldn't understand how to do it.

component.html

<mat-button-toggle (click)="onKeywordSelect($event)" *ngFor="let keyword of keywords" [id]="keyword.id" [attr.id]="keyword.id" [value]="keyword.id" class="keyword">
  <div class="text">{{ keyword.name }}</div>
</mat-button-toggle>

component.ts

// imports and @Component

export class NavbarComponent implements OnInit {

  keywords = [new Keyword('name1'), new Keyword('name2')]; // sample data
  $selectedKeyword: $ | any; // I've imported JQuery

  onKeywordSelect(event: any) {
    // This element depends on where you mouse was positioned when clicking
    // Most often not the <mat-button-toggle> but some child element
    const target = event.target;
    // To get to the <mat-button-toggle> component that was clicked
    const matButton = $(target).closest('mat-button-toggle');

    if (this.$selectedKeyword !== undefined) {
        // At the start there is no selected keyword
        // TODO: Set the 'checked' property of the cur selected keyword to false
    }
    this.$selectedKeyword = $matButton;
  }
}

I tried it with @ViewChild() but because the id of the selected keyword changes when the user selects one I don't know how to keep track of the selected component reference.

Edit

Forgot to mention: Yes I'm aware of mat-button-toggle-group but I don't want to use it because of some styling. Is there no other way to solve this?

2 Answers 2

1

Edit: Updated my ans as your requirement is not to use mat-button-toggle-group:

You can use checked property and set current and last selected value on change event like this:

component.html:

<mat-button-toggle
  *ngFor="let keyword of keywords"
  value="{{keyword.id}}"
  [id]="keyword.id"
  [attr.id]="keyword.id"
  (change)="this.onChange(keyword.id)"
  [checked]="this.currValue === keyword.id">
  {{keyword.name}}
</mat-button-toggle>

<div class="example-selected-value">
    Last Selected value: {{this.lastValue}}
</div>
<div class="example-selected-value">
    Current Selected value: {{this.currValue}}
</div>

component.ts:

keywords: any = [
    {id: 1, name: "name1"},
    {id: 2, name: "name2"},
    {id: 3, name: "name3"},
  ]
  lastValue: string = "";
  currValue: string = "";

  onChange = (value) => {
    this.lastValue = this.currValue;
    this.currValue = value;
  }

Check Demo Here.

Sign up to request clarification or add additional context in comments.

1 Comment

Thanks! Works great. Didn't think of that.
0

Add mat-button-toggle-group to select only one button and get value of group to get last selected button 

see: https://stackblitz.com/angular/yrqebgjbxao?file=app%2Fbutton-toggle-exclusive-example.ts

2 Comments

I already know about mat-button-toggle-group, but I'm trying to achieve this effect without wrapping the buttons in this element.
you can use name(to select only single button) & form controller(to get value) <mat-button-toggle name="yourName" formControlName=controller (click)="onKeywordSelect($event)" *ngFor="let keyword of keywords" [id]="keyword.id" [attr.id]="keyword.id" [value]="keyword.id" class="keyword"> <div class="text">{{ keyword.name }}</div> </mat-button-toggle>

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.