Quiero cambiar (forzar) los valores de los campos de entrada mientras escribo usando una directiva de atributos. Con él, me gustaría crear directivas como mayúsculas, minúsculas, maxlength, filterchar, etc. para usar en campos de entrada en formularios. Encontré este ejemplo: Ejemplo de mecanografiado de directiva de atributo angular 2 pero esto no parece funcionar. Tal vez lo hizo para una versión anterior de Angular2. Sin embargo, es exactamente lo que me gustaría hacer.
Cuando creo una directiva como esta:
import {Directive} from 'angular2/core'; import {NgModel} from 'angular2/common'; @Directive({ selector: '[ngModel][uppercase]', host: { '(input)' : 'onInputChange()' } }) export class UppercaseDirective{ constructor(public model:NgModel){} onInputChange(){ var newValue = this.model.value.toUpperCase(); this.model.valueAccessor.writeValue(newValue); this.model.viewToModelUpdate(newValue); } }Y úsalo en un formulario como este:
<input type="text" class="form-control" [(ngModel)]="field.name" ngControl="name" #name="ngForm" required uppercase> (y registrar NgModel como proveedor). obtengo un
undefined this.model.value.
Puedo usar $event.target.value = $event.target.value.toUpperCase() (al pasar $event con onInputChange() ) y eso funciona para la vista (muestra la entrada en mayúsculas. Pero no t actualice el campo de vinculación "field.name".
Entonces, ¿cómo crear una directiva de atributo Angular2 que haga esto?
-- EDITAR --
Después de investigar un poco más, logré obtener lo que quería. La respuesta que dio Günter está más cerca de mi intención original y quizás mejor. Pero aquí hay otra manera:
import {Directive, Input, Output, EventEmitter} from 'angular2/core'; @Directive({ selector: '[ngModel][uppercase]', host: { "(input)": 'onInputChange($event)' } }) export class UppercaseDirective{ @Output() ngModelChange:EventEmitter<any> = new EventEmitter() value: any onInputChange($event){ this.value = $event.target.value.toUpperCase() this.ngModelChange.emit(this.value) } }Como dije, no estoy seguro de si esta también es una buena manera de hacer esto, por lo que los comentarios son bienvenidos.
Aunque la respuesta de Günter parece prometedora, hay un error en el sentido de que el valor final en el modelo tiene la última letra ingresada en minúsculas.
Mira aquí:
https://plnkr.co/edit/SzxO2Ykg2pKq1qfgKVMH
Utilice la respuesta proporcionada en la pregunta. Funciona correctamente.
@Directive({ selector: '[ngModel][uppercase]', host: { "(input)": 'onInputChange($event)' } }) export class UppercaseDirective{ @Output() ngModelChange:EventEmitter<any> = new EventEmitter() value: any onInputChange($event){ this.value = $event.target.value.toUpperCase() this.ngModelChange.emit(this.value) } }actualizar
Este enfoque no funciona correctamente. Consulte la respuesta de @RyanHow para obtener una mejor solución.
original
@Directive({ selector: '[ngModel][uppercase]', providers: [NgModel], host: { '(ngModelChange)' : 'onInputChange($event)' } }) export class UppercaseDirective{ constructor(private model:NgModel){} onInputChange(event){ this.model.valueAccessor.writeValue(event.toUpperCase()); } }Me he enfrentado al mismo problema, donde necesito crear la selección personalizada en Angular con select2 . He creado la siguiente directiva para lograr esto con la directiva de atributos y ngModel .
import {ElementRef, Directive, EventEmitter, Output, Input} from '@angular/core'; import {NgModel} from "@angular/forms"; declare let $; @Directive({ selector: '[custom-select]', providers: [NgModel] }) export class CustomSelectComponent{ $eventSelect:any; @Output() ngModelChange:EventEmitter<any> = new EventEmitter(); @Input() set ngModel(value:any){ //listen to the input value change of ngModel and change in the plugin accordingly. if(this.$eventSelect){ this.$eventSelect.val(value).trigger('change',{fromComponent:true}); } } constructor(private elementRef: ElementRef) {} ngOnInit(){ this.$eventSelect = $(this.elementRef.nativeElement); this.$eventSelect.select2({minimumResultsForSearch:-1}); this.$eventSelect.on("change.select2", (event,data)=> { //listen to the select change event and chanage the model value if(!data || !data.fromComponent){ //dont change model when its chagned from the input change event this.ngModelChange.emit(this.$eventSelect.val()); } }); } }con el siguiente uso
<select custom-select [(ngModel)]="protocol.type"> <option value="1">option1</option> <option value="1">option2</option> </select>