UNPKG

ng-zorro-antd

Version:

An enterprise-class UI components based on Ant Design and Angular

519 lines (513 loc) 20.7 kB
import { __decorate } from 'tslib'; import { UP_ARROW, DOWN_ARROW, ENTER } from '@angular/cdk/keycodes'; import * as i0 from '@angular/core'; import { EventEmitter, forwardRef, Component, ChangeDetectionStrategy, ViewEncapsulation, Optional, Output, ViewChild, Input, NgModule } from '@angular/core'; import * as i4 from '@angular/forms'; import { NG_VALUE_ACCESSOR, FormsModule } from '@angular/forms'; import { Subject, fromEvent } from 'rxjs'; import { takeUntil } from 'rxjs/operators'; import { isNotNil, InputBoolean } from 'ng-zorro-antd/core/util'; import * as i1 from '@angular/cdk/a11y'; import * as i2 from '@angular/cdk/bidi'; import { BidiModule } from '@angular/cdk/bidi'; import * as i3 from 'ng-zorro-antd/icon'; import { NzIconModule } from 'ng-zorro-antd/icon'; import { CommonModule } from '@angular/common'; class NzInputNumberComponent { constructor(ngZone, elementRef, cdr, focusMonitor, directionality) { this.ngZone = ngZone; this.elementRef = elementRef; this.cdr = cdr; this.focusMonitor = focusMonitor; this.directionality = directionality; this.destroy$ = new Subject(); this.isFocused = false; this.disabledUp = false; this.disabledDown = false; this.dir = 'ltr'; this.onChange = () => { }; this.onTouched = () => { }; this.nzBlur = new EventEmitter(); this.nzFocus = new EventEmitter(); this.nzSize = 'default'; this.nzMin = -Infinity; this.nzMax = Infinity; this.nzParser = (value) => value .trim() .replace(/。/g, '.') .replace(/[^\w\.-]+/g, ''); this.nzPrecisionMode = 'toFixed'; this.nzPlaceHolder = ''; this.nzStep = 1; this.nzInputMode = 'decimal'; this.nzId = null; this.nzDisabled = false; this.nzAutoFocus = false; this.nzFormatter = value => value; } onModelChange(value) { this.parsedValue = this.nzParser(value); this.inputElement.nativeElement.value = `${this.parsedValue}`; const validValue = this.getCurrentValidValue(this.parsedValue); this.setValue(validValue); } getCurrentValidValue(value) { let val = value; if (val === '') { val = ''; } else if (!this.isNotCompleteNumber(val)) { val = `${this.getValidValue(val)}`; } else { val = this.value; } return this.toNumber(val); } // '1.' '1x' 'xx' '' => are not complete numbers isNotCompleteNumber(num) { return (isNaN(num) || num === '' || num === null || !!(num && num.toString().indexOf('.') === num.toString().length - 1)); } getValidValue(value) { let val = parseFloat(value); // https://github.com/ant-design/ant-design/issues/7358 if (isNaN(val)) { return value; } if (val < this.nzMin) { val = this.nzMin; } if (val > this.nzMax) { val = this.nzMax; } return val; } toNumber(num) { if (this.isNotCompleteNumber(num)) { return num; } const numStr = String(num); if (numStr.indexOf('.') >= 0 && isNotNil(this.nzPrecision)) { if (typeof this.nzPrecisionMode === 'function') { return this.nzPrecisionMode(num, this.nzPrecision); } else if (this.nzPrecisionMode === 'cut') { const numSplit = numStr.split('.'); numSplit[1] = numSplit[1].slice(0, this.nzPrecision); return Number(numSplit.join('.')); } return Number(Number(num).toFixed(this.nzPrecision)); } return Number(num); } getRatio(e) { let ratio = 1; if (e.metaKey || e.ctrlKey) { ratio = 0.1; } else if (e.shiftKey) { ratio = 10; } return ratio; } down(e, ratio) { if (!this.isFocused) { this.focus(); } this.step('down', e, ratio); } up(e, ratio) { if (!this.isFocused) { this.focus(); } this.step('up', e, ratio); } getPrecision(value) { const valueString = value.toString(); if (valueString.indexOf('e-') >= 0) { return parseInt(valueString.slice(valueString.indexOf('e-') + 2), 10); } let precision = 0; if (valueString.indexOf('.') >= 0) { precision = valueString.length - valueString.indexOf('.') - 1; } return precision; } // step={1.0} value={1.51} // press + // then value should be 2.51, rather than 2.5 // if this.props.precision is undefined // https://github.com/react-component/input-number/issues/39 getMaxPrecision(currentValue, ratio) { if (isNotNil(this.nzPrecision)) { return this.nzPrecision; } const ratioPrecision = this.getPrecision(ratio); const stepPrecision = this.getPrecision(this.nzStep); const currentValuePrecision = this.getPrecision(currentValue); if (!currentValue) { return ratioPrecision + stepPrecision; } return Math.max(currentValuePrecision, ratioPrecision + stepPrecision); } getPrecisionFactor(currentValue, ratio) { const precision = this.getMaxPrecision(currentValue, ratio); return Math.pow(10, precision); } upStep(val, rat) { const precisionFactor = this.getPrecisionFactor(val, rat); const precision = Math.abs(this.getMaxPrecision(val, rat)); let result; if (typeof val === 'number') { result = ((precisionFactor * val + precisionFactor * this.nzStep * rat) / precisionFactor).toFixed(precision); } else { result = this.nzMin === -Infinity ? this.nzStep : this.nzMin; } return this.toNumber(result); } downStep(val, rat) { const precisionFactor = this.getPrecisionFactor(val, rat); const precision = Math.abs(this.getMaxPrecision(val, rat)); let result; if (typeof val === 'number') { result = ((precisionFactor * val - precisionFactor * this.nzStep * rat) / precisionFactor).toFixed(precision); } else { result = this.nzMin === -Infinity ? -this.nzStep : this.nzMin; } return this.toNumber(result); } step(type, e, ratio = 1) { this.stop(); e.preventDefault(); if (this.nzDisabled) { return; } const value = this.getCurrentValidValue(this.parsedValue) || 0; let val = 0; if (type === 'up') { val = this.upStep(value, ratio); } else if (type === 'down') { val = this.downStep(value, ratio); } const outOfRange = val > this.nzMax || val < this.nzMin; if (val > this.nzMax) { val = this.nzMax; } else if (val < this.nzMin) { val = this.nzMin; } this.setValue(val); this.updateDisplayValue(val); this.isFocused = true; if (outOfRange) { return; } this.autoStepTimer = setTimeout(() => { this[type](e, ratio); }, 300); } stop() { if (this.autoStepTimer) { clearTimeout(this.autoStepTimer); } } setValue(value) { if (`${this.value}` !== `${value}`) { this.onChange(value); } this.value = value; this.parsedValue = value; this.disabledUp = this.disabledDown = false; if (value || value === 0) { const val = Number(value); if (val >= this.nzMax) { this.disabledUp = true; } if (val <= this.nzMin) { this.disabledDown = true; } } } updateDisplayValue(value) { const displayValue = isNotNil(this.nzFormatter(value)) ? this.nzFormatter(value) : ''; this.displayValue = displayValue; this.inputElement.nativeElement.value = `${displayValue}`; } writeValue(value) { this.value = value; this.setValue(value); this.updateDisplayValue(value); this.cdr.markForCheck(); } registerOnChange(fn) { this.onChange = fn; } registerOnTouched(fn) { this.onTouched = fn; } setDisabledState(disabled) { this.nzDisabled = disabled; this.cdr.markForCheck(); } focus() { this.focusMonitor.focusVia(this.inputElement, 'keyboard'); } blur() { this.inputElement.nativeElement.blur(); } ngOnInit() { this.focusMonitor .monitor(this.elementRef, true) .pipe(takeUntil(this.destroy$)) .subscribe(focusOrigin => { if (!focusOrigin) { this.isFocused = false; this.updateDisplayValue(this.value); this.nzBlur.emit(); Promise.resolve().then(() => this.onTouched()); } else { this.isFocused = true; this.nzFocus.emit(); } }); this.dir = this.directionality.value; this.directionality.change.pipe(takeUntil(this.destroy$)).subscribe((direction) => { this.dir = direction; }); this.ngZone.runOutsideAngular(() => { fromEvent(this.inputElement.nativeElement, 'keyup') .pipe(takeUntil(this.destroy$)) .subscribe(() => this.stop()); fromEvent(this.inputElement.nativeElement, 'keydown') .pipe(takeUntil(this.destroy$)) .subscribe(event => { const { keyCode } = event; if (keyCode !== UP_ARROW && keyCode !== DOWN_ARROW && keyCode !== ENTER) { return; } this.ngZone.run(() => { if (keyCode === UP_ARROW) { const ratio = this.getRatio(event); this.up(event, ratio); this.stop(); } else if (keyCode === DOWN_ARROW) { const ratio = this.getRatio(event); this.down(event, ratio); this.stop(); } else { this.updateDisplayValue(this.value); } this.cdr.markForCheck(); }); }); }); } ngOnChanges(changes) { if (changes.nzFormatter && !changes.nzFormatter.isFirstChange()) { const validValue = this.getCurrentValidValue(this.parsedValue); this.setValue(validValue); this.updateDisplayValue(validValue); } } ngAfterViewInit() { if (this.nzAutoFocus) { this.focus(); } } ngOnDestroy() { this.focusMonitor.stopMonitoring(this.elementRef); this.destroy$.next(); this.destroy$.complete(); } } NzInputNumberComponent.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "13.2.5", ngImport: i0, type: NzInputNumberComponent, deps: [{ token: i0.NgZone }, { token: i0.ElementRef }, { token: i0.ChangeDetectorRef }, { token: i1.FocusMonitor }, { token: i2.Directionality, optional: true }], target: i0.ɵɵFactoryTarget.Component }); NzInputNumberComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "12.0.0", version: "13.2.5", type: NzInputNumberComponent, selector: "nz-input-number", inputs: { nzSize: "nzSize", nzMin: "nzMin", nzMax: "nzMax", nzParser: "nzParser", nzPrecision: "nzPrecision", nzPrecisionMode: "nzPrecisionMode", nzPlaceHolder: "nzPlaceHolder", nzStep: "nzStep", nzInputMode: "nzInputMode", nzId: "nzId", nzDisabled: "nzDisabled", nzAutoFocus: "nzAutoFocus", nzFormatter: "nzFormatter" }, outputs: { nzBlur: "nzBlur", nzFocus: "nzFocus" }, host: { properties: { "class.ant-input-number-focused": "isFocused", "class.ant-input-number-lg": "nzSize === 'large'", "class.ant-input-number-sm": "nzSize === 'small'", "class.ant-input-number-disabled": "nzDisabled", "class.ant-input-number-rtl": "dir === 'rtl'" }, classAttribute: "ant-input-number" }, providers: [ { provide: NG_VALUE_ACCESSOR, useExisting: forwardRef(() => NzInputNumberComponent), multi: true } ], viewQueries: [{ propertyName: "inputElement", first: true, predicate: ["inputElement"], descendants: true, static: true }], exportAs: ["nzInputNumber"], usesOnChanges: true, ngImport: i0, template: ` <div class="ant-input-number-handler-wrap"> <span unselectable="unselectable" class="ant-input-number-handler ant-input-number-handler-up" (mousedown)="up($event)" (mouseup)="stop()" (mouseleave)="stop()" [class.ant-input-number-handler-up-disabled]="disabledUp" > <i nz-icon nzType="up" class="ant-input-number-handler-up-inner"></i> </span> <span unselectable="unselectable" class="ant-input-number-handler ant-input-number-handler-down" (mousedown)="down($event)" (mouseup)="stop()" (mouseleave)="stop()" [class.ant-input-number-handler-down-disabled]="disabledDown" > <i nz-icon nzType="down" class="ant-input-number-handler-down-inner"></i> </span> </div> <div class="ant-input-number-input-wrap"> <input #inputElement autocomplete="off" class="ant-input-number-input" [attr.id]="nzId" [attr.autofocus]="nzAutoFocus ? 'autofocus' : null" [disabled]="nzDisabled" [attr.min]="nzMin" [attr.max]="nzMax" [placeholder]="nzPlaceHolder" [attr.step]="nzStep" [attr.inputmode]="nzInputMode" [ngModel]="displayValue" (ngModelChange)="onModelChange($event)" /> </div> `, isInline: true, directives: [{ type: i3.NzIconDirective, selector: "[nz-icon]", inputs: ["nzSpin", "nzRotate", "nzType", "nzTheme", "nzTwotoneColor", "nzIconfont"], exportAs: ["nzIcon"] }, { type: i4.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { type: i4.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { type: i4.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); __decorate([ InputBoolean() ], NzInputNumberComponent.prototype, "nzDisabled", void 0); __decorate([ InputBoolean() ], NzInputNumberComponent.prototype, "nzAutoFocus", void 0); i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "13.2.5", ngImport: i0, type: NzInputNumberComponent, decorators: [{ type: Component, args: [{ selector: 'nz-input-number', exportAs: 'nzInputNumber', template: ` <div class="ant-input-number-handler-wrap"> <span unselectable="unselectable" class="ant-input-number-handler ant-input-number-handler-up" (mousedown)="up($event)" (mouseup)="stop()" (mouseleave)="stop()" [class.ant-input-number-handler-up-disabled]="disabledUp" > <i nz-icon nzType="up" class="ant-input-number-handler-up-inner"></i> </span> <span unselectable="unselectable" class="ant-input-number-handler ant-input-number-handler-down" (mousedown)="down($event)" (mouseup)="stop()" (mouseleave)="stop()" [class.ant-input-number-handler-down-disabled]="disabledDown" > <i nz-icon nzType="down" class="ant-input-number-handler-down-inner"></i> </span> </div> <div class="ant-input-number-input-wrap"> <input #inputElement autocomplete="off" class="ant-input-number-input" [attr.id]="nzId" [attr.autofocus]="nzAutoFocus ? 'autofocus' : null" [disabled]="nzDisabled" [attr.min]="nzMin" [attr.max]="nzMax" [placeholder]="nzPlaceHolder" [attr.step]="nzStep" [attr.inputmode]="nzInputMode" [ngModel]="displayValue" (ngModelChange)="onModelChange($event)" /> </div> `, providers: [ { provide: NG_VALUE_ACCESSOR, useExisting: forwardRef(() => NzInputNumberComponent), multi: true } ], changeDetection: ChangeDetectionStrategy.OnPush, encapsulation: ViewEncapsulation.None, host: { class: 'ant-input-number', '[class.ant-input-number-focused]': 'isFocused', '[class.ant-input-number-lg]': `nzSize === 'large'`, '[class.ant-input-number-sm]': `nzSize === 'small'`, '[class.ant-input-number-disabled]': 'nzDisabled', '[class.ant-input-number-rtl]': `dir === 'rtl'` } }] }], ctorParameters: function () { return [{ type: i0.NgZone }, { type: i0.ElementRef }, { type: i0.ChangeDetectorRef }, { type: i1.FocusMonitor }, { type: i2.Directionality, decorators: [{ type: Optional }] }]; }, propDecorators: { nzBlur: [{ type: Output }], nzFocus: [{ type: Output }], inputElement: [{ type: ViewChild, args: ['inputElement', { static: true }] }], nzSize: [{ type: Input }], nzMin: [{ type: Input }], nzMax: [{ type: Input }], nzParser: [{ type: Input }], nzPrecision: [{ type: Input }], nzPrecisionMode: [{ type: Input }], nzPlaceHolder: [{ type: Input }], nzStep: [{ type: Input }], nzInputMode: [{ type: Input }], nzId: [{ type: Input }], nzDisabled: [{ type: Input }], nzAutoFocus: [{ type: Input }], nzFormatter: [{ type: Input }] } }); /** * Use of this source code is governed by an MIT-style license that can be * found in the LICENSE file at https://github.com/NG-ZORRO/ng-zorro-antd/blob/master/LICENSE */ class NzInputNumberModule { } NzInputNumberModule.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "13.2.5", ngImport: i0, type: NzInputNumberModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule }); NzInputNumberModule.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "12.0.0", version: "13.2.5", ngImport: i0, type: NzInputNumberModule, declarations: [NzInputNumberComponent], imports: [BidiModule, CommonModule, FormsModule, NzIconModule], exports: [NzInputNumberComponent] }); NzInputNumberModule.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "13.2.5", ngImport: i0, type: NzInputNumberModule, imports: [[BidiModule, CommonModule, FormsModule, NzIconModule]] }); i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "13.2.5", ngImport: i0, type: NzInputNumberModule, decorators: [{ type: NgModule, args: [{ imports: [BidiModule, CommonModule, FormsModule, NzIconModule], declarations: [NzInputNumberComponent], exports: [NzInputNumberComponent] }] }] }); /** * Use of this source code is governed by an MIT-style license that can be * found in the LICENSE file at https://github.com/NG-ZORRO/ng-zorro-antd/blob/master/LICENSE */ /** * Generated bundle index. Do not edit. */ export { NzInputNumberComponent, NzInputNumberModule }; //# sourceMappingURL=ng-zorro-antd-input-number.mjs.map