Angular4 - Нет доступа для доступа к формам

У меня есть пользовательский элемент:

<div formControlName="surveyType">
  <div *ngFor="let type of surveyTypes"
       (click)="onSelectType(type)"
       [class.selected]="type === selectedType">
    <md-icon>{{ type.icon }}</md-icon>
    <span>{{ type.description }}</span>
  </div>
</div>

Когда я пытаюсь добавить formControlName, я получаю сообщение об ошибке:

ОШИБКА Ошибка: Нет доступа к значению для элемента управления формы с именем: 'SurveyType'

Я пытался добавить ngDefaultControl безуспешно. Кажется, потому что нет ввода/выбора... и я не знаю, что делать.

Я хотел бы привязать мой клик к этому formControl, чтобы, когда кто-то нажимал на всю карту, это выдвигало мой "тип" в formControl. Является ли это возможным?

Ответ 1

Вы можете использовать formControlName только для директив, которые реализуют ControlValueAccessor.

Внедрить интерфейс

Итак, чтобы сделать то, что вы хотите, вам нужно создать компонент, который реализует ControlValueAccessor, что означает реализацию следующих трех функций:

  • writeValue (говорит Angular, как написать значение из модели в представление)
  • registerOnChange (регистрирует функцию обработчика, вызываемую при изменении представления)
  • registerOnTouched (регистрирует обработчик, вызываемый, когда компонент получает событие касания, полезно знать, был ли компонент сфокусирован).

Зарегистрировать поставщика

Затем вы должны сказать Angular, что эта директива - это ControlValueAccessor (интерфейс не собирается вырезать ее, так как она удаляется из кода при компиляции TypeScript на JavaScript). Вы делаете это, регистрируя поставщика.

Поставщик должен предоставить NG_VALUE_ACCESSOR и использовать существующее значение. Вам также понадобится forwardRef здесь. Обратите внимание, что NG_VALUE_ACCESSOR должен быть несколькими провайдерами.

Например, если ваша настраиваемая директива называется MyControlComponent, вы должны добавить что-то по следующим строкам внутри объекта, переданного в @Component decorator:

providers: [
  { 
    provide: NG_VALUE_ACCESSOR,
    multi: true,
    useExisting: forwardRef(() => MyControlComponent),
  }
]

использование

Ваш компонент готов к использованию. При использовании форм с ngModel привязка ngModel теперь будет работать правильно.

С реактивными формами вы теперь можете правильно использовать formControlName и элемент управления формы будет вести себя так, как ожидалось.

Ресурсы

Ответ 2

Я думаю, вы должны использовать formControlName="surveyType" на input а не на div