Reputation: 38
I'm using Angular 6 with reactive forms, I need to switch form between editable and custom 'readonly' view. There's multiple custom input components in project, so it seems that the easiest way is to use [readOnly] binding on custom-form element. The question is:
How can I get parent's readOnly value inside custom-input component without direct bindings to each of them?
For example:
Template with form
<custom-form formGroup="formGroup" [readOnly]="!(canEdit$ | async)">
<custom-input formControlName="field1"></custom-input>
<custom-input formControlName="field2"></custom-input>
<custom-select formControlName="field3"></custom-select>
...
</custom-form>
Custom input template
// Show input if form readOnly is false
<input *ngIf="!formIsReadOnly"...>
// Show some other representation if not
<span *ngIf="formIsReadOnly">...</span>
Upvotes: 0
Views: 1167
Reputation: 14219
If you don't want to add a readonly
input parameter to your custom controls then you will need a service or an opaque token that each of the controls gets from its constructor to determine if the control will be readonly or not.
For an opaque token you will need to provide a boolean value at the root of the app and then anytime you want to change it you have to re-provide.
If you want to be able to toggle the readonly value on an off you will need to use a service.
readonly.service.ts@Injectable()
export class ReadonlyService {
public readonly = false;
}
readonly.component.ts
@Component({
selector: 'app-readonly',
templateUrl: './readonly.component.html',
providers: [ReadonlyService],
})
export class ReadonlyComponent implements OnInit {
constructor(public readonlyService: ReadonlyService) { }
ngOnInit() {
this.readonlyService.readonly = true;
}
}
customInput.component.ts
@Input() public value: any;
constructor(public readonlyService: ReadonlyService) { }
customInput.component.html
<ng-container *ngIf="!readonlyService.readonly; else readonlyView">
<input placeholder="Enter a value" [(ngModel)]="value">
</ng-container>
<ng-template #readonlyView>
Your readonly value is: {{value}}
</ng-template>
Upvotes: 1