angulartypescriptangular6ngrxngrx-reducers

Call same function in reducer for multiple mat-slide-toggle/checkboxes in component.html


I'm pretty new to angular and ngrx and I'm working on a project where the user is able to generate forms. The user has the option to add, from a sidebar, multiple form-elements (e.g labels, textfields, dropwdown menus, checkboxes, etc). Next to every generated form-element there are two buttons, deleting and options, now i have to add a slide-toggle/checkbox next to these two buttons (as seen in the picture below).

Generated form elements

======================================================

component.html

<!-- sidebar for adding formelements-->

<div id="add-element-div">
    <button mat-icon-button matTooltip="Label"
            (click)="store.dispatch(createAction.editorAddLabel(currentPageNumber))">
      <mat-icon class="color">label</mat-icon>
    </button>
.....
</div>

<!-- option buttons for every element-->
<div class="ElementOptionButtons">

<button mat-icon-button
 (click)="store.dispatch(this.createAction.editorRemoveElement(currentPageNumber,
 currentForm.pages[currentPageNumber].pageElements.indexOf(FormularElement)))"
 matTooltip="Delete">
 <i class="material-icons">delete</i>
</button>
....


<!-- toogle-slider/checkbox -->


  <mat-slide-toggle
    *ngIf="FormularElement.type!=='label'"

    (change)="store.dispatch(createAction.editorAddAsRequired(currentPageNumber,
    currentForm.pages[currentPageNumber].pageElements.indexOf(FormularElement)))" 
    matTooltip="Pflichtfeld">
    <p>{{i}}</p>
  </mat-slide-toggle>

</div>

reducer.ts

   case fromEditorForm.EDITOR_ADD_AS_REQUIRED: {
      const changedState = JSON.parse(JSON.stringify(state));
      console.log('Reducer: mark as required');
      console.log(" element: " + action.elementIndex + " pageNumbeR: " + action.pageNumber );
      //changedState.form.pages[action.pageNumber].pageElements[action.elementIndex].required=true;
      return changedState;
    }
      return changedState;

component.ts

export class EditorComponent implements OnInit {
  public chosenBusinessType;
  public currentForm: Form;
  public currentPage: FormularPage;
  public currentPageElements: FormElement[];
  public currentPageNumber;

  public loadedForms: Form[];

  public createAction = new ActionFactory();

  constructor(private store: Store<fromStore.GeneratorState>,
              private formsService: FormsService,
              private route: ActivatedRoute) {

    this.store.select(fromStore.getLoadedForms).subscribe((forms) => {
      this.loadedForms = forms.entities;
    });
  }

  ngOnInit() {
    this.currentPageNumber = 0;
    this.route.params.subscribe(params => {
      if (params.id === 'newForm') {
        console.log('EDITOR: Aufgerufen zum Erstellen eines neuen Formulars');
        this.currentForm = new Form();
      } else {
        console.log('EDITOR: Aufgerufen zum Bearbeiten eines existierenden Formulars');
        for (const form of this.loadedForms) {
          if (form.id === params.id) {
            this.currentForm = form;
          }
        }
      }
      this.store.dispatch(this.createAction.editorChangeForm(this.currentForm));


      this.store.select(fromStore.getFormInEditor).subscribe((object) => {
        this.currentForm = object.form;
        this.chosenBusinessType = this.currentForm.businessType;
      });
    });
  }

======================================================

What i want

When the slide-toggle/checkbox is checked then the element should be marked as required. I want to put one method for all slider on the (change).

What is the problem

When i try to slide the slider, all sliders gonna get set on true or nothing happens (depends on what i tried). If i don't have a (change) in the html then the slider i toggle gets toggled, not the others, as soon as i put a function on the (change) the problem with all sliders or none appears.

What have i tried

I added an index to the sliders (seen in the picture above) to be sure that every slider has a different id. If i click on the sliders it loggs the correct formElement, but the slider don't get checked.

Of course i have searched on stackoverflow/google for similiar questions, this was the problem that came close to mine. Difference is that there is no ngrx and that he toggles every slider with a different method. But i guess my problem is because the slider is a two-way-binding?

What i'm gonna do next

As for every added element from the sidebar, a function (in reducer.ts) is executed that pushes a new FormElement (component.ts). I would make a function that is executed every time an element is added to FormElement that also adds a slide-toggle element, but i don't know if this is best practice

=======

As i said i'm pretty new to Angular and ngrx, if i'm missing some important basics please link articles/examples. If you need more of code or anything else i'll can update the post.


Solution

  • Found the solution by myself.

    The whole thing is wrapped in a div with a ngFor loop. I then added a ngModel for the slider, i also added an elemntSlider as a model to the whole form model with is now added (the elementSlider) to every element that is added to the form.

             <mat-slide-toggle
              *ngIf="FormularElement.type!=='label'"
              [(ngModel)]="FormularElement.elementSlider"
            </mat-slide-toggle>