11

I'm using Sematinc-UI and Angular2 ReactiveFormsModule form and i'd like to use [formControl] for select multiple.

If i use select it works with no problems:

        <select class="ui fluid dropdown" [formControl]="myForm.controls.category">
            <option *ngFor="let item of categories" value="{{item}}">{{item}}</option>
        </select>

If i use select multiple it doesn't work:

        <select multiple="" class="ui fluid dropdown" [formControl]="myForm.controls.category">
            <option *ngFor="let item of categories" value="{{item}}">{{item}}</option>
        </select>

I get this error:

core.umd.js:3462 EXCEPTION: Uncaught (in promise): Error: Error in http://localhost:3000/app/components/category.component.js class CategoryComponent - inline template:0:1701 caused by: values.map is not a function

What could be the problem?

smartmouse
  • 13,912
  • 34
  • 100
  • 166
  • What's in `category.component.js` (and `.ts`) where it says that values.map is not a function.? – Alex Szabo Oct 04 '16 at 07:46
  • I have not `values` variable nor in `.js` file nor in `.ts` file. – smartmouse Oct 04 '16 at 07:49
  • I'm finding the same problem. I build the FormBuilder group and when I add `'courseIds': [1,3,5]` (where courseIds is a multiple select) it complains that "this.validator is not a function". If I pass in `'courseIds': {value: [1,3,5]}` I get "values.map is not a function", because it's now been passed the whole object as the value rather than the array. How are you supposed to pass multiple values to the FormControl constructor? – steverippl Oct 21 '16 at 23:46

4 Answers4

9

I got it working. The trick was to make sure that the value is always an array, even when nothing is selected.

<select multiple class="ui fluid dropdown" [formControl]="myForm.controls.category">
    <option *ngFor="let item of categories" [ngValue]="item">{{item}}</option>
</select>

When creating the FormControl make sure the blank value is an empty array, rather than '' or undefined.

this.control = new FormControl([]);

I'm not using Semantic-UI, just standard Angular 2

Daniel Crisp
  • 1,945
  • 1
  • 15
  • 23
1

Working in ionic2 and reactive forms, I was able to validate a multiple select using the validator 'required' only, minlength() did not work. You need to pass null to the model if you want not to pass the validation. Empty array will pass the 'required' validation. A bit weird if you ask me.

Becario Senior
  • 704
  • 10
  • 18
1

I tried Daniel's answers for my ionic project & it works. Here is a sample if anyone is looking

buildForm() {
    this.registerForm = this.formBuilder.group({
      'contact': ['03007654321', [Validators.required]],
      'agree': [true, Validators.requiredTrue],
      'categories': this.formBuilder.array([]),
      'locations': [[], Validators.required],
    });
  }

and in your HTML template use it like this

<ion-item  >
      <ion-label>Gender</ion-label>
      <ion-select multiple="true" [formControl]="registerForm.controls.locations">
        <ion-option value="f">Female</ion-option>
        <ion-option value="m">Male</ion-option>
      </ion-select>
    </ion-item>

Note: I'm using this in ionic on ion-select but I am guessing it'll work with regular HTML select( ) too.

Junaid
  • 4,682
  • 1
  • 34
  • 40
0

Looking at the tests for FormControl (https://github.com/angular/angular/blob/master/modules/%40angular/forms/test/form_control_spec.ts) it's clear that if you pass in an array then the second and subsequent values are treated as validators (hence the first error in my comment above). To pass in an array it has to be "boxed" (within an object), but FormControl expects the "disabled" property in order to use the "value" property as the value, so in the end the right format was 'courseIds': {value: [1,3,5], disabled: false}.

steverippl
  • 378
  • 4
  • 15