I have written an attribute directive to convert Persian and Arabic numbers to English numbers and I'm using it on many <input>
tags all throughout my forms.
Problem is, sometimes it doesn't convert the last digits to English numbers. I mean, it shows the users that it does (conversion happens realtime because of the keyup event binding) but the information that gets sent to the server is wrong.
Example:
When I use this directive on an input, when the user enters ۱۲۳۴۵۶۷۸۹
in the input field, I expect this directive to change it to 123456789
but it changes it to 12345678۹
or sometimes 123457۸۹
. (missing to convert the last digits)
convert-to-english-numeral.directive.ts:
export class Convert2EnglishNumeralDirective {
constructor(private elRef: ElementRef, private renderer: Renderer2) {}
@HostListener('keyup') keyup() {
const inputVal = this.elRef.nativeElement.value;
this.renderer.setProperty(
this.elRef.nativeElement,
'value',
`${convert2EnglishNumeral(inputVal)}`
);
}
@HostListener('blur') blur() {
const inputVal = this.elRef.nativeElement.value;
this.renderer.setProperty(
this.elRef.nativeElement,
'value',
`${convert2EnglishNumeral(inputVal)}`
);
}
convert2EnglishNumeral(text: any): string {
return text.toString().replace(/[\u0660-\u0669\u06f0-\u06f9]/g, (c) => {
// tslint:disable-next-line: no-bitwise
return c.charCodeAt(0) & 0xf;
});
}
}
Here's how I solved this issue. I'm not sure if it's best practice or not but here it goes:
convert-to-english-numeral.directive.ts:
export class Convert2EnglishNumeralDirective {
constructor(private elRef: ElementRef, private renderer: Renderer2) {}
@HostListener('keyup')
onKeyup() {
const inputVal = this.elRef.nativeElement.value;
this.renderer.setProperty(
this.elRef.nativeElement,
'value',
convert2EnglishNumeral(inputVal)
);
}
@HostListener('input', ['$event'])
onInputChange(event) {
const inputVal = this.elRef.nativeElement.value;
this.renderer.setProperty(
this.elRef.nativeElement,
'value',
convert2EnglishNumeral(inputVal)
);
}
convert2EnglishNumeral(text: any): string {
return text.toString().replace(/[\u0660-\u0669\u06f0-\u06f9]/g, (c) => {
// tslint:disable-next-line: no-bitwise
return c.charCodeAt(0) & 0xf;
});
}
}