4

Is there any built-in functionality in Angular, so that I can say:

remove all FormArray elements except at index 2

maybe something like 'RemoveRange" as known from other libs?

3 Answers3

3

Angular does not have this functionality inbuilt. You can instead store the required value, clear the formArray and then push the stored value back into the now empty formArray

keepOnly(index: number) {
  const valueToKeep = this.formArray.at(index);
  this.formArray.clear();
  this.formArray.push(valueToKeep);
}
nash11
  • 8,220
  • 3
  • 19
  • 55
  • that's indeed my current workaround, but the solution from Athan is very promising,.. –  Aug 12 '19 at 10:33
  • 2
    @Lonely With the solution from Athan your FormArray will lose connection to parent control. In most cases it won't be noticed but for example validations won't be propagated to your main form – yurzui Aug 12 '19 at 10:35
  • dear @nash11, thank you, that's probably the solution today, maybe angular folks integrate someday a built-in possibility for that,.. –  Aug 12 '19 at 10:50
2

Wouldn't something like this work:

formArray = new FormArray([formArray.at(index)]);

Edit:

No, it would not work well because the FormArray will lose connection to parent control as @yurzui said. So @nash11 's answer is the correct one.

As an addition to the accepted answer I would like to point out that in the occasion where someone has subscribed to changes of any deleted member the subscription would still be alive resulting in a memory leak.

Example of the above situation.

Thanos Soulis
  • 583
  • 5
  • 9
  • @Lonely `formArray` is the original FormArray. All I am doing is creating a new FormArray with only the FormControl at the requested `index` of the original FormArray and then overwriting it. – Thanos Soulis Aug 12 '19 at 10:29
  • Would you see the comment from @yurzui, he is right, validation information is gone :/ –  Aug 12 '19 at 10:42
  • @Lonely yes I am looking into it because I was also curious what happens when there are observables subscribed to the formArray – Thanos Soulis Aug 12 '19 at 10:47
  • 1
    @Lonely The now accepted answer is the correct one. You can also see my example on the observables issue I was curious about. – Thanos Soulis Aug 12 '19 at 11:23
1

There is no built-in method in Angular to achieve this. One possibility would be to keep only one array item at itemIndex with slice() and set the FormArray value with the new array after clearing it with the clear() method (available in Angular 8+):

const arrayValue = this.form.get('myArray').value;
this.form.get('myArray').clear();
this.form.get('myArray').push(this.fb.control(arrayValue.slice(itemIndex, itemIndex + 1)[0]));
255kb - Mockoon
  • 6,657
  • 2
  • 22
  • 29
  • Does not that mean deleting the right side of the index? What about the left ones? –  Aug 12 '19 at 09:50
  • This will not work. The array you pass to ````setValue```` should match the structure of the control. – nash11 Aug 12 '19 at 09:56
  • @nash11 True, i updated the answer. @ Lonely, this will get you a slice of the array starting at index and ending at index + 1 (excluded) which gives you on item :) https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/slice – 255kb - Mockoon Aug 12 '19 at 10:19