Document static method approach
parent
be94a48b8a
commit
babd4e8d92
|
@ -0,0 +1,87 @@
|
|||
# Parent Component Creates Form ; Child Components Define Structure
|
||||
|
||||
Another approach for refactoring a component into child sub-components where the parent component is responsible for creating the entre Reactive Form would be to define static factory methods within each child component rather than within a full-fledged service. As with the [Parent Component Creates Form and Passes Form Controls Into Child Components (Global Form)](../global-form/README.md) approach, the appropriate form controls would be passed into the children.
|
||||
|
||||
In many ways, this approach is a hybrid between the Parent Form and Global Form approaches.
|
||||
|
||||
```typescript
|
||||
export class AppComponent implements OnInit, OnDestroy {
|
||||
contact: Contact;
|
||||
form: FormGroup;
|
||||
|
||||
private subscription: Subscription;
|
||||
|
||||
constructor(private service: ContactService, private fb: FormBuilder) {}
|
||||
|
||||
public ngOnInit() {
|
||||
this.subscription = this.service
|
||||
.loadContact()
|
||||
.subscribe((data: Contact) => {
|
||||
this.contact = data;
|
||||
this.form = this.fb.group({
|
||||
name: NameComponent.buildForm(data.name),
|
||||
addresses: AddressListComponent.buildForm(data.addresses),
|
||||
});
|
||||
});
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
The HTML templating will be identical to the Global Form approach.
|
||||
|
||||
## Static Form Builder Methods
|
||||
|
||||
Rather than having a separate factory service, this approach uses static methods on each of the child sub-classes. This approach intentionally couples the logic for creating a sub-form structure with the component that would display it, keeping the logic in one place rather than separating it between components and an otherwise unrelated service. The rule-of-thumb in this approach is that the component which needs to display the form to a user will best know what the structure of that form needs to be.
|
||||
|
||||
### Name Component
|
||||
|
||||
```typescript
|
||||
static buildForm(name: Name): FormGroup {
|
||||
return new FormGroup({
|
||||
firstName: new FormControl(name ? name.firstName : ''),
|
||||
lastName: new FormControl(name ? name.lastName : ''),
|
||||
middleName: new FormControl(name ? name.middleName : ''),
|
||||
prefix: new FormControl(name ? name.prefix : ''),
|
||||
suffix: new FormControl(name ? name.suffix : ''),
|
||||
});
|
||||
}
|
||||
```
|
||||
|
||||
### Address List Component
|
||||
|
||||
```typescript
|
||||
static buildForm(addresses: Address[]): FormArray {
|
||||
const list: FormArray = new FormArray([]);
|
||||
|
||||
if (addresses) {
|
||||
addresses.forEach(addr => {
|
||||
list.push(AddressComponent.buildForm(addr));
|
||||
});
|
||||
}
|
||||
|
||||
return list;
|
||||
}
|
||||
```
|
||||
|
||||
### Address Component
|
||||
|
||||
```typescript
|
||||
static buildForm(addr: Address): FormGroup {
|
||||
return new FormGroup({
|
||||
line1: new FormControl(addr ? addr.line1 : ''),
|
||||
line2: new FormControl(addr ? addr.line2 : ''),
|
||||
city: new FormControl(addr ? addr.city : ''),
|
||||
state: new FormControl(addr ? addr.state : ''),
|
||||
postalCode: new FormControl(addr ? addr.postalCode : ''),
|
||||
});
|
||||
}
|
||||
```
|
||||
|
||||
## Pros
|
||||
|
||||
- The child components encapsulate the form controls and their display, while keeping the form creation logic separate from the actual template rendering
|
||||
- The child components can easily be re-used
|
||||
|
||||
## Cons
|
||||
|
||||
- The overall shape of the form from the parent component's perspective is not always clear
|
Loading…
Reference in New Issue