Angular использование mat-checkboxes против mat-radio-кнопок в форме - PullRequest
2 голосов
/ 30 апреля 2020

Я создаю приложение для викторины, и мне нужно переключаться между mat-checkbox или mat-radio-button, в зависимости от того, есть ли на вопрос один или несколько ответов. Вопрос № 1 является ответом на вопрос с одним выбором и отображается с помощью кнопки-переключателя mat, тогда как Вопрос № 2 является вопросом с множественным ответом, но также отображается с помощью кнопки-переключателя mat вместо переключателя mat-radio.

Вот так выглядит мой шаблон:

<form [formGroup]="formGroup">
    <ol *ngIf="multipleAnswer === false">
        // using mat-radio-buttons here 
    </ol>
    <ol *ngIf="multipleAnswer === true">
        // using mat-checkboxes here
    </ol>
</form>

, а в моем файле ts лог c выглядит так:

multipleAnswer: boolean;

ngOnInit() {
  this.multipleAnswer = this.quizService.getQuestionType();
}

ngOnChanges(changes: SimpleChanges) {
  if (changes.question) {
    switch (this.question.type) {
      case 'SINGLE_CHOICE':
        this.formGroup = new FormGroup({
          answer: new FormControl([null, Validators.required])
        });
        break;
      case 'MULTIPLE_CHOICE':
        const multipleChoiceValidator = (control: AbstractControl) =>
          control.value.reduce(
            (valid: boolean, currentValue: boolean) => valid || currentValue
            , false
          ) ? null : {answers: 'At least one answer needs to be checked!'};
        this.formGroup = new FormGroup({
          answers: this.formBuilder.array(this.question.shuffledAnswers
              .map((answer: string) => this.formBuilder.control(false)),
            multipleChoiceValidator
          ),
        });
        break;
    }
  }
}

не нужно перемешивать Ответы тип вопроса должен быть выведен из файла assets / quiz.ts (не нужно жестко кодировать тип вопроса), а ответы должны быть числами, а не строками

в моем QuizService:

getQuestionType(): boolean {
  return (this.correctAnswers && this.correctAnswers.length === 1);
}

1 Ответ

1 голос
/ 02 мая 2020

Есть несколько проблем. Во-первых, вызов multipleAnswer only inside ngOnInit устанавливает эту логическую переменную только один раз в начале, она должна быть внутри ngOnChanges.

Но это не единственная проблема здесь, главная проблема в вашем QuizService. Здесь вы используете this.quizService.getQuestionType(); метод для установки multipleAnswer true или false, но внутри вашего getQuestionType() метода QuizService вы проверяете this.correctAnswers, если он установлен, и имеет длину элемента 1, но this.correctAnswers всегда пуст при вызове.

Другая проблема в вашем ngOnChanges у вас есть switch (this.question.type) здесь this.question кажется неопределенным в любое время.

Отредактируйте ваш код, как показано ниже, и проверяйте вывод консоли каждый раз, когда появляется вопрос.

Добавьте новый метод get correctAnswers из вопроса.

getCorrectAnswers(question:QuizQuestion){
   return question.options.filter((item)=> item.correct);
}

И отредактируйте Начиная с ngOnChanges, как показано ниже, я также добавил вывод консоли, чтобы вы могли видеть данные из нового метода выше.

ngOnChanges(changes: SimpleChanges) {   
   if (changes.question && changes.question.currentValue !== changes.question.firstChange){
     this.currentQuestion = changes.question.currentValue;
     this.correctAnswers = this.getCorrectAnswers(this.currentQuestion);
     this.multipleAnswer = this.correctAnswers.length > 1 ? true : false;
     console.log('correct ans: ', this.correctAnswers);
     ...

Я не могу изменить весь код, так как у вас есть собственный лог c за вашим кодом, но я обновил ответ, чтобы переменные, связанные с этой проблемой, правильно устанавливались внутри 'ngOnChanges`.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...