Как переключить кнопку-переключатель по умолчанию, выбранную в angular 8, с помощью ControlValueAccessor

Я пытаюсь создать настраиваемый элемент с помощью Angulars ControlValueAccessor. Цель - переключатель с тремя состояниями: истина, ложь и ноль. По умолчанию должен быть выбран Null, я пробовал некоторые решения из других сообщений, но они не работали.
Я попытался добавить «value = null» в группу mat-button-toggle-group, а также добавить атрибут «checked» в саму null mat-button-toggle.

HTML:

<div class="nullableBoolWrapper" fxLayout="row">
<mat-label class="centred-vertically">{{ label }}</mat-label>
<mat-button-toggle-group class="selection-button"
[disabled]="isDisabled"
[(ngModel)]="selectedValue"
(change)="changed($event)">
    <mat-button-toggle ngDefaultControl value=true>{{ descriptionList[0].description }}</mat-button-toggle>
    <mat-button-toggle ngDefaultControl value=false>{{ descriptionList[1].description }}</mat-button-toggle>
    <mat-button-toggle ngDefaultControl value=null [disabled]="!selectableNull">{{ descriptionList[2].description }}</mat-button-toggle>
</mat-button-toggle-group>

TS:

import { Description } from './../core/models/description';
import { Component, ViewEncapsulation, forwardRef, Input, OnInit } from '@angular/core';
import { ControlValueAccessor, NG_VALUE_ACCESSOR } from '@angular/forms';

export const NULLABLE_BOOL_VALUE_ACCESSOR: any = {
  provide: NG_VALUE_ACCESSOR,
  useExisting: forwardRef(() => NullableBoolComponent),
  multi: true
};

@Component({
  selector: 'nullable-bool',
  templateUrl: './nullable-bool.component.html',
  styleUrls: ['./nullable-bool.component.scss'],
  providers: [NULLABLE_BOOL_VALUE_ACCESSOR]
})
export class NullableBoolComponent implements ControlValueAccessor, OnInit {

  constructor() { }

  @Input('descriptionList') descriptionList: Description[];
  @Input('selectableNull') selectableNull = false;
  @Input('label') label: string;

  public selectedValue: boolean | null = null;
  public isDisabled = false;

  private defaultList: Description[] = [{ description: 'Yes' }, { description: 'No' }, { description: 'Not set' }];
  private onChange: any = () => {};
  private onTouch: any = () => {};

  writeValue(val: boolean | null): void { this.selectedValue = val; }

  registerOnChange(fn: any): void { this.onChange = fn; }

  registerOnTouched(fn: any): void { this.onTouch = fn; }

  setDisabledState?(isDisabled: boolean): void { this.isDisabled = isDisabled; }

  ngOnInit() { this.descriptionList === undefined ? this.descriptionList = this.defaultList : null; }

  changed($event: any): void {
    this.onTouch();
    this.onChange($event);
  }
}

Решение:

<div class="nullableBoolWrapper" fxLayout="row">
    <mat-label class="centred-vertically">{{ label }}</mat-label>
    <mat-button-toggle-group class="selection-button"
    [disabled]="isDisabled"
    (change)="changed($event)" #gro="matButtonToggleGroup" value="null">
        <mat-button-toggle ngDefaultControl [value]="true">{{ descriptionList[0].description }}</mat-button-toggle>
        <mat-button-toggle ngDefaultControl [value]="false">{{ descriptionList[1].description }}</mat-button-toggle>
        <mat-button-toggle ngDefaultControl value="null" [disabled]="!selectableNull">{{ descriptionList[2].description }}</mat-button-toggle>
    </mat-button-toggle-group>
</div>

В моем случае мне пришлось удалить ngModel.

Привет


person KastenBrot    schedule 16.03.2020    source источник


Ответы (1)


Итак, я провел небольшое исследование, и проблема в том, что [value] = "null" присваивает значение null атрибуту value, в отличие от того, если у вас value = null, тогда он присваивает "null" вместо null.

и «null» не равно нулю, поэтому он не будет выбран.

Имеет 2 решения.

Я сделал вам пример в stackblitz

Надеюсь, вы понимаете, о чем я.

person Pavel B.    schedule 16.03.2020
comment
Думаю, я понимаю, значит, значение null возвращается в виде строки? Я пробовал ваши решения, но по какой-то причине они у меня не работают ... Не получаю никаких ошибок. - person KastenBrot; 16.03.2020
comment
Можете ли вы показать мне свой код после того, как вы внесли изменения? - person Pavel B.; 16.03.2020
comment
вы должны добавить значение = null к ‹mat-button-toggle-group›, если вы хотите, чтобы это работало. - person Pavel B.; 16.03.2020
comment
добавил это к вопросу - person KastenBrot; 16.03.2020
comment
Похоже, это проблема с ngModel, если вы используете значение, оно работает так, как должно. - person Pavel B.; 16.03.2020
comment
facepalm да, я удалил ngModel, и он работает ... Спасибо за быстрый ответ! - person KastenBrot; 16.03.2020