Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

writeValue function in ControlValueAccessor class called once in angular 2 custom component

there is a custom angular2 component like below:

template

<input class="form-control" id="searchbox" placeholder="شهر" (keyup)="search()" [(ngModel)]="name" autocomplete="off"/>
<div id="searchresult" *ngFor="let city of cities" (click)="cityselected(city)">
    {{city.name}}
</div>

component

        @Component({
        moduleId: module.id,
        selector: 'city-search',
        templateUrl: './city-search.component.html',
        styleUrls: ['./city-search.component.css'],
        providers: [
            {
                provide: NG_VALUE_ACCESSOR,
                useExisting: forwardRef(() => CitySearchComponent),
                multi: true
            }
        ]
    })
    export class CitySearchComponent implements OnInit, ControlValueAccessor{

        cities: Array<City>;
        name: string;
        displaysearchbox: boolean;

        errorMessage: string;

        constructor(private cityService: CityService 
, private helper : Helper) { }

        ngOnInit() {
            this.cities = new Array<City>();
            this.displaysearchbox = false;
        }

        search(): void {
            if (this.name) {              
 this.cityService.
search(this.helper.arabictopersian(this.name))
.subscribe(
                    data => {
                        this.cities = data as Array<City>
                    }
                    , error => this.errorMessage = <any>error);
            }       
        }

        cityselected(city: City): void {
            this.name = city.name;
        }
        writeValue(value: any) {   //just fire once to get the inital value    
            if (value !== undefined) {
                this.name = value; 
            }
            this.propagateChange(this.name);
        }
        propagateChange = (_: any) => { };

        registerOnChange(fn) {
            this.propagateChange = fn;
        }
        registerOnTouched() { }
    }

as it is shown in the code component class implements ControlValueAccessor and here is how i use this:

<form class="form-horizontal">
    <city-search id="bc" name="city" [(ngModel)]="city"></city-search>
    city:{{city}}<!--nothing happens -->
</form>

but custom component has 1-way binding not 2-way binding .. this component gets initial value but does not change based on input changes at all..when I debug it on browser the writeValue function just get fired at loading and after that does not get fired at all.

like image 866
Paridokht Avatar asked Nov 02 '25 01:11

Paridokht


1 Answers

I suppose you should call propagateChange method when you're choosing new value

cityselected(city: any): void {
  this.name = city.name;
  this.propagateChange(this.name); 
}

Plunker Example

So whenever you want to update value for ngControl from ControlValueAccessor you should call function that you set inside registerOnChange method

registerOnChange(fn) {
  this.propagateChange = fn;
}

Usually such method is called onChange function https://github.com/angular/angular/blob/4.2.0-rc.1/packages/forms/src/directives/default_value_accessor.ts#L79

like image 97
yurzui Avatar answered Nov 03 '25 16:11

yurzui



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!