0

I am using angular 5 and in the html file i need to validate a checkbox to make sure user checks atleast one box. I am able to get an error but not in the way I require. Currently with the below code I am getting an error message after every checkbox option, but I require just one message after all the boxes.

<div class="form-group">

   <label for="options">Categories:</label>

     <label class = "control-label">

       <div *ngFor="let category of initialCategories">

         <input class = "form-control" type="checkbox" 
               name="categories" #categories="ngModel" value=" 
               {{category.name}}" [(ngModel)]="category.checked" 
               required/> {{category.name}}

               <div [hidden]="categories.valid || categories.pristine 
               ||!categories.dirty">
                    Please select at least one option.  
                </div>

       </div>

      </label>

</div>

If I put the div to show error outside the ngFor div then it will show not found error since its outside the loop.

1
  • I deleted and undeleted an answer, so you won't be notified, but please check my answer if it would suit your needs :) Commented Mar 27, 2018 at 10:52

1 Answer 1

2

We cannot see if you are using the NgForm directive here, but if you aren't using it, use it.

Currently, what you have is just one form control for your whole array, you would want to have a form control for each value. So what we will do is add a dynamic name, achieved by using the index of the iteration.

We can attach a change event on the checkboxes, and whenever a checkbox is clicked, we check if at least one is checked. If not, we set a custom error to the form.

Remove required from the template of the checkboxes, import NgForm and ViewChild so that we can refer to our form when we want to set the custom error. So modify your template to:

<form #myForm="ngForm">
  <label for="options">Categories:</label>
    <label>
    <div *ngFor="let category of initialCategories; let i = index" >
      <input type="checkbox" name="categories{{i}}" #categories="ngModel" value="{{category.name}}" [(ngModel)]="category.checked" (change)="checkValidity()"/> {{category.name}}
    </div>
    </label>
    <div [hidden]="!myForm?.errors?.notValid">
        Please select at least one option.
    </div>
</form>

and the TS file:

@ViewChild('myForm') myForm: NgForm;

checkValidity() {
  let valid = this.initialCategories.some(x => x.checked === true);
  if (valid) {
    this.myForm.form.setErrors(null);
  } else {
    this.myForm.form.setErrors({notValid: true});
  }
}

You would also probably want to set the custom error initially, so you can do it in OnInit if you like.

Here's a StackBlitz demostrating the above code.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.