Reputation: 1689
I work on angular 4, I have list of checkbox which on page load will be unchecked. There is a delete button which will be enabled when any checkbox is checked.
hero.component.html
<div *ngFor="let hero of heros">
<span>
<input type='checkbox' name='drama' (click)='selectedHero()' />
</span>
<span>hero.name</span>
</div>
<button [class.disabled]='!inEditMode'>Delete</button>
hero.component.ts
private inEditMode = false;
selectedHero(){
var elements = document.getElementsByName("drama");
for (let i = 0; i < elements.length; i++) {
if (elements[i].type == "checkbox") {
if (elements[i].checked) {
this.inEditMode = true;
}
else {
this.inEditMode = false;
}
}
}
}
I am getting error in .type
and .checked
.
Error is
Property 'type' doesnot exist on type 'HTMLElement
Property 'checked' doesnot exist on type 'HTMLElement.
How can I iterate over the checkboxes to see if any on them is checked, and if checked enable the button. And if not checked disabled the button? Please guide
Upvotes: 1
Views: 6311
Reputation: 1211
Add one extra property in Hero model like, IsSelected and bind it with every check-boxes
selectedHero() {
var data = this.heroes.find((obj: Hero) => obj.IsSelected === true);
if (data) {
this.inEditMode = true;
} else {
this.inEditMode = false;
}
}
<div *ngFor="let hero of heros">
<span>
<input type='checkbox' value="{{hero.IsSelected}}" [(ngModel)]="hero.IsSelected" name='IsSelected' (change)='selectedHero()'/> />
</span>
<span>hero.name</span>
</div>
<button [class.disabled]='!inEditMode'>Delete</button>
Upvotes: 0
Reputation: 2986
Your code is working fine, but your for loop in typescript sometime works and sometime fails because of for loop.
in your html : <button [disabled]='!inEditMode'>Delete</button>
In your typescript:
selectedHero() {
var elements = (<HTMLInputElement[]><any>document.getElementsByName("drama"));
for (let i = 0; i < elements.length; i++) {
if (elements[i].type == "checkbox") {
if (elements[i].checked) {
console.log("Checked", elements[i].checked);
this.inEditMode = true;
break; //<== Add this line in your for loop
}
else {
console.log("Unchecked", elements[i].checked);
this.inEditMode = false;
}
}
}
}
When for loop starts until all elements has to be check you have to break the for loop when atleast one checkbox is checked.
Here is working example: Enable Button on mutiple check box selection
Hope this will works for you!!!
Upvotes: 1
Reputation: 1339
When working with checkboxes, I create an array of checkboxes and in that array, I keep all (in your case id of heroes) checked checkboxes. If array is empty, you disable your button, and if array has at least one member, you enable button. Also when you want to check which checkboxes are checked, you simply itterate through an array of checkboxes.
checkarray: any = [];
To check is checkbox checked:
isChecked(item: any): boolean {
if (this.checkarray.find(x => x.IDHero == item.IDHero)) {
return true;
}
else {
return false;
}
}
To delete member from array:
deletefromArray(array: any, element: any, id: string) {
let temp: any = [];
for (let i = 0; i < array.length; i++) {
temp.push(array[i]);
}
array.splice(0);
for (let i = 0; i < temp.length; i++) {
if (temp[i][id] != element[id]) {
array.push(temp[i]);
}
}
return array;
}
To add checked checkboxes to array:
checkbox(item: IDK, event) {
if (event.ctrlKey) {
if (this.checkarray.find(x => x.IDHero == item.IDHero)) {
this.deleteFromArray(this.checkarray, item, 'IDHero');
let temp: any = [];
for (let i = 0; i < this.checkarray.length; i++) {
temp.push(this.checkarray[i]);
}
this.checkarray.splice(0);
for (let i = 0; i < temp.length; i++) {
if (temp[i].IDHero != item.IDHero) {
this.checkarray.push(temp[i]);
}
}
}
else {
this.checkarray.push(item);
}
}
else {
if (!this.checkarray.find(x => x.IDHero == item.IDHero)) {
this.checkarray.splice(0);
this.checkarray.push(item);
} else {
this.checkarray.splice(0);
}
}
}
I use CTRL
for multy check.
HTML would be:
<div *ngFor="let hero of heros" (click)="checkbox(hero,$event)>
<span><input type='checkbox' name='drama' [checked]="isChecked(hero)"/></span>
<span>hero.name</span>
<button [disabled]='checkarray.length == 0'>Delete</button>
Upvotes: 0
Reputation: 4692
Your approach is not wrong.
Try typecasting it with
var elements = (<HTMLInputElement[]><any>document.getElementsByName('drama'));
alternative try using ngModel, it makes your life easier.
<input [(ngModel)]="checkBox.option1" type="checkbox" data-toggle="toggle">Option
<input [(ngModel)]="checkBox.option2" type="checkbox" data-toggle="toggle">Option
<button [disabled]='checkBox.option1 || checkBox.option2'>Delete</button>
app.component.ts
checkBox:any{};
constructor(){
checkBox={
option1:false,
option2:false
};
}
optionChecked becomes true when checked thus disabling the button
Upvotes: 0
Reputation: 1243
your elements[i] is a HTMLElement, typecast it to HTMLInputElement.
Checked property will be there for HTMLInputElement in typescript.
Below should work.
for(let i=0;i<elements.length;i++){
if((elements[i] as HTMLInputElement).type == "checkbox"){
if((elements[i] as HTMLInputElement).checked){
this.inEditMode = true;
}
Upvotes: 0
Reputation: 2166
Try with .
The problem is that typescript is typesafe. The elements[i] holds the type HTMLElement which does not contain a type property. The subtype HTMLInputElement does however contain the type property.
selectedHero(){
var elements = document.getElementsByName("drama");
for(let i=0;i<elements.length;i++){
var element = <HTMLInputElement>elements[i];
if(element.type == "checkbox"){
if(element.checked){
this.inEditMode = true;
}
else{
this.inEditMode = false;
}
}
}
}
Upvotes: 0
Reputation: 452
You have to cast the result of getElementsByName("drama");
like this:
var elements = (<HTMLInputElement[]><any>document.getElementsByName('drama'));
as document.getElementsByName() returns the type HTMLElement
Upvotes: 0