@webilix/ngx-form-m3 0.0.45 → 0.0.48

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -207,6 +207,8 @@ class InputErrorPipe {
207
207
  return `شماره کارت بانکی صحیح مشخص نشده است.`;
208
208
  case 'bank-sheba':
209
209
  return `شماره شبا صحیح مشخص نشده است.`;
210
+ case 'username':
211
+ return value;
210
212
  case 'pattern':
211
213
  switch (type) {
212
214
  case 'EMAIL':
@@ -493,6 +495,48 @@ const LengthValidator = (length) => {
493
495
  };
494
496
  };
495
497
 
498
+ const UsernameValidator = (verify) => {
499
+ return (formControl) => {
500
+ const value = formControl.value;
501
+ if (Helper.IS.empty(value) || !Helper.IS.string(value))
502
+ return null;
503
+ // MINLENGTH
504
+ const minLength = verify?.minLength;
505
+ if (minLength && minLength > 0 && value.length < minLength)
506
+ return { username: `مقدار باید حداقل داری ${Helper.NUMBER.format(minLength)} کاراکتر باشد.` };
507
+ // USERNAME
508
+ const regExp = new RegExp(/^[a-z0-9-.]{1,}$/);
509
+ if (!regExp.test(value)) {
510
+ const chars = [
511
+ 'حروف انگلیسی کوچک',
512
+ 'اعداد انگلیسی',
513
+ !!verify?.useDash ? 'خط فاصله' : '',
514
+ !!verify?.useDot ? 'نقطه' : '',
515
+ ].filter((char) => char !== '');
516
+ return { username: `کاراکترهای مجاز: ${chars.join('، ')}` };
517
+ }
518
+ // USE DASH
519
+ if (!verify?.useDash && value.indexOf('-') !== -1)
520
+ return { username: `امکان استفاده از خط فاصله در کلمه عبور وجود ندارد.` };
521
+ // USE DOT
522
+ if (!verify?.useDot && value.indexOf('.') !== -1)
523
+ return { username: `امکان استفاده از نقطه در کلمه عبور وجود ندارد.` };
524
+ // START WITH CHAR
525
+ if (!!verify?.startWithChar) {
526
+ const regExp = new RegExp(/^[a-z]{1}/);
527
+ if (!regExp.test(value))
528
+ return { username: 'مقدار باید با یک کاراکتر انگلیسی شروع شده باشد.' };
529
+ }
530
+ // END WITH CHAR
531
+ if (!!verify?.endWithChar) {
532
+ const regExp = new RegExp(/[a-z]{1}$/);
533
+ if (!regExp.test(value))
534
+ return { username: 'مقدار باید با یک کاراکتر انگلیسی تمام شده باشد.' };
535
+ }
536
+ return null;
537
+ };
538
+ };
539
+
496
540
  class InputBankCardMethods extends InputMethods {
497
541
  control(input, validators) {
498
542
  validators.push(BankCardValidator());
@@ -1801,7 +1845,7 @@ class InputTagComponent {
1801
1845
  event.option.deselect();
1802
1846
  }
1803
1847
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.1.4", ngImport: i0, type: InputTagComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
1804
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.1.4", type: InputTagComponent, isStandalone: true, selector: "ng-component", inputs: { values: { classPropertyName: "values", publicName: "values", isSignal: false, isRequired: true, transformFunction: null }, isButtonDisabled: { classPropertyName: "isButtonDisabled", publicName: "isButtonDisabled", isSignal: false, isRequired: true, transformFunction: null }, inputValue: { classPropertyName: "inputValue", publicName: "inputValue", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { inputValue: "inputValueChange" }, host: { attributes: { "selector": "input-tag" } }, ngImport: i0, template: "<mat-form-field [appearance]=\"input.appearance || config.appearance\" [floatLabel]=\"tags.length === 0 ? 'auto' : 'always'\">\n <mat-label>{{ input.title || '\u062A\u06AF' }}</mat-label>\n @if (formControl.invalid) { <mat-error>{{ formControl.errors | InputErrorPipe : input.type }}</mat-error> }\n\n <!-- HINT -->\n @if (input.hint) { <mat-hint>{{ input.hint }}</mat-hint> }\n\n <!-- BUTTON -->\n @if (input.button) {\n <span matIconSuffix>\n <button\n mat-icon-button\n type=\"button\"\n [disabled]=\"isButtonDisabled\"\n (click)=\"input.button.onClick(values)\"\n [tabIndex]=\"-1\"\n >\n <mat-icon [style.color]=\"isButtonDisabled ? undefined : input.button.color\">\n {{ input.button.icon }}\n </mat-icon>\n </button>\n </span>\n }\n\n <mat-chip-grid #chipGrid [formControl]=\"formControl\" class=\"ngx-helper-form-m3-tag-input\">\n @for (tag of tags; track $index) {\n <mat-chip-row (removed)=\"removeTag(tag); tagInput.value = ''\">\n <span class=\"tag\">{{ tag }}</span>\n <button matChipRemove type=\"button\"><mat-icon>cancel</mat-icon></button>\n </mat-chip-row>\n }\n </mat-chip-grid>\n <input\n type=\"text\"\n name=\"inputValue\"\n [(ngModel)]=\"inputValue\"\n [AutoFocusDirective]=\"config.autoFocus === input.name\"\n [matChipInputFor]=\"chipGrid\"\n [matAutocomplete]=\"auto\"\n [matChipInputSeparatorKeyCodes]=\"separatorKeysCodes\"\n (matChipInputTokenEnd)=\"addTag($event); tagInput.value = ''\"\n #tagInput\n />\n <mat-autocomplete #auto=\"matAutocomplete\" (optionSelected)=\"selectTag($event); tagInput.value = ''\">\n @for (option of filteredTags(); track $index) {\n <mat-option [value]=\"option\">{{ option }}</mat-option>\n }\n </mat-autocomplete>\n\n <!-- DESCRIPTION -->\n @if (input.description) {\n <div\n class=\"ngx-form-m3-input-description\"\n [class.ngx-form-m3-disabled-input]=\"formControl.disabled\"\n [innerHTML]=\"input.description | MultiLinePipe\"\n ></div>\n }\n</mat-form-field>\n", styles: [""], dependencies: [{ kind: "ngmodule", type: ReactiveFormsModule }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.FormControlDirective, selector: "[formControl]", inputs: ["formControl", "disabled", "ngModel"], outputs: ["ngModelChange"], exportAs: ["ngForm"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "ngmodule", type: MatAutocompleteModule }, { kind: "component", type: i2.MatAutocomplete, selector: "mat-autocomplete", inputs: ["aria-label", "aria-labelledby", "displayWith", "autoActiveFirstOption", "autoSelectActiveOption", "requireSelection", "panelWidth", "disableRipple", "class", "hideSingleSelectionIndicator"], outputs: ["optionSelected", "opened", "closed", "optionActivated"], exportAs: ["matAutocomplete"] }, { kind: "component", type: i2.MatOption, selector: "mat-option", inputs: ["value", "id", "disabled"], outputs: ["onSelectionChange"], exportAs: ["matOption"] }, { kind: "directive", type: i2.MatAutocompleteTrigger, selector: "input[matAutocomplete], textarea[matAutocomplete]", inputs: ["matAutocomplete", "matAutocompletePosition", "matAutocompleteConnectedTo", "autocomplete", "matAutocompleteDisabled"], exportAs: ["matAutocompleteTrigger"] }, { kind: "ngmodule", type: MatChipsModule }, { kind: "component", type: i3$2.MatChipGrid, selector: "mat-chip-grid", inputs: ["disabled", "placeholder", "required", "value", "errorStateMatcher"], outputs: ["change", "valueChange"] }, { kind: "directive", type: i3$2.MatChipInput, selector: "input[matChipInputFor]", inputs: ["matChipInputFor", "matChipInputAddOnBlur", "matChipInputSeparatorKeyCodes", "placeholder", "id", "disabled", "readonly", "matChipInputDisabledInteractive"], outputs: ["matChipInputTokenEnd"], exportAs: ["matChipInput", "matChipInputFor"] }, { kind: "directive", type: i3$2.MatChipRemove, selector: "[matChipRemove]" }, { kind: "component", type: i3$2.MatChipRow, selector: "mat-chip-row, [mat-chip-row], mat-basic-chip-row, [mat-basic-chip-row]", inputs: ["editable"], outputs: ["edited"] }, { kind: "component", type: MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: MatIconButton, selector: "button[mat-icon-button], a[mat-icon-button], button[matIconButton], a[matIconButton]", exportAs: ["matButton", "matAnchor"] }, { kind: "ngmodule", type: MatInputModule }, { kind: "directive", type: i2$1.MatLabel, selector: "mat-label" }, { kind: "directive", type: i2$1.MatHint, selector: "mat-hint", inputs: ["align", "id"] }, { kind: "directive", type: i2$1.MatError, selector: "mat-error, [matError]", inputs: ["id"] }, { kind: "directive", type: i2$1.MatSuffix, selector: "[matSuffix], [matIconSuffix], [matTextSuffix]", inputs: ["matTextSuffix"] }, { kind: "directive", type: AutoCompleteDirective, selector: "input[type=\"text\"]" }, { kind: "directive", type: AutoFocusDirective, selector: "[AutoFocusDirective]", inputs: ["AutoFocusDirective"] }, { kind: "pipe", type: InputErrorPipe, name: "InputErrorPipe" }, { kind: "pipe", type: MultiLinePipe, name: "MultiLinePipe" }] });
1848
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.1.4", type: InputTagComponent, isStandalone: true, selector: "ng-component", inputs: { values: { classPropertyName: "values", publicName: "values", isSignal: false, isRequired: true, transformFunction: null }, isButtonDisabled: { classPropertyName: "isButtonDisabled", publicName: "isButtonDisabled", isSignal: false, isRequired: true, transformFunction: null }, inputValue: { classPropertyName: "inputValue", publicName: "inputValue", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { inputValue: "inputValueChange" }, host: { attributes: { "selector": "input-tag" } }, ngImport: i0, template: "<mat-form-field [appearance]=\"input.appearance || config.appearance\" [floatLabel]=\"tags.length === 0 ? 'auto' : 'always'\">\n <mat-label>{{ input.title || '\u062A\u06AF' }}</mat-label>\n @if (formControl.invalid) { <mat-error>{{ formControl.errors | InputErrorPipe : input.type }}</mat-error> }\n\n <!-- HINT -->\n @if (input.hint) { <mat-hint>{{ input.hint }}</mat-hint> }\n\n <!-- BUTTON -->\n @if (input.button) {\n <span matIconSuffix>\n <button\n mat-icon-button\n type=\"button\"\n [disabled]=\"isButtonDisabled\"\n (click)=\"input.button.onClick(values)\"\n [tabIndex]=\"-1\"\n >\n <mat-icon [style.color]=\"isButtonDisabled ? undefined : input.button.color\">\n {{ input.button.icon }}\n </mat-icon>\n </button>\n </span>\n }\n\n <mat-chip-grid #chipGrid [formControl]=\"formControl\" class=\"ngx-helper-form-m3-tag-input\">\n @for (tag of tags; track $index) {\n <mat-chip-row (removed)=\"removeTag(tag); tagInput.value = ''\">\n <span class=\"tag\">{{ tag }}</span>\n <button matChipRemove type=\"button\"><mat-icon>cancel</mat-icon></button>\n </mat-chip-row>\n }\n <input\n type=\"text\"\n name=\"inputValue\"\n [(ngModel)]=\"inputValue\"\n [AutoFocusDirective]=\"config.autoFocus === input.name\"\n [matChipInputFor]=\"chipGrid\"\n [matAutocomplete]=\"auto\"\n [matChipInputSeparatorKeyCodes]=\"separatorKeysCodes\"\n (matChipInputTokenEnd)=\"addTag($event); tagInput.value = ''\"\n #tagInput\n />\n </mat-chip-grid>\n <mat-autocomplete #auto=\"matAutocomplete\" (optionSelected)=\"selectTag($event); tagInput.value = ''\">\n @for (option of filteredTags(); track $index) { <mat-option [value]=\"option\">{{ option }}</mat-option> }\n </mat-autocomplete>\n\n <!-- DESCRIPTION -->\n @if (input.description) {\n <div\n class=\"ngx-form-m3-input-description\"\n [class.ngx-form-m3-disabled-input]=\"formControl.disabled\"\n [innerHTML]=\"input.description | MultiLinePipe\"\n ></div>\n }\n</mat-form-field>\n", styles: [""], dependencies: [{ kind: "ngmodule", type: ReactiveFormsModule }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.FormControlDirective, selector: "[formControl]", inputs: ["formControl", "disabled", "ngModel"], outputs: ["ngModelChange"], exportAs: ["ngForm"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "ngmodule", type: MatAutocompleteModule }, { kind: "component", type: i2.MatAutocomplete, selector: "mat-autocomplete", inputs: ["aria-label", "aria-labelledby", "displayWith", "autoActiveFirstOption", "autoSelectActiveOption", "requireSelection", "panelWidth", "disableRipple", "class", "hideSingleSelectionIndicator"], outputs: ["optionSelected", "opened", "closed", "optionActivated"], exportAs: ["matAutocomplete"] }, { kind: "component", type: i2.MatOption, selector: "mat-option", inputs: ["value", "id", "disabled"], outputs: ["onSelectionChange"], exportAs: ["matOption"] }, { kind: "directive", type: i2.MatAutocompleteTrigger, selector: "input[matAutocomplete], textarea[matAutocomplete]", inputs: ["matAutocomplete", "matAutocompletePosition", "matAutocompleteConnectedTo", "autocomplete", "matAutocompleteDisabled"], exportAs: ["matAutocompleteTrigger"] }, { kind: "ngmodule", type: MatChipsModule }, { kind: "component", type: i3$2.MatChipGrid, selector: "mat-chip-grid", inputs: ["disabled", "placeholder", "required", "value", "errorStateMatcher"], outputs: ["change", "valueChange"] }, { kind: "directive", type: i3$2.MatChipInput, selector: "input[matChipInputFor]", inputs: ["matChipInputFor", "matChipInputAddOnBlur", "matChipInputSeparatorKeyCodes", "placeholder", "id", "disabled", "readonly", "matChipInputDisabledInteractive"], outputs: ["matChipInputTokenEnd"], exportAs: ["matChipInput", "matChipInputFor"] }, { kind: "directive", type: i3$2.MatChipRemove, selector: "[matChipRemove]" }, { kind: "component", type: i3$2.MatChipRow, selector: "mat-chip-row, [mat-chip-row], mat-basic-chip-row, [mat-basic-chip-row]", inputs: ["editable"], outputs: ["edited"] }, { kind: "component", type: MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: MatIconButton, selector: "button[mat-icon-button], a[mat-icon-button], button[matIconButton], a[matIconButton]", exportAs: ["matButton", "matAnchor"] }, { kind: "ngmodule", type: MatInputModule }, { kind: "directive", type: i2$1.MatLabel, selector: "mat-label" }, { kind: "directive", type: i2$1.MatHint, selector: "mat-hint", inputs: ["align", "id"] }, { kind: "directive", type: i2$1.MatError, selector: "mat-error, [matError]", inputs: ["id"] }, { kind: "directive", type: i2$1.MatSuffix, selector: "[matSuffix], [matIconSuffix], [matTextSuffix]", inputs: ["matTextSuffix"] }, { kind: "directive", type: AutoCompleteDirective, selector: "input[type=\"text\"]" }, { kind: "directive", type: AutoFocusDirective, selector: "[AutoFocusDirective]", inputs: ["AutoFocusDirective"] }, { kind: "pipe", type: InputErrorPipe, name: "InputErrorPipe" }, { kind: "pipe", type: MultiLinePipe, name: "MultiLinePipe" }] });
1805
1849
  }
1806
1850
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.1.4", ngImport: i0, type: InputTagComponent, decorators: [{
1807
1851
  type: Component,
@@ -1818,7 +1862,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.1.4", ngImpor
1818
1862
  AutoFocusDirective,
1819
1863
  InputErrorPipe,
1820
1864
  MultiLinePipe,
1821
- ], template: "<mat-form-field [appearance]=\"input.appearance || config.appearance\" [floatLabel]=\"tags.length === 0 ? 'auto' : 'always'\">\n <mat-label>{{ input.title || '\u062A\u06AF' }}</mat-label>\n @if (formControl.invalid) { <mat-error>{{ formControl.errors | InputErrorPipe : input.type }}</mat-error> }\n\n <!-- HINT -->\n @if (input.hint) { <mat-hint>{{ input.hint }}</mat-hint> }\n\n <!-- BUTTON -->\n @if (input.button) {\n <span matIconSuffix>\n <button\n mat-icon-button\n type=\"button\"\n [disabled]=\"isButtonDisabled\"\n (click)=\"input.button.onClick(values)\"\n [tabIndex]=\"-1\"\n >\n <mat-icon [style.color]=\"isButtonDisabled ? undefined : input.button.color\">\n {{ input.button.icon }}\n </mat-icon>\n </button>\n </span>\n }\n\n <mat-chip-grid #chipGrid [formControl]=\"formControl\" class=\"ngx-helper-form-m3-tag-input\">\n @for (tag of tags; track $index) {\n <mat-chip-row (removed)=\"removeTag(tag); tagInput.value = ''\">\n <span class=\"tag\">{{ tag }}</span>\n <button matChipRemove type=\"button\"><mat-icon>cancel</mat-icon></button>\n </mat-chip-row>\n }\n </mat-chip-grid>\n <input\n type=\"text\"\n name=\"inputValue\"\n [(ngModel)]=\"inputValue\"\n [AutoFocusDirective]=\"config.autoFocus === input.name\"\n [matChipInputFor]=\"chipGrid\"\n [matAutocomplete]=\"auto\"\n [matChipInputSeparatorKeyCodes]=\"separatorKeysCodes\"\n (matChipInputTokenEnd)=\"addTag($event); tagInput.value = ''\"\n #tagInput\n />\n <mat-autocomplete #auto=\"matAutocomplete\" (optionSelected)=\"selectTag($event); tagInput.value = ''\">\n @for (option of filteredTags(); track $index) {\n <mat-option [value]=\"option\">{{ option }}</mat-option>\n }\n </mat-autocomplete>\n\n <!-- DESCRIPTION -->\n @if (input.description) {\n <div\n class=\"ngx-form-m3-input-description\"\n [class.ngx-form-m3-disabled-input]=\"formControl.disabled\"\n [innerHTML]=\"input.description | MultiLinePipe\"\n ></div>\n }\n</mat-form-field>\n" }]
1865
+ ], template: "<mat-form-field [appearance]=\"input.appearance || config.appearance\" [floatLabel]=\"tags.length === 0 ? 'auto' : 'always'\">\n <mat-label>{{ input.title || '\u062A\u06AF' }}</mat-label>\n @if (formControl.invalid) { <mat-error>{{ formControl.errors | InputErrorPipe : input.type }}</mat-error> }\n\n <!-- HINT -->\n @if (input.hint) { <mat-hint>{{ input.hint }}</mat-hint> }\n\n <!-- BUTTON -->\n @if (input.button) {\n <span matIconSuffix>\n <button\n mat-icon-button\n type=\"button\"\n [disabled]=\"isButtonDisabled\"\n (click)=\"input.button.onClick(values)\"\n [tabIndex]=\"-1\"\n >\n <mat-icon [style.color]=\"isButtonDisabled ? undefined : input.button.color\">\n {{ input.button.icon }}\n </mat-icon>\n </button>\n </span>\n }\n\n <mat-chip-grid #chipGrid [formControl]=\"formControl\" class=\"ngx-helper-form-m3-tag-input\">\n @for (tag of tags; track $index) {\n <mat-chip-row (removed)=\"removeTag(tag); tagInput.value = ''\">\n <span class=\"tag\">{{ tag }}</span>\n <button matChipRemove type=\"button\"><mat-icon>cancel</mat-icon></button>\n </mat-chip-row>\n }\n <input\n type=\"text\"\n name=\"inputValue\"\n [(ngModel)]=\"inputValue\"\n [AutoFocusDirective]=\"config.autoFocus === input.name\"\n [matChipInputFor]=\"chipGrid\"\n [matAutocomplete]=\"auto\"\n [matChipInputSeparatorKeyCodes]=\"separatorKeysCodes\"\n (matChipInputTokenEnd)=\"addTag($event); tagInput.value = ''\"\n #tagInput\n />\n </mat-chip-grid>\n <mat-autocomplete #auto=\"matAutocomplete\" (optionSelected)=\"selectTag($event); tagInput.value = ''\">\n @for (option of filteredTags(); track $index) { <mat-option [value]=\"option\">{{ option }}</mat-option> }\n </mat-autocomplete>\n\n <!-- DESCRIPTION -->\n @if (input.description) {\n <div\n class=\"ngx-form-m3-input-description\"\n [class.ngx-form-m3-disabled-input]=\"formControl.disabled\"\n [innerHTML]=\"input.description | MultiLinePipe\"\n ></div>\n }\n</mat-form-field>\n" }]
1822
1866
  }], propDecorators: { values: [{
1823
1867
  type: Input,
1824
1868
  args: [{ required: true }]
@@ -1938,6 +1982,97 @@ class InputTextareaMethods extends InputMethods {
1938
1982
  }
1939
1983
  }
1940
1984
 
1985
+ class InputTimeComponent {
1986
+ formControl = inject(INPUT_CONTROL);
1987
+ input = inject(INPUT_TYPE);
1988
+ config = inject(INPUT_CONFIG);
1989
+ values;
1990
+ isButtonDisabled;
1991
+ hour = '--';
1992
+ hours = [...Array(24).keys()].map((hour) => hour.toString().padStart(2, '0'));
1993
+ minute = '--';
1994
+ minutes = [...Array(60).keys()].map((minute) => minute.toString().padStart(2, '0'));
1995
+ second = '--';
1996
+ seconds = [...Array(60).keys()].map((minute) => minute.toString().padStart(2, '0'));
1997
+ ngOnInit() {
1998
+ if (!this.input.value)
1999
+ return;
2000
+ const value = this.input.value.split(':');
2001
+ this.hour = value[0];
2002
+ this.minute = value[1];
2003
+ this.second = this.input.showSeconds ? value[2] : '00';
2004
+ }
2005
+ setValue() {
2006
+ const value = this.hour === '--' ? null : [this.hour, this.minute, this.second].join(':');
2007
+ this.formControl.setValue(value);
2008
+ this.formControl.markAsTouched();
2009
+ }
2010
+ resetTime() {
2011
+ this.hour = '--';
2012
+ this.minute = '--';
2013
+ this.second = '--';
2014
+ this.setValue();
2015
+ }
2016
+ setNow() {
2017
+ const now = new Date();
2018
+ this.hour = now.getHours().toString().padStart(2, '0');
2019
+ this.minute = now.getMinutes().toString().padStart(2, '0');
2020
+ this.second = this.input.showSeconds ? now.getSeconds().toString().padStart(2, '0') : '00';
2021
+ this.setValue();
2022
+ }
2023
+ setHour(hour) {
2024
+ this.hour = hour;
2025
+ this.minute = this.minute === '--' ? '00' : this.minute;
2026
+ this.second = this.input.showSeconds ? (this.second === '--' ? '00' : this.minute) : '00';
2027
+ this.setValue();
2028
+ }
2029
+ setMinute(minute) {
2030
+ if (this.hour === '--')
2031
+ return;
2032
+ this.minute = minute;
2033
+ this.setValue();
2034
+ }
2035
+ setSecond(second) {
2036
+ if (this.hour === '--' || !this.input.showSeconds)
2037
+ return;
2038
+ this.second = second;
2039
+ this.setValue();
2040
+ }
2041
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.1.4", ngImport: i0, type: InputTimeComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
2042
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.1.4", type: InputTimeComponent, isStandalone: true, selector: "ng-component", inputs: { values: "values", isButtonDisabled: "isButtonDisabled" }, host: { attributes: { "selector": "input-time" } }, ngImport: i0, template: "<mat-form-field [appearance]=\"input.appearance || config.appearance\" [floatLabel]=\"formControl.value ? 'always' : 'auto'\">\n <mat-label>{{ input.title || '\u0633\u0627\u0639\u062A' }}</mat-label>\n @if (formControl.invalid) { <mat-error>{{ formControl.errors | InputErrorPipe : input.type }}</mat-error> }\n\n <!-- HINT -->\n @if (input.hint) { <mat-hint>{{ input.hint }}</mat-hint> }\n\n <!-- SUFFIX -->\n <span matTextSuffix class=\"ngx-form-m3-input-suffix click\" [class.ngx-form-m3-disabled-input]=\"formControl.disabled\">\n <span>&nbsp;</span>\n <mat-icon (click)=\"formControl.value ? resetTime() : setNow(); formControl.markAsTouched()\">\n {{ formControl.value ? 'close' : 'access_time' }}\n </mat-icon>\n </span>\n\n <!-- BUTTON -->\n @if (input.button) {\n <span matIconSuffix>\n <button\n mat-icon-button\n type=\"button\"\n [disabled]=\"isButtonDisabled\"\n (click)=\"input.button.onClick(values)\"\n [tabIndex]=\"-1\"\n >\n <mat-icon [style.color]=\"isButtonDisabled ? undefined : input.button.color\">\n {{ input.button.icon }}\n </mat-icon>\n </button>\n </span>\n }\n\n <!-- INPUT -->\n <input matInput type=\"text\" [name]=\"input.name\" [formControl]=\"formControl\" [style.display]=\"'none !important'\" />\n <div class=\"ngx-helper-form-m3-time-input\">\n <button\n mat-button\n type=\"button\"\n [matMenuTriggerFor]=\"hourMenu\"\n [disabled]=\"formControl.disabled\"\n [class.ngx-form-m3-disabled-input]=\"formControl.disabled\"\n >\n {{ hour }}\n </button>\n <mat-menu #hourMenu=\"matMenu\" class=\"ngx-helper-form-m3-time-input-hour\">\n @for (h of hours; track $index) {\n <button mat-menu-item (click)=\"setHour(h)\" [disabled]=\"hour === h || formControl.disabled\">\n <span class=\"hour\">{{ h }}</span>\n </button>\n }\n </mat-menu>\n\n <div class=\"colon\" [class.ngx-form-m3-disabled-input]=\"formControl.disabled\">:</div>\n\n <button\n mat-button\n type=\"button\"\n [matMenuTriggerFor]=\"minuteMenu\"\n [disabled]=\"hour === '--' || formControl.disabled\"\n [class.ngx-form-m3-disabled-input]=\"hour === '--' || formControl.disabled\"\n >\n {{ minute }}\n </button>\n <mat-menu #minuteMenu=\"matMenu\" class=\"ngx-helper-form-m3-time-input-minute\">\n @for (m of minutes; track $index) {\n <button mat-menu-item (click)=\"setMinute(m)\" [disabled]=\"minute === m || formControl.disabled\">\n <span class=\"minute\">{{ m }}</span>\n </button>\n }\n </mat-menu>\n\n <!-- SECOND -->\n @if (input.showSeconds) {\n <div class=\"colon\" [class.ngx-form-m3-disabled-input]=\"formControl.disabled\">:</div>\n\n <button\n mat-button\n type=\"button\"\n [matMenuTriggerFor]=\"secondMenu\"\n [disabled]=\"hour === '--' || formControl.disabled\"\n [class.ngx-form-m3-disabled-input]=\"hour === '--' || formControl.disabled\"\n >\n {{ second }}\n </button>\n <mat-menu #secondMenu=\"matMenu\" class=\"ngx-helper-form-m3-time-input-second\">\n @for (s of seconds; track $index) {\n <button mat-menu-item (click)=\"setSecond(s)\" [disabled]=\"second === s || formControl.disabled\">\n <span class=\"second\">{{ s }}</span>\n </button>\n }\n </mat-menu>\n }\n </div>\n\n <!-- DESCRIPTION -->\n @if (input.description) {\n <div\n class=\"ngx-form-m3-input-description\"\n [class.ngx-form-m3-disabled-input]=\"formControl.disabled\"\n [innerHTML]=\"input.description | MultiLinePipe\"\n ></div>\n }\n</mat-form-field>\n", styles: [""], dependencies: [{ kind: "ngmodule", type: ReactiveFormsModule }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.FormControlDirective, selector: "[formControl]", inputs: ["formControl", "disabled", "ngModel"], outputs: ["ngModelChange"], exportAs: ["ngForm"] }, { kind: "component", type: MatButton, selector: " button[matButton], a[matButton], button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button], a[mat-button], a[mat-raised-button], a[mat-flat-button], a[mat-stroked-button] ", inputs: ["matButton"], exportAs: ["matButton", "matAnchor"] }, { kind: "component", type: MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: MatIconButton, selector: "button[mat-icon-button], a[mat-icon-button], button[matIconButton], a[matIconButton]", exportAs: ["matButton", "matAnchor"] }, { kind: "ngmodule", type: MatInputModule }, { kind: "directive", type: i2$1.MatInput, selector: "input[matInput], textarea[matInput], select[matNativeControl], input[matNativeControl], textarea[matNativeControl]", inputs: ["disabled", "id", "placeholder", "name", "required", "type", "errorStateMatcher", "aria-describedby", "value", "readonly", "disabledInteractive"], exportAs: ["matInput"] }, { kind: "directive", type: i2$1.MatLabel, selector: "mat-label" }, { kind: "directive", type: i2$1.MatHint, selector: "mat-hint", inputs: ["align", "id"] }, { kind: "directive", type: i2$1.MatError, selector: "mat-error, [matError]", inputs: ["id"] }, { kind: "directive", type: i2$1.MatSuffix, selector: "[matSuffix], [matIconSuffix], [matTextSuffix]", inputs: ["matTextSuffix"] }, { kind: "ngmodule", type: MatMenuModule }, { kind: "component", type: i3$1.MatMenu, selector: "mat-menu", inputs: ["backdropClass", "aria-label", "aria-labelledby", "aria-describedby", "xPosition", "yPosition", "overlapTrigger", "hasBackdrop", "class", "classList"], outputs: ["closed", "close"], exportAs: ["matMenu"] }, { kind: "component", type: i3$1.MatMenuItem, selector: "[mat-menu-item]", inputs: ["role", "disabled", "disableRipple"], exportAs: ["matMenuItem"] }, { kind: "directive", type: i3$1.MatMenuTrigger, selector: "[mat-menu-trigger-for], [matMenuTriggerFor]", inputs: ["mat-menu-trigger-for", "matMenuTriggerFor", "matMenuTriggerData", "matMenuTriggerRestoreFocus"], outputs: ["menuOpened", "onMenuOpen", "menuClosed", "onMenuClose"], exportAs: ["matMenuTrigger"] }, { kind: "ngmodule", type: MatSelectModule }, { kind: "pipe", type: InputErrorPipe, name: "InputErrorPipe" }, { kind: "pipe", type: MultiLinePipe, name: "MultiLinePipe" }] });
2043
+ }
2044
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.1.4", ngImport: i0, type: InputTimeComponent, decorators: [{
2045
+ type: Component,
2046
+ args: [{ host: { selector: 'input-time' }, imports: [
2047
+ ReactiveFormsModule,
2048
+ MatButton,
2049
+ MatFormField,
2050
+ MatIcon,
2051
+ MatIconButton,
2052
+ MatInputModule,
2053
+ MatMenuModule,
2054
+ MatSelectModule,
2055
+ InputErrorPipe,
2056
+ MultiLinePipe,
2057
+ ], template: "<mat-form-field [appearance]=\"input.appearance || config.appearance\" [floatLabel]=\"formControl.value ? 'always' : 'auto'\">\n <mat-label>{{ input.title || '\u0633\u0627\u0639\u062A' }}</mat-label>\n @if (formControl.invalid) { <mat-error>{{ formControl.errors | InputErrorPipe : input.type }}</mat-error> }\n\n <!-- HINT -->\n @if (input.hint) { <mat-hint>{{ input.hint }}</mat-hint> }\n\n <!-- SUFFIX -->\n <span matTextSuffix class=\"ngx-form-m3-input-suffix click\" [class.ngx-form-m3-disabled-input]=\"formControl.disabled\">\n <span>&nbsp;</span>\n <mat-icon (click)=\"formControl.value ? resetTime() : setNow(); formControl.markAsTouched()\">\n {{ formControl.value ? 'close' : 'access_time' }}\n </mat-icon>\n </span>\n\n <!-- BUTTON -->\n @if (input.button) {\n <span matIconSuffix>\n <button\n mat-icon-button\n type=\"button\"\n [disabled]=\"isButtonDisabled\"\n (click)=\"input.button.onClick(values)\"\n [tabIndex]=\"-1\"\n >\n <mat-icon [style.color]=\"isButtonDisabled ? undefined : input.button.color\">\n {{ input.button.icon }}\n </mat-icon>\n </button>\n </span>\n }\n\n <!-- INPUT -->\n <input matInput type=\"text\" [name]=\"input.name\" [formControl]=\"formControl\" [style.display]=\"'none !important'\" />\n <div class=\"ngx-helper-form-m3-time-input\">\n <button\n mat-button\n type=\"button\"\n [matMenuTriggerFor]=\"hourMenu\"\n [disabled]=\"formControl.disabled\"\n [class.ngx-form-m3-disabled-input]=\"formControl.disabled\"\n >\n {{ hour }}\n </button>\n <mat-menu #hourMenu=\"matMenu\" class=\"ngx-helper-form-m3-time-input-hour\">\n @for (h of hours; track $index) {\n <button mat-menu-item (click)=\"setHour(h)\" [disabled]=\"hour === h || formControl.disabled\">\n <span class=\"hour\">{{ h }}</span>\n </button>\n }\n </mat-menu>\n\n <div class=\"colon\" [class.ngx-form-m3-disabled-input]=\"formControl.disabled\">:</div>\n\n <button\n mat-button\n type=\"button\"\n [matMenuTriggerFor]=\"minuteMenu\"\n [disabled]=\"hour === '--' || formControl.disabled\"\n [class.ngx-form-m3-disabled-input]=\"hour === '--' || formControl.disabled\"\n >\n {{ minute }}\n </button>\n <mat-menu #minuteMenu=\"matMenu\" class=\"ngx-helper-form-m3-time-input-minute\">\n @for (m of minutes; track $index) {\n <button mat-menu-item (click)=\"setMinute(m)\" [disabled]=\"minute === m || formControl.disabled\">\n <span class=\"minute\">{{ m }}</span>\n </button>\n }\n </mat-menu>\n\n <!-- SECOND -->\n @if (input.showSeconds) {\n <div class=\"colon\" [class.ngx-form-m3-disabled-input]=\"formControl.disabled\">:</div>\n\n <button\n mat-button\n type=\"button\"\n [matMenuTriggerFor]=\"secondMenu\"\n [disabled]=\"hour === '--' || formControl.disabled\"\n [class.ngx-form-m3-disabled-input]=\"hour === '--' || formControl.disabled\"\n >\n {{ second }}\n </button>\n <mat-menu #secondMenu=\"matMenu\" class=\"ngx-helper-form-m3-time-input-second\">\n @for (s of seconds; track $index) {\n <button mat-menu-item (click)=\"setSecond(s)\" [disabled]=\"second === s || formControl.disabled\">\n <span class=\"second\">{{ s }}</span>\n </button>\n }\n </mat-menu>\n }\n </div>\n\n <!-- DESCRIPTION -->\n @if (input.description) {\n <div\n class=\"ngx-form-m3-input-description\"\n [class.ngx-form-m3-disabled-input]=\"formControl.disabled\"\n [innerHTML]=\"input.description | MultiLinePipe\"\n ></div>\n }\n</mat-form-field>\n" }]
2058
+ }], propDecorators: { values: [{
2059
+ type: Input,
2060
+ args: [{ required: true }]
2061
+ }], isButtonDisabled: [{
2062
+ type: Input,
2063
+ args: [{ required: true }]
2064
+ }] } });
2065
+
2066
+ class InputTimeMethods extends InputMethods {
2067
+ control(input, validators) {
2068
+ const value = input.value && Helper.IS.STRING.time(input.value) ? input.value : null;
2069
+ return new FormControl(value, validators);
2070
+ }
2071
+ value(value, input) {
2072
+ return Helper.IS.string(value) && Helper.IS.STRING.time(value) ? value : null;
2073
+ }
2074
+ }
2075
+
1941
2076
  class InputUrlComponent {
1942
2077
  formControl = inject(INPUT_CONTROL);
1943
2078
  input = inject(INPUT_TYPE);
@@ -1979,6 +2114,47 @@ class InputUrlMethods extends InputMethods {
1979
2114
  }
1980
2115
  }
1981
2116
 
2117
+ class InputUsernameComponent {
2118
+ formControl = inject(INPUT_CONTROL);
2119
+ input = inject(INPUT_TYPE);
2120
+ config = inject(INPUT_CONFIG);
2121
+ values;
2122
+ isButtonDisabled;
2123
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.1.4", ngImport: i0, type: InputUsernameComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
2124
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.1.4", type: InputUsernameComponent, isStandalone: true, selector: "ng-component", inputs: { values: "values", isButtonDisabled: "isButtonDisabled" }, host: { attributes: { "selector": "input-username" } }, ngImport: i0, template: "<mat-form-field [appearance]=\"input.appearance || config.appearance\">\n <mat-label>{{ input.title || '\u0646\u0627\u0645 \u06A9\u0627\u0631\u0628\u0631\u06CC' }}</mat-label>\n @if (formControl.invalid) { <mat-error>{{ formControl.errors | InputErrorPipe : input.type }}</mat-error> }\n\n <!-- HINT -->\n @if (input.hint) { <mat-hint>{{ input.hint }}</mat-hint> }\n\n <!-- BUTTON -->\n @if (input.button) {\n <span matIconSuffix>\n <button\n mat-icon-button\n type=\"button\"\n [disabled]=\"isButtonDisabled\"\n (click)=\"input.button.onClick(values)\"\n [tabIndex]=\"-1\"\n >\n <mat-icon [style.color]=\"isButtonDisabled ? undefined : input.button.color\">\n {{ input.button.icon }}\n </mat-icon>\n </button>\n </span>\n }\n\n <input\n matInput\n type=\"text\"\n [name]=\"input.name\"\n [formControl]=\"formControl\"\n [ngClass]=\"'ngx-form-m3-en'\"\n [AutoFocusDirective]=\"config.autoFocus === input.name\"\n />\n\n <!-- DESCRIPTION -->\n @if (input.description) {\n <div\n class=\"ngx-form-m3-input-description\"\n [class.ngx-form-m3-disabled-input]=\"formControl.disabled\"\n [innerHTML]=\"input.description | MultiLinePipe\"\n ></div>\n }\n</mat-form-field>\n", styles: [""], dependencies: [{ kind: "directive", type: NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "ngmodule", type: ReactiveFormsModule }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.FormControlDirective, selector: "[formControl]", inputs: ["formControl", "disabled", "ngModel"], outputs: ["ngModelChange"], exportAs: ["ngForm"] }, { kind: "component", type: MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: MatIconButton, selector: "button[mat-icon-button], a[mat-icon-button], button[matIconButton], a[matIconButton]", exportAs: ["matButton", "matAnchor"] }, { kind: "ngmodule", type: MatInputModule }, { kind: "directive", type: i2$1.MatInput, selector: "input[matInput], textarea[matInput], select[matNativeControl], input[matNativeControl], textarea[matNativeControl]", inputs: ["disabled", "id", "placeholder", "name", "required", "type", "errorStateMatcher", "aria-describedby", "value", "readonly", "disabledInteractive"], exportAs: ["matInput"] }, { kind: "directive", type: i2$1.MatLabel, selector: "mat-label" }, { kind: "directive", type: i2$1.MatHint, selector: "mat-hint", inputs: ["align", "id"] }, { kind: "directive", type: i2$1.MatError, selector: "mat-error, [matError]", inputs: ["id"] }, { kind: "directive", type: i2$1.MatSuffix, selector: "[matSuffix], [matIconSuffix], [matTextSuffix]", inputs: ["matTextSuffix"] }, { kind: "directive", type: AutoCompleteDirective, selector: "input[type=\"text\"]" }, { kind: "directive", type: AutoFocusDirective, selector: "[AutoFocusDirective]", inputs: ["AutoFocusDirective"] }, { kind: "pipe", type: InputErrorPipe, name: "InputErrorPipe" }, { kind: "pipe", type: MultiLinePipe, name: "MultiLinePipe" }] });
2125
+ }
2126
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.1.4", ngImport: i0, type: InputUsernameComponent, decorators: [{
2127
+ type: Component,
2128
+ args: [{ host: { selector: 'input-username' }, imports: [
2129
+ NgClass,
2130
+ ReactiveFormsModule,
2131
+ MatFormField,
2132
+ MatIcon,
2133
+ MatIconButton,
2134
+ MatInputModule,
2135
+ AutoCompleteDirective,
2136
+ AutoFocusDirective,
2137
+ InputErrorPipe,
2138
+ MultiLinePipe,
2139
+ ], template: "<mat-form-field [appearance]=\"input.appearance || config.appearance\">\n <mat-label>{{ input.title || '\u0646\u0627\u0645 \u06A9\u0627\u0631\u0628\u0631\u06CC' }}</mat-label>\n @if (formControl.invalid) { <mat-error>{{ formControl.errors | InputErrorPipe : input.type }}</mat-error> }\n\n <!-- HINT -->\n @if (input.hint) { <mat-hint>{{ input.hint }}</mat-hint> }\n\n <!-- BUTTON -->\n @if (input.button) {\n <span matIconSuffix>\n <button\n mat-icon-button\n type=\"button\"\n [disabled]=\"isButtonDisabled\"\n (click)=\"input.button.onClick(values)\"\n [tabIndex]=\"-1\"\n >\n <mat-icon [style.color]=\"isButtonDisabled ? undefined : input.button.color\">\n {{ input.button.icon }}\n </mat-icon>\n </button>\n </span>\n }\n\n <input\n matInput\n type=\"text\"\n [name]=\"input.name\"\n [formControl]=\"formControl\"\n [ngClass]=\"'ngx-form-m3-en'\"\n [AutoFocusDirective]=\"config.autoFocus === input.name\"\n />\n\n <!-- DESCRIPTION -->\n @if (input.description) {\n <div\n class=\"ngx-form-m3-input-description\"\n [class.ngx-form-m3-disabled-input]=\"formControl.disabled\"\n [innerHTML]=\"input.description | MultiLinePipe\"\n ></div>\n }\n</mat-form-field>\n" }]
2140
+ }], propDecorators: { values: [{
2141
+ type: Input,
2142
+ args: [{ required: true }]
2143
+ }], isButtonDisabled: [{
2144
+ type: Input,
2145
+ args: [{ required: true }]
2146
+ }] } });
2147
+
2148
+ class InputUsernameMethods extends InputMethods {
2149
+ control(input, validators) {
2150
+ validators.push(UsernameValidator(input.verify));
2151
+ return new FormControl(input.value || null, validators);
2152
+ }
2153
+ value(value, input) {
2154
+ return Helper.IS.string(value) && value !== '' ? value : null;
2155
+ }
2156
+ }
2157
+
1982
2158
  class InputComponent {
1983
2159
  formGroup;
1984
2160
  input;
@@ -2055,7 +2231,9 @@ const InputInfo = {
2055
2231
  TAG: { title: 'تگ', methods: new InputTagMethods(), component: InputTagComponent },
2056
2232
  TEXT: { title: 'متن یک خطی', methods: new InputTextMethods(), component: InputTextComponent },
2057
2233
  TEXTAREA: { title: 'متن چند خطی', methods: new InputTextareaMethods(), component: InputTextareaComponent },
2234
+ TIME: { title: 'ساعت', methods: new InputTimeMethods(), component: InputTimeComponent },
2058
2235
  URL: { title: 'آدرس سایت', methods: new InputUrlMethods(), component: InputUrlComponent },
2236
+ USERNAME: { title: 'نام کاربری', methods: new InputUsernameMethods(), component: InputUsernameComponent },
2059
2237
  };
2060
2238
 
2061
2239
  const NGX_FORM_CONFIG = new InjectionToken('NGX-FORM-CONFIG');