I have two components item-list and item . The item-list component display a list of items with checkboxes. I have been trying to push the items to a new Array when checked in the checkbox, but the Array holds only the last item when logged.
Below is the code I tried,
item-list.component.html
<div>
<mat-form-field appearance="outline">
<input matInput placeholder="Add a Task" (keyup.enter)="addTask()"autocomplete="off"[formControl]="nameControl"/>
</mat-form-field>
</div>
<app-item
[value]="value"
*ngFor="let value of data; index as index"
>
</app-item>
item.component.html
<div >
<div >
<mat-checkbox color="secondary" [(ngModel)]="IsChecked" (change)="onChange($event)">
</mat-checkbox>
</div>
</div>
<div >
<div [ngClass]="{ 'line-through': value.task }">
{{ value.task | uppercase }}
</div>
</div>
item.component.Ts
import { Component, EventEmitter, Input, OnInit, Output } from '@angular/core';
@Component({
selector: 'app-item',
templateUrl: './item.component.html',
styleUrls: ['./item.component.scss'],
})
export class ItemComponent implements OnInit {
@Input()
value: any;
IsChecked: boolean;
public ArrayChecked: any[] = [];
constructor() {
this.IsChecked = false;
}
ngOnInit(): void {}
onChange($event: any) {
if ($event.checked) {
this.ArrayChecked.push(this.value.task);
console.log('the task is added', this.ArrayChecked);
}
else console.log('the task is removed');
}
}
In the above code for component item, I tried pushing the items to a new array 'ArrayChecked' inside the onChange(), but when I log the result, the array holds only the last item that I checked. I would like to get the list of all items that were checked in the checkboxes.
Can someone help me fix my code , so all the checked items are inside 'ArrayChecked[]'. Thanks in advance!
CodePudding user response:
The problem here is that ArrayChecked
is initialized in every item
component, which means that each component is only going to push values to its own ArrayChecked
variable. Therefore, only the value of the last checked checkbox is logged.
This can be fixed by initializing ArrayChecked
in the item-list
component instead of the item
component. Then, the item
component should fire an event when its checkbox's value changes with the item's task. You can then listen to this event in item-list
and push the task to ArrayChecked
.
item.component.ts
import { Component, EventEmitter, Input, OnInit, Output } from '@angular/core';
@Component({
selector: 'app-item',
templateUrl: './item.component.html',
styleUrls: ['./item.component.scss'],
})
export class ItemComponent implements OnInit {
@Input()
value: any;
// Emitted when the task is checked
@Output()
checkTask = new EventEmitter<any>;
IsChecked: boolean;
constructor() {
this.IsChecked = false;
}
ngOnInit(): void {}
onChange($event: any) {
if ($event.checked) {
// We now emit the checkTask event instead of directly pushing it to the array
this.checkTask.emit(this.value.task);
console.log('the task is added', this.ArrayChecked);
}
else console.log('the task is removed');
}
}
item-list.component.html
<app-item
[value]="value"
(checkTask)="addCheckedTask($event)"
*ngFor="let value of data; index as index"
>
</app-item>
item-list.component.ts
addCheckedTask($event: any): void {
this.ArrayChecked.push($event);
}