Reputation: 153
Lets say i have a checkbox and each checkbox has a categoryId. When i check the checkbox i will get the categoryId and each data will be save as a formArray, example at index 0: 1,1:2,2:4,3:[6] . So this is the data i currently get but my question is instead of storing the data at different index number i want to get the result as index 0:["1,3,4,6"] as array of string. I want to store the data only in index 0 in other words i want to store all the checkbox categoryId only in one index as a string. I'll share my code below. This is the code that i used to get the categoryId from checkbox
onChange(categoryId: string[], isChecked: boolean) {
debugger
const categoryIdArray = (this.patientReportForm.controls.hubxCategoryId as FormArray);
if (isChecked) {
categoryIdArray.push(new FormControl(categoryId))
} else {
let index = categoryIdArray.controls.findIndex(x => x.value == categoryId)
categoryIdArray.removeAt(index);
}
}
This is formcontrol
this.patientReportForm = this.formBuilder.group({
patientId : new FormControl(Number(this.clientId)),
hubxCategoryId : this.formBuilder.array([]),
notes : new FormControl(),
})
this is my html section for checkbox
<div *ngFor="let hubxReport of hubxReportList; let i=index">
<div class="lineheader ">
<section class="" [formGroup]="patientReportForm">
<p><mat-checkbox color="primary" (change)="onChange(hubxReport.categoryId, $event.checked)">{{hubxReport.categoryName}}</mat-checkbox></p>
</section>
</div>
this is the data i currently get
and this is the result i want to get
my final result here patientid is null. Below i'm assigning patientid : this.clientid. when i debug and i check it, this.clientid carries a value 40.But when i submit patientid shows null
patientReportForm=this.getGroup({patientId : this.clientId ,hubxCategoryId:"",notes:""})
here this.clientid carries value 40.
Upvotes: 0
Views: 260
Reputation: 57939
convertValue(){
const values = this.form.get('hubxCategoryId').value;
//values is an array [true,true,false,...]
return this.hubxReport
//filter gets [{hubxCategoryId:2,categoryName:".."},
// {hubxCategoryId:6,categoryName:".."},..]
.filter((x, index) => values[index])
//maps return only the "Id" [2,6,...]
.map(x=>x.hubxCategoryId)
//join return an string "2,6,..."
.join(",")
}
But take a look to this SO, you not create a FormArray else a FormControl that store an array
Update step by step
Imagine you has
hubxReportList=[{hubxCategoryId:1,categoryName:'Marka'},
{hubxCategoryId:2,categoryName:'Kilometraza'},
{hubxCategoryId:3,categoryName:'Alu felne'}]
You can to have a function like
getGroup(data:any=null)
{
data=data || {patienID:0,hubxCategoryId :"",notes:""}
const list=data.hubxCategoryId?data.hubxCategoryId.split(',').map(x=>+x):[]
return new FormGroup({
patienID:new FormControl<number>(data.patienID),
hubxCategoryId :new FormArray(this.hubxReportList.map(x=>new FormControl(list.indexOf(x.hubxCategoryId)>0))),
notes:new FormControl<string>(data.notes)
})
}
//and use
patientReportForm2=this.getGroup(
{patienID:0,hubxCategoryId:"1,3",notes:""})
//or
patientReportForm2=this.getGroup()
As always we have a FormArray we use a getter
get hubxCategoryIdArray()
{
return this.patientReportForm2.get('hubxCategoryId') as FormArray
}
And the .html
<form [formGroup]="patientReportForm" (submit)="submit(patientReportForm)">
<div class="lineheader" formArrayName="hubxCategoryId">
<section
class=""
*ngFor="let control of hubxCategoryIdArray.controls; let i = index"
>
<p>
<input type="checkbox" color="primary" [formControlName]="i" />
{{ hubxReportList[i].categoryName }}
</p>
</section>
</div>
<button>submit</button>
</form>
The function submit like
submit(form:FormGroup)
{
if (form.valid)
{
const data:any={...form.value};
data.hubxCategoryId=this.hubxReportList
.filter((x, index) => form.value.hubxCategoryId[index])
.map(x=>x.hubxCategoryId)
.join(",")
console.log(data)
}
}
Another option is really use a FormControl, not a FormArray that store an string separated by commas
getGroup(data:any=null)
{
data=data || {patienID:0,hubxCategoryId :"",notes:""}
return new FormGroup({
patienID:new FormControl(data.patienID),
hubxCategoryId :new FormControl(data.hubxCategoryId ),
notes:new FormControl(data.notes)
})
}
We use ngModel inside a FormGroup
<div *ngFor="let hubxReport of hubxReportList; let i = index">
<div class="lineheader">
<section class="">
<p>
<input
type="checkbox"
color="primary"
[ngModel]="
(patientReportForm.get('hubxCategoryId')?.value || [])
.split(',').indexOf(
'' + hubxReport.hubxCategoryId
) >= 0
"
(ngModelChange)="onChange(hubxReport.hubxCategoryId, $event)"
[ngModelOptions]="{ standalone: true }"
/>
{{ hubxReport.categoryName }}
</p>
</section>
</div>
</div>
And the function onChange
onChange(categoryId:any,checked:boolean)
{
let newValue:string
const oldValue:string=this.patientReportForm.get('hubxCategoryId').value
const oldArray=oldValue?oldValue.split(',').map(x=>+x):[]
if (checked)
newValue=this.hubxReportList
.filter((x) => x.hubxCategoryId==categoryId || oldArray.indexOf(x.hubxCategoryId)>=0)
.map(x=>x.hubxCategoryId)
.join(",")
else
newValue=this.hubxReportList
.filter((x) => x.hubxCategoryId!=categoryId && oldArray.indexOf(x.hubxCategoryId)>=0)
.map(x=>x.hubxCategoryId)
.join(",")
console.log(oldArray,newValue)
this.patientReportForm.get('hubxCategoryId').setValue(newValue)
}
onChange(categoryId:any,checked:boolean)
{
let newValue:string
const oldValue:string=this.patientReportForm.get('hubxCategoryId').value
const oldArray=oldValue?oldValue.split(',').map(x=>+x):[]
if (checked)
newValue=this.hubxReportList
.filter((x) => x.hubxCategoryId==categoryId || oldArray.find(y=>y==x.hubxCategoryId))
.map(x=>x.hubxCategoryId)
.join(",")
else
newValue=this.hubxReportList
.filter((x) => x.hubxCategoryId!=categoryId && oldArray.find(y=>y==x.hubxCategoryId))
.map(x=>x.hubxCategoryId)
.join(",")
this.patientReportForm.get('hubxCategoryId').setValue(newValue)
}
In this case we needn't make anything in submit
You can see in the stackblitz both case
BONUS: we can create a custom form control like the link I indicate, in this stackblitz is improve the code to mannage an string separated by commas
Upvotes: 2
Reputation: 412
Try this: let desiredFormat= this.patientReportForm.value.hubxCategoryId.join(",")
Upvotes: 0