我已经声明了一种将大数字分成三位数的格式,并经常这样使用。
<div>Huge number: {{ i_am_huge | make_threesome }}</div>
现在,存在对相应功能的请求,但需要在这样的输入控件中实现。
<input id="numeroUno"
type="text">
我能想到的方法是听打字,并为每个键重新格式化盒子的内容。
<input id="numeroUno"
type="text"
(keyup)="formatify">
但是,尽管这种方法行得通,但我不禁怀疑它是否涉及过多的Q&D,因此,在围绕这种范例构建整个控制动物群之前,我想了解更多信息。
通常的谷歌搜索并没有给我太多。但是,由于要求的性质非常特殊,因此可能很难找到。
此时的假设是,不应以这种方式使用输入控制,这说明了我方法的笨拙。
答案 0 :(得分:2)
使用指令。在stackblitz中,您可以看到工作原理。
指令在变量“值”中存储不带空格的字符串。每次发生更改时(我使用@HotListener(input)),获取光标的位置,获取元素的值,删除空格,添加数字并将光标放在该位置
@Directive({ selector: "[testPipe]" })
export class TestPipe implements OnInit {
private el: HTMLInputElement;
private value: any;
constructor(@Optional() private ngControl:NgControl,
private elementRef: ElementRef) {
this.el = this.elementRef.nativeElement;
}
@HostListener("input", ["$event.target.value"])
onInput() {
let pos = this.el.selectionStart; //get the position of the cursor
this.value = this.el.value.replace(/ /gi, ""); //store the value without spaces
if (this.value.length%3==1) //If we must add an extra space
pos++;
//Yes, it's a "bizarro" way to separate in group of three
this.el.value=this.value.match(/(.+?)(?=(.{3})+(?!.)|$)/g).join(' ');
//this.el.value=this.value.match(/(\d+?)(?=(\d{3})+(?!\d)|$)/g).join(' ');
//Finally give the position of cursor
this.el.selectionStart = this.el.selectionEnd = pos;
if (this.ngControl)
this.ngControl.control.setValue(this.el.value,{emit:false})
}
ngOnInit()
{
this.value = this.el.value.replace(/ /gi, "");
this.el.value=this.value.match(/(.+?)(?=(.{3})+(?!.)|$)/g).join(' ');
// this.el.value=this.value.match(/(\d+?)(?=(\d{3})+(?!\d)|$)/g).join(' ');
if (this.ngControl)
this.ngControl.control.setValue(this.el.value,{emit:false})
}
}
更新,我在构造函数中添加了@Optional()ngControl:NgControl,因此,如果将指令应用于ngControl(输入属于formGroup或具有[(ngModel)],也要更改值
答案 1 :(得分:1)
我认为您应该在此处使用(attribute) directive。您可以将指令用于验证目的,所以为什么不使用它在输入字段中进行格式化(实际上,目前正在尝试在我自己的项目中执行类似的操作)。
基本上看起来像这样(例如来自角度文档的示例):
import { Directive, ElementRef, HostListener, Input } from '@angular/core';
@Directive({
selector: '[appHighlight]'
})
export class HighlightDirective {
constructor(private el: ElementRef) { }
@Input('appHighlight') highlightColor: string;
@HostListener('mouseenter') onMouseEnter() {
this.highlight(this.highlightColor || 'red');
}
@HostListener('mouseleave') onMouseLeave() {
this.highlight(null);
}
private highlight(color: string) {
this.el.nativeElement.style.backgroundColor = color;
}
}
这样,您可以在输入字段内操作值,并侦听click
之类的事件。
在生效之前,您还必须做一件事:将伪指令(非常类似于[ngStyle]
或[ngClass]
)添加到通过[your-directives-name]
提交的输入中。查看以下代码段及其完成方式:
<h1>My First Attribute Directive</h1>
<h4>Pick a highlight color</h4>
<div>
<input type="radio" name="colors" (click)="color='lightgreen'">Green
<input type="radio" name="colors" (click)="color='yellow'">Yellow
<input type="radio" name="colors" (click)="color='cyan'">Cyan
</div>
<p [appHighlight]="color">Highlight me!</p>