2016-08-26 4 views
4

У меня есть форма, где я бы хотел, чтобы пользователь редактировал подписку на журнал, которую он хотел бы получить. Код выглядит следующим образом:Как обрабатывать группу checkbox в Angular 2 RC5?

Компонент:

export class OrderFormComponent { 

    subscriptions = [ 
     {id: 'weekly', display: 'Weekly newsletter'}, 
     {id: 'monthly', display: 'Monthly newsletter'}, 
     {id: 'quarterly', display: 'Quarterly newsletter'}, 
    ]; 

    mySubs = [ 
     this.subscriptions[1] 
    ] 

    order = new FormGroup({ 
     subs: new FormArray(this.mySubs.map(sub => new FormControl(sub)), Validations.required) //Lost at this part 
    }); 
} 

Шаблон:

<form [formGroup]="order"> 

<div formArrayName="subs"> 
    <label>Sign me up for newsletters</label> 
    <p *ngFor="let s of subscriptions; let i=index"> 
     <input type="checkbox" [value]="s.id" [formControlName]="i" /> {{ s.display }} 
    </p>   
</div> 

<div> 
    <input type="checkbox" formControlName="agree" /> I agree to the terms and conditions. 
</div> 

{{ order.value | json }} 

Когда я запустить приложение, три галочки отображаются, но только один проверяется (неправильно один в этом). Тот, который проверен, имеет ярлык, а другие - нет.

component output

Что я здесь делаю неправильно?

ответ

5

Хорошо, поэтому я, наконец, понял это.

В моем компоненте у меня есть:

// The order retrieved from the server 
subscription = { 
    schedules: [{id: 'weekly', display: 'Weekly update'}], 
} 

//The FormGroup element 
this.subscriptionForm = new FormGroup({ 
     //Here I fill up a FormArray with some FormControls initialized to the 
     //currently selected schedules 
     schedules: new FormArray(this.subscription.schedules.map(schedule => new FormControl(schedule)), Validators.minLength(1)) 
    }); 

По мнению у меня есть:

<div> 
    <label>Frequency</label> 
    <p *ngFor="let schedule of viewData.schedules"> 
     <input type="checkbox" 
       [checked]="subscription.schedules.includes(schedule)" 
       (change)="changeSchedules(schedule)"> {{ schedule.display }} 
    </p> 
</div> 

А вот метод changeSchedules() в классе:

changeSchedules(schedule: any) { 
    var currentScheduleControls: FormArray = this.subscriptionForm.get('schedules') as FormArray; 
    var index = currentScheduleControls.value.indexOf(schedule); 
    if(index > -1) currentScheduleControls.removeAt(index) //If the user currently uses this schedule, remove it. 
    else currentScheduleControls.push(new FormControl(schedule)); //Otherwise add this schedule. 
} 

работает как прелесть! Форма проверяет, как ожидалось, без дополнительного метода, необходимого для извлечения/консолидации массива подписки перед отправкой формы.

+0

Как '[checked] =" subscription.schedules.includes (schedule) "работать, поскольку' subscription.schedules' никогда не изменяется? – Kevin

+0

Я честно не помню, как все остальное было подключено, чтобы оно работало. С тех пор я перешел от Углового. Извините:/ – kshep92

+0

Отличный ответ! Благодарю. Это позволяет мне избежать создания настраиваемого компонента для аналогичной задачи –

0

Вы сделали ошибку в создании экземпляра FormControl. Вместо того, чтобы создать новый экземпляр FormControl для всех вариантов, вы сделали только один (путем итерации через ваш mySub). Измените код, чтобы быть что-то вроде этого (не проверено):

order = new FormGroup({ 
    // creating an array of form control with default values 
    subs: new FormArray(this.subscriptions.map(sub => new FormControl(this.isSelectedSub(sub))), Validations.required) 
}); 


//... 
isSelectedSub(sub): boolean { 
    return this.mySubs.indexOf(sub) >= 0; 
} 

И вы, вероятно, нужна функция, чтобы консолидировать флажки массива выбранных подписки журнала перед отправкой.

Смежные вопросы