Angular ControlValueAccessor - Documentation | www.HtmlElements.com

Using Angular ControlValueAccessor interface



This topic will go over how to use Smart CheckBox component and use ngModel forms and Reactive Forms.

1. Creating the Component smart-input.component.ts

	import { Component, Input, forwardRef } from '@angular/core';
	import { ControlValueAccessor, NG_VALUE_ACCESSOR, NG_VALIDATORS, FormControl, Validator } from '@angular/forms';

	@Component({
		selector: 'smart-input',
		template:
			`
			<smart-check-box
			  [checked]="value" 
			  (change)="onChange($event)" 
			  (keyup)="onChange($event)">
			
			</smart-check-box>
			`,
		providers: [
		{
		  provide: NG_VALUE_ACCESSOR,
		  useExisting: forwardRef(() => SmartInputComponent),
		  multi: true,
		},
		{
		  provide: NG_VALIDATORS,
		  useExisting: forwardRef(() => SmartInputComponent),
		  multi: true,
		}]        
	})
	export class SmartInputComponent implements ControlValueAccessor, Validator {
		private value: boolean;
		private data: any;

		// this is the initial value set to the component
		public writeValue(obj: any) {
			if (obj) {
				this.data = obj;
				
				this.value = this.data;
			}
		}

		// registers 'fn' that will be fired wheb changes are made
		// this is how we emit the changes back to the form
		public registerOnChange(fn: any) {
			this.propagateChange = fn;
		}

		// validates the form, returns null when valid else the validation object
		// in this case we're checking if the smart parsing has passed or failed from the onChange method
		public validate(c: FormControl) {
			return true;
		}

		// not used, used for touch input
		public registerOnTouched() { }

		// change events from the checkbox
		private onChange(event) {
			// get value from checkbox
			let newValue = event.target.checked;
			this.data = newValue;
			
			// update the form
			this.propagateChange(this.data);
		}

		// the method set in registerOnChange to emit changes back to the form
		private propagateChange = (_: any) => { };
	}
	


2. Creating smart-input.module.ts
	import { FormsModule, ReactiveFormsModule } from '@angular/forms';
	import { CommonModule } from '@angular/common';
	import { NgModule, CUSTOM_ELEMENTS_SCHEMA } from '@angular/core';
	import { SmartInputComponent }   from './smart-input.component';

	@NgModule({
		imports: [
			CommonModule,
			FormsModule,
		],
		schemas: [ CUSTOM_ELEMENTS_SCHEMA ],
	   
		exports: [
			SmartInputComponent,
		],
		declarations: [
			SmartInputComponent,
		],
		providers: [],
	})
	export class SmartInputModule { }
	

3. Creating app.module.ts
	import { NgModule, CUSTOM_ELEMENTS_SCHEMA  } from '@angular/core';
	import { BrowserModule } from '@angular/platform-browser'; 
	import { FormsModule,ReactiveFormsModule } from '@angular/forms';
	import { SmartInputModule } from './smart-input.module';

	import { AppComponent } from './app.component';
	import '@smarthtmlelements/smart-core/source/smart.core.js';

	@NgModule({
		declarations: [AppComponent],
		imports: [BrowserModule, FormsModule, ReactiveFormsModule, SmartInputModule],
		schemas: [ CUSTOM_ELEMENTS_SCHEMA ],
		providers: [],
		bootstrap: [AppComponent]
	})

	export class AppModule { }
			
	

4. Creating app.component.ts
	import { Component, OnInit } from '@angular/core';
	import { FormGroup, FormBuilder } from '@angular/forms';

	export class Hero {
	  id: number;
	  name: string;
	}

	@Component({
	  selector: 'app-root',
	  template: `
	   <h1>NgModel</h1>  
		<form #form="ngForm">  
		 <smart-input [(ngModel)]="result" name="result"></smart-input>  
		</form>  
		<p>form is valid: {{ form.valid ? 'true' : 'false' }}</p>  
		<p>Value:</p>  
		<pre>{{ result}}</pre>  
		<h1>Reactive Form</h1>  
		<form [formGroup]="reactiveForm">  
		 <smart-input formControlName="result"></smart-input>  
		</form>  
		<p>form is valid: {{ reactiveForm.valid ? 'true' : 'false' }}</p>  
		<p>Value:</p>  
		<pre>{{ reactiveForm.value | json}}</pre>  
		`
	})
	export class AppComponent {
	  
	  public result = {};
	  public reactiveForm: FormGroup;
	  
	  constructor(private fb: FormBuilder) {
		this.result = true;
		
		this.reactiveForm = this.fb.group({
		  result: true;
		})
	  }
	}
	

Result:
controlvalueaccessor
Note: In the package.json, you should include a dependency to Smart's npm package. Ex: "@smarthtmlelements/smart-core": "2.0.0"

Download our example from here:

angular-controlvalueaccessor-sample.zip.