Topic: Trying to use switch (with lever) to toggle activate/deactivate function but it is not working

olaniyimoses pro asked 5 years ago


The code is supposed list the item with lever showing activate or deactivate based on what is saved in the database. and then be able to toggle anyone of the items

the items are are listed but the switch is activated for all items when only one item should be active as saved in the database. Please me, i will really appreciate. thank you

// the html code to list items to toggle

<table class="table-sm" mdbTable> <thead> <tr> <th>Name</th> <th>Activate</th> </tr> </thead> <tbody> <tr *ngFor="let season of seasons"> <td>{{ season.Name }}</td> <td> <form [formGroup]="form"> <div class="switch primary-switch"> <label> <input type="checkbox" formControlName="IsActive" /> <span class="lever"></span> </label> </div> </form> </td> </tr> </tbody> </table>

//the ts file

<table class="table-sm" mdbTable> <thead> <tr> <th>Name</th> <th>Activate</th> </tr> </thead> <tbody> <tr *ngFor="let season of seasons"> <td>{{ season.Name }}</td> <td> <form [formGroup]="form"> <div class="switch primary-switch"> <label> <input type="checkbox" formControlName="IsActive" /> <span class="lever"></span> </label> </div> </form> </td> </tr> </tbody> </table>

// and the service.ts file

getSeasons() { this.http.get<{message:string, seasons: any}>('http://localhost:3000/api/seasons/') .pipe(map((seasons) => { return seasons.seasons.map(season => { status = season.IsActive ? 'checked' : 'unchecked'; return { id: season._id, Name: season.Name, IsActive: status, DateCreated: season.DateCreated }; }); })) .subscribe((transformedSeasons) => { this.seasons = transformedSeasons; console.log(this.seasons); this.updateSeasons.next([...this.seasons]); }); }


Damian Gemza staff answered 4 years ago


Dear @olaniyimoses

I'm not sure if I have understood your problem well. Could you please correct me, if I'm wrong?

Do you want to create a table with some of seasons. After clicking on the switch element, you want to activate / deactivate seasons (every seasons rows or specific season row)?

Please take a look at the below code if it's something similar to your desired behavior:

.html:

<div class="container">
  <div class="row">
    <div class="col-md-6 mx-auto my-5">
      <table mdbTable>
        <thead>
        <tr>
          <th *ngFor="let head of headElements" scope="col">{{head}} </th>
        </tr>
        </thead>
        <tbody>
        <tr mdbTableCol *ngFor="let el of elements; let i = index" #rows>
          <th scope="row">
            <mdb-checkbox [disabled]="disabledElementIndex === i">Season {{i + 1}}</mdb-checkbox>
          </th>
          <td>{{el.first}}</td>
          <td>{{el.last}}</td>
          <td>
            <!-- Material switch -->
            <div class="switch" >
              <label>
                Off
                <input type="checkbox" (change)="onSwitchChange($event.target.value, i)">
                <span class="lever"></span> On
              </label>
            </div>
          </td>
        </tr>
        </tbody>
      </table>
    </div>
  </div>
</div>

.ts:

import {Component, ElementRef, QueryList, Renderer2, ViewChildren} from '@angular/core';

@Component({
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.scss']
})
export class AppComponent {
  @ViewChildren('rows') rows: QueryList<ElementRef>;
  elements: any = [
    {id: 1, first: 'Mark', last: 'Otto', handle: '@mdo'},
    {id: 2, first: 'Jacob', last: 'Thornton', handle: '@fat'},
    {id: 3, first: 'Larry', last: 'the Bird', handle: '@twitter'},
  ];

  disabledElement = null;
  disabledElementIndex = null;
  headElements = ['ID', 'First', 'Last', 'Handle'];

  constructor(private renderer: Renderer2) {
  }

  onSwitchChange(value: any, item: number) {
    this.disabledElementIndex = item;
    this.disabledElement = this.rows.toArray().find((row: ElementRef, index: number) => index === item).nativeElement.firstElementChild.firstElementChild;

    if (this.disabledElement.getAttribute('disabled') === 'true') {
      this.renderer.setAttribute(this.disabledElement, 'disabled', 'false');
      this.disabledElementIndex = null;
    } else {
      this.renderer.setAttribute(this.disabledElement, 'disabled', 'true');
    }
  }
}

Best Regards,

Damian


olaniyimoses pro commented 4 years ago

@Damian Gemza Yes, when i click on specific season row. That is each row will have its own switch element and when i click anyone, it should just activate / deactivate the one i click and not all the rows. Thank you. I really appreciate your prompt response. I'm not sure the sample code you showed me will do just that.


Damian Gemza staff commented 4 years ago

Take a try and let me know. If this won't fit your needs, you have to write the needed code on your own.


Damian Gemza staff answered 5 years ago


Dear @olaniyimoses

You have pasted HTML code two times - there's no ts code for the component.

Could you please provide it to me?

Also, could you describe one more time, which behavior you want to achieve?

Best Regards,

Damian


olaniyimoses pro commented 5 years ago

@Damian Gemza

This is the TS code

import { Component, OnInit, OnDestroy } from '@angular/core'; import { Subscription } from 'rxjs'; import { FormGroup, FormControl } from '@angular/forms';

import { Season } from '../season/season.model'; import { SeasonService } from '../season/season.service'; import { ActivatedRoute, ParamMap } from '@angular/router';

@Component({ selector: 'app-list-season', templateUrl: './list-season.component.html', styleUrls: ['./list-season.component.scss'] }) export class ListSeasonComponent implements OnInit, OnDestroy { form: FormGroup; isLoading = false; private seasonId: string; IsActive = false; seasons: Season[] =[]; private seasonsSubscription: Subscription;

constructor(public seasonServices: SeasonService, public route: ActivatedRoute) { }

ngOnInit() { this.route.paramMap.subscribe((paramMap: ParamMap) => { if(paramMap.has('seasonId')) { this.seasonId = paramMap.get('seasonId'); } });

this.form = new FormGroup({
  'IsActive': new FormControl(this.getToggle)
})

this.isLoading = true;
this.seasonServices.getSeasons();
this.seasonsSubscription = this.seasonServices.getSeasonsUpdateListener()
  .subscribe((seasons: Season[]) => {
    this.isLoading = false;
    this.seasons = seasons;
  });

}

getToggle(){ return this.form.controls['IsActive'].value; }

ngOnDestroy() { this.seasonsSubscription.unsubscribe(); }

onToggleSeason() { this.seasonServices.activateSeason(this.seasonId, this.IsActive); return false; }

}

// here is the html code again {{ season.Name }}

// and the season.service.ts activateSeason(seasonId: string, IsActive:boolean){ let seasonInfo: any = {"IsActive": IsActive}; this.http.put('http://localhost:3000/api/seasons/' +seasonId, seasonInfo) .subscribe(res => { console.log(res); }) }

i'm using the onToggleSeason function to toggle a state of a boolean field in the database using switch element (lever) on the front end. I have a table called Season and i want to be able to activate / deactivate seasons when i click on the lever in the front end. I hope it is clear enough. Thank you so much.



Please insert min. 20 characters.

FREE CONSULTATION

Hire our experts to build a dedicated project. We'll analyze your business requirements, for free.

Status

Answered

Specification of the issue

  • ForumUser: Pro
  • Premium support: No
  • Technology: MDB Angular
  • MDB Version: 7.5.1
  • Device: Desktop
  • Browser: Chrome/MS Edge
  • OS: Win 10
  • Provided sample code: No
  • Provided link: No