Angular 2 ngFor ngModel 复选框在编辑表单中的双向数据绑定

Angular 2 ngFor ngModel Checkboxes Two Way Data Binding In Edit Form

我正在尝试创建一个允许您编辑当前选定任务的表单。表单填充来自所选任务的数据。

我有使用 ngModel 进行双向数据绑定的复选框。

我在 ngFor 上也有复选框,使用 ngModel 进行双向数据绑定。

使用 ngModel 而不使用 ngFor 的复选框的行为符合我的预期。如果复选框发生变化(checked/unchecked),它将重置回按下取消按钮后最初设置的值。

__________MY 问题 IS__________

使用 ngModelngFor 的复选框表现不同。如果复选框发生变化(checked/unchecked),它将保留在点击取消按钮后当前设置的任何值。

我希望它在单击取消按钮时重置其值。

__________QUESTION__________

为什么 ngFor 内的复选框与不在 ngFor 内的复选框的行为不同?

__________CODE BELOW__________

Check Plunker Demo

组件task.component.ts

import { Component, OnInit } from '@angular/core';

@Component({
    selector: 'app-task',
    templateUrl: './task.component.html',
})
export class TaskComponent implements OnInit {

    constructor() {}

    ngOnInit() {
    }

    staffs = [{id: 1, name: 'John', allowed: true, tasks: [] }, {id: 2, name: 'Ana', allowed: true, tasks: [] }];
    tasks = [
        {
            id: 1,
            name: 'Move object with mind',
            duration: 30,
            enablePoint: true,
            enableGodlike: false,
            staffs: [
                {
                    staffId: 1,
                    name: 'John',
                    allowed: true,
                },
                {
                    staffId: 2,
                    name: 'Ana',
                    allowed: true,
                }
            ]
        }
    ];

    id: number;
    name: string;
    enablePoint: boolean;
    enableGodlike: boolean;
    selectedTaskStaffs: any[];
    editTaskState: boolean = false;


    // TASKS
    showEditTaskForm(task) {
        this.id                    = task.id;
        this.name                  = task.name;
        this.enablePoint           = task.enablePoint;
        this.enableGodlike         = task.enableGodlike;
        this.selectedTaskStaffs    = task;
        this.editTaskState         = true;
    }


    editTask() {
        // run edit code here
        this.editTaskState = false;
    }


    closeEditTaskForm() {
        this.editTaskState = false;
    }

}

HTML task.component.html

<!-- EDIT TASK FORM -->
<div *ngIf="
      editTaskState === true"
      class="panel mar-top-4">

    <form (submit)="editTask()">

        <div class="row">
            <div class="small-12 columns">

                <h2 class="text-center mar-tb-2">Edit Task</h2>

                <input
                    [(ngModel)]="enablePoint"
                    name="enablePoint"
                    type="checkbox"
                    id="point">
                    <label for="point">Enable Point (if uncheck, this resets to initial value(true) after cancel)</label>
                <br>
                <input
                    [(ngModel)]="enableGodlike"
                    name="enableGodlike"
                    type="checkbox"
                    id="godlike"><label for="godlike">Enable Godlike (if check, this resets to initial value(false) after cancel)</label>
                <hr>


                <h2 class="text-center mar-tb-2">Staff</h2>
                <div class="row">
                    <div *ngFor="let staff of selectedTaskStaffs.staffs" class="small-6 columns">
                        <label>
                            <input
                            [(ngModel)]="staff.allowed"
                            name="staff{{staff.staffId}}"
                            type="checkbox">
                            {{staff.name}} (if uncheck, this <strong>DOESN'T</strong> resets to initial value(true) after cancel)
                        </label>
                    </div>
                </div>
                <hr>


                <div class="clearfix">
                    <button (click)="deleteTask()" type="button" class="button alert float-left">Delete</button>
                    <button type="submit" class="button float-right">Edit</button>
                    <button (click)="closeEditTaskForm()" type="button" class="button secondary float-right">Cancel</button>
                </div>


            </div>
        </div>
    </form>
</div>



<!-- LIST OF TASKS -->
<div    *ngIf="
            editTaskState === false"
            class="panel">

    <div class="row">
        <div class="small-12 columns">

            <h2 class="mar-top-3">Tasks</h2>

            <table>
                <thead>
                    <tr>
                        <th>Task</th>
                        <th>Duration</th>
                        <th>Point</th>
                        <th>Godlike</th>
                    </tr>
                </thead>
                <tbody>
                    <tr (click)="showEditTaskForm(task)" *ngFor="let task of tasks">
                        <td>{{task.name}} (click to edit)</td>
                        <td>{{task.duration}}</td>
                        <td>{{task.enablePoint}}</td>
                        <td>{{task.enableGodlike}}</td>
                    </tr>
                </tbody>
            </table>

        </div>
    </div>

</div>

Why do checkboxes inside ngFor behave differently then checkboxes not inside ngFor?

简而言之,这是因为没有 ngFor 的复选框使用不可变原始 (bool) 值

this.enablePoint = task.enablePoint;
this.enableGodlike = task.enableGodlike;

ngFor 中操作可变对象引用:

this.selectedTaskStaffs = task;

如果您在 selectedTaskStaffs 内更改 属性,那么您的 task 也会更改