ngx-validator
Version:
It is an angular library which has custom input and validation component, custom validation directive and form template generator, which work on data based on typesript class property decorators. Custom validation directive replaces html input validator
1 lines • 88.4 kB
Source Map (JSON)
{"version":3,"file":"ngx-validator.mjs","sources":["../../../projects/ngx-validator/src/lib/ngx-validator.service.ts","../../../projects/ngx-validator/src/lib/reflect-input.models.ts","../../../projects/ngx-validator/src/lib/reflector-functions.ts","../../../projects/ngx-validator/src/lib/value-accessor.ts","../../../projects/ngx-validator/src/lib/validate.ts","../../../projects/ngx-validator/src/lib/element-base.ts","../../../projects/ngx-validator/src/lib/ngx-custom-template-for.directive.ts","../../../projects/ngx-validator/src/lib/ngx-dropdown-for/ngx-dropdown-for.component.ts","../../../projects/ngx-validator/src/lib/ngx-dropdown-for/ngx-dropdown-for.component.html","../../../projects/ngx-validator/src/lib/ngx-validator.directive.ts","../../../projects/ngx-validator/src/lib/ngx-validator-for/ngx-validator-for.component.ts","../../../projects/ngx-validator/src/lib/ngx-validator-for/ngx-validator-for.component.html","../../../projects/ngx-validator/src/lib/ngx-label-for/ngx-label-for.component.ts","../../../projects/ngx-validator/src/lib/ngx-label-for/ngx-label-for.component.html","../../../projects/ngx-validator/src/lib/ngx-input-for/ngx-input-for.component.ts","../../../projects/ngx-validator/src/lib/ngx-input-for/ngx-input-for.component.html","../../../projects/ngx-validator/src/lib/ngx-form-for-reactive/ngx-form-for-reactive.component.ts","../../../projects/ngx-validator/src/lib/ngx-form-for-reactive/ngx-form-for-reactive.component.html","../../../projects/ngx-validator/src/lib/ngx-form-for/ngx-form-for.component.ts","../../../projects/ngx-validator/src/lib/ngx-form-for/ngx-form-for.component.html","../../../projects/ngx-validator/src/lib/ngx-validator.module.ts","../../../projects/ngx-validator/src/public-api.ts","../../../projects/ngx-validator/src/ngx-validator.ts"],"sourcesContent":["import { Injectable } from '@angular/core';\n\n@Injectable({\n providedIn: 'root'\n})\nexport class NgxValidatorService {\n\n constructor() { }\n}\n","export interface ParamInputModel {\r\n value?: any;\r\n field?: string;\r\n error: string;\r\n customValue?: any;\r\n customFunc?: (propertyValue: any, dataModel?: any) => boolean;\r\n}\r\n\r\nexport interface RangeInputModel {\r\n min?: number | Date;\r\n max?: number | Date;\r\n error: string;\r\n}\r\n\r\nexport enum DataTypeEnum {\r\n Int,\r\n Number,\r\n MultilineText,\r\n Url,\r\n ImageUrl,\r\n Password,\r\n Hexadecimal,\r\n Date,\r\n Array,\r\n Upload\r\n}\r\n\r\nexport interface DecoratorReturnModel {\r\n key: string;\r\n value: any;\r\n}\r\n\r\nexport interface CssInputModel {\r\n group?: string;\r\n label?: string;\r\n input?: string;\r\n error?: string;\r\n}\r\n\r\nexport type PropertyFunction<T> = () => T;\r\n","import 'reflect-metadata';\r\nimport { ParamInputModel, RangeInputModel, DecoratorReturnModel, DataTypeEnum } from './reflect-input.models';\r\n\r\n\r\nfunction isEmpty(obj) {\r\n for (const key in obj) {\r\n if (obj.hasOwnProperty(key)) {\r\n return false;\r\n }\r\n }\r\n return true;\r\n}\r\n\r\n\r\n// tslint:disable-next-line:callable-types\r\nexport function ModelState<T extends { new(...args: any[]): {} }>(constructor: T) {\r\n\r\n return class extends constructor {\r\n /**\r\n * Returns model validation state\r\n */\r\n IsValid() {\r\n for (const item of Reflect.getMetadataKeys(this)) {\r\n const attribs = getDecorators(this, item);\r\n for (const attrib of attribs.filter(x => x.key !== 'ReadOnly' && x.key !== 'NoForm')) {\r\n const messg = ngxValidate(attrib.key, attrib.value, this[item], this);\r\n if (messg) {\r\n return false;\r\n }\r\n }\r\n }\r\n return true;\r\n }\r\n /**\r\n * Placeholder(string)\r\n * Validate: function\r\n */\r\n ModelErrors(): { [key: string]: { [key: string]: any } } {\r\n const errs: { [key: string]: any } = {};\r\n let tmp: { [key: string]: any } = {};\r\n for (const item of Reflect.getMetadataKeys(this)) {\r\n const attribs = getDecorators(this, item);\r\n for (const attrib of attribs.filter(x => x.key !== 'ReadOnly' && x.key !== 'NoForm')) {\r\n const messg = ngxValidate(attrib.key, attrib.value, this[item], this);\r\n if (messg) {\r\n tmp[attrib.key] = messg;\r\n }\r\n }\r\n if (!isEmpty(tmp)) {\r\n errs[item] = tmp;\r\n }\r\n tmp = {};\r\n }\r\n return errs;\r\n }\r\n };\r\n}\r\n/**\r\n * Validates field if it has valid value according to value parameter\r\n */\r\nexport function DataType(param: { value: DataTypeEnum, error?: string }) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, param, target);\r\n Reflect.defineMetadata('custom-reflect:DataType', param, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Validates field if it represents valid credit card number\r\n */\r\nexport function CreditCard(param: { error: string }) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, param, target);\r\n Reflect.defineMetadata('custom-reflect:CreditCard', param, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Compares field to other field and checks if they are equal\r\n */\r\nexport function Compare(param: { field: string, error: string }) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, param, target);\r\n Reflect.defineMetadata('custom-reflect:Compare', param, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Validates if field value contains specific value\r\n */\r\nexport function Contains(param: { value: string, error: string }) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, param, target);\r\n Reflect.defineMetadata('custom-reflect:Contains', param, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Validates field according to custom logic\r\n */\r\nexport function Custom(param: { value?: any, error: string, customFunc: (...args: any[]) => any }) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, param, target);\r\n Reflect.defineMetadata('custom-reflect:Custom', param, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Sets the name metadata for the field\r\n */\r\nexport function Name(param: string) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, param, target);\r\n Reflect.defineMetadata('custom-reflect:Name', param, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Validates field and checks if it has null, undefined or empty value\r\n */\r\nexport function Required(param: string) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, param, target);\r\n Reflect.defineMetadata('custom-reflect:Required', param, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Validates field if other field has specific value and checks if it has null, undefined or empty value\r\n */\r\nexport function RequiredIf(param: { field: string, value: any, error: string }) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, param, target);\r\n Reflect.defineMetadata('custom-reflect:RequiredIf', param, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Sets field's input value to readonly\r\n */\r\nexport function ReadOnly() {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, propertyKey, target);\r\n Reflect.defineMetadata('custom-reflect:ReadOnly', null, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Validates if field has valid value according to specified pattern\r\n */\r\nexport function Pattern(param: { value: RegExp, error: string }) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, param, target);\r\n Reflect.defineMetadata('custom-reflect:Pattern', param, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Validates if field has valid value more than specific value\r\n */\r\nexport function MinValue(input: { value: number | Date, error: string }) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, input, target);\r\n Reflect.defineMetadata('custom-reflect:MinValue', input, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Validates if field has valid value less than specific value\r\n */\r\nexport function MaxValue(input: { value: number | Date, error: string }) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, input, target);\r\n Reflect.defineMetadata('custom-reflect:MaxValue', input, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Validates if field value does not contain specific value\r\n */\r\nexport function NotContains(param: { value: string, error: string }) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, param, target);\r\n Reflect.defineMetadata('custom-reflect:NotContains', param, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Tells form generator component not to generate input for this field\r\n */\r\nexport function NoForm() {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, propertyKey, target);\r\n Reflect.defineMetadata('custom-reflect:NoForm', null, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Validates if field value length fits in min and max values\r\n */\r\nexport function StringLength(input: { min?: number, max?: number, error: string }) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, input, target);\r\n Reflect.defineMetadata('custom-reflect:StringLength', input, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Validates if field value is valid email value\r\n */\r\nexport function Email(input: string) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, input, target);\r\n Reflect.defineMetadata('custom-reflect:Email', input, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Sets placeholder value for field input\r\n */\r\nexport function Placeholder(input: string) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, input, target);\r\n Reflect.defineMetadata('custom-reflect:Placeholder', input, target, propertyKey);\r\n };\r\n}\r\n\r\n/**\r\n * Validates if field value length fits in min and max values\r\n */\r\nexport function Range(input: { min?: number | Date, max?: number | Date, error: string }) {\r\n return (target: any, propertyKey: string) => {\r\n Reflect.defineMetadata(propertyKey, input, target);\r\n Reflect.defineMetadata('custom-reflect:Range', input, target, propertyKey);\r\n };\r\n}\r\n\r\nexport function configurable(value: boolean) {\r\n return (target: any, propertyKey: string, descriptor: PropertyDescriptor) => {\r\n descriptor.configurable = value;\r\n };\r\n}\r\n\r\n/**\r\n * Placeholder(string)\r\n * Validate: function\r\n */\r\nexport function getDecorators(target: any, propertyName: string | symbol): DecoratorReturnModel[] {\r\n const keys: any[] = Reflect.getMetadataKeys(target, propertyName);\r\n\r\n const decorators = keys.filter(key => key.toString().startsWith('custom-reflect:'))\r\n .reduce((values, key) => {\r\n const value = Reflect.getMetadata(key, target, propertyName);\r\n return values.concat({ key: key.toString().replace('custom-reflect:', ''), value });\r\n }, []);\r\n return decorators;\r\n}\r\n\r\nexport function ngxValidate(key: string, param: string | ParamInputModel | RangeInputModel, value: any, dataModel?: any): string {\r\n\r\n let retstr: string;\r\n\r\n if ((value === null || value === undefined || value === '') && key !== 'Required' && key !== 'RequiredIf'\r\n && key !== 'Compare' && key !== 'Range') {\r\n return null;\r\n }\r\n let errorString = '';\r\n if (typeof param === 'string') {\r\n errorString = param;\r\n } else {\r\n errorString = param.error;\r\n }\r\n if (!errorString) {\r\n errorString = 'error not asigned!';\r\n }\r\n switch (key) {\r\n case 'CreditCard': {\r\n value = value.replace(/[- ]+/g, '');\r\n\r\n const Visa = /^4[0-9]{12}(?:[0-9]{3})?$/;\r\n const MasterCard = /^(?:5[1-5][0-9]{2}|222[1-9]|22[3-9][0-9]|2[3-6][0-9]{2}|27[01][0-9]|2720)[0-9]{12}$/;\r\n const Amex = /^3[47][0-9]{13}$/;\r\n const DinersClub = /^3(?:0[0-5]|[68][0-9])[0-9]{11}$/;\r\n const Discover = /^6(?:011|5[0-9]{2})[0-9]{12}$/;\r\n const JCB = /^(?:2131|1800|35\\d{3})\\d{11}$/;\r\n const BCGlobal = /^(6541|6556)[0-9]{12}$/;\r\n const CarteBlanche = /^389[0-9]{11}$/;\r\n const InstaPayment = /^63[7-9][0-9]{13}$/;\r\n const KoreanLocalCard = /^9[0-9]{15}$/;\r\n const Laser = /^(6304|6706|6709|6771)[0-9]{12,15}$/;\r\n const Maestro = /^(5018|5020|5038|6304|6759|6761|6763)[0-9]{8,15}$/;\r\n const Solo = /^(6334|6767)[0-9]{12}|(6334|6767)[0-9]{14}|(6334|6767)[0-9]{15}$/;\r\n // tslint:disable-next-line:max-line-length\r\n const Switch = /^(4903|4905|4911|4936|6333|6759)[0-9]{12}|(4903|4905|4911|4936|6333|6759)[0-9]{14}|(4903|4905|4911|4936|6333|6759)[0-9]{15}|564182[0-9]{10}|564182[0-9]{12}|564182[0-9]{13}|633110[0-9]{10}|633110[0-9]{12}|633110[0-9]{13}$/;\r\n const UnionPay = /^(62[0-9]{14,17})$/;\r\n\r\n if (!checkLuhn(value) ||\r\n !(Visa.test(value) || MasterCard.test(value) || Amex.test(value) || DinersClub.test(value)\r\n || Discover.test(value) || JCB.test(value) || BCGlobal.test(value) || CarteBlanche.test(value)\r\n || InstaPayment.test(value) || KoreanLocalCard.test(value) || Laser.test(value)\r\n || Maestro.test(value) || Solo.test(value) || Switch.test(value) || UnionPay.test(value) ||\r\n ((param as ParamInputModel).customValue && (param as ParamInputModel).customValue.test(value)))) {\r\n retstr = (param as ParamInputModel).error;\r\n }\r\n break;\r\n }\r\n case 'Compare': {\r\n if (value !== dataModel[(param as ParamInputModel).field]) {\r\n retstr = errorString;\r\n }\r\n break;\r\n }\r\n case 'Contains': {\r\n if (value.indexOf((param as ParamInputModel).value) === -1) {\r\n retstr = errorString;\r\n }\r\n break;\r\n }\r\n case 'Custom': {\r\n const result = (param as ParamInputModel).customFunc(value, dataModel);\r\n if (!result) {\r\n retstr = errorString;\r\n }\r\n break;\r\n }\r\n case 'DataType': {\r\n if ((param as ParamInputModel).value === DataTypeEnum.Number) {\r\n const reg = /^[+-]?\\d+(\\.\\d+)?$/;\r\n if (isNaN(parseFloat(value)) || !reg.test(value)) {\r\n retstr = errorString;\r\n }\r\n }\r\n if ((param as ParamInputModel).value === DataTypeEnum.Date) {\r\n if (!(value instanceof Date)) {\r\n retstr = errorString;\r\n }\r\n }\r\n if ((param as ParamInputModel).value === DataTypeEnum.Hexadecimal) {\r\n const expression = /^([0-9a-fA-F]+)$/i;\r\n if (!expression.test(value)) {\r\n retstr = errorString;\r\n }\r\n }\r\n if ((param as ParamInputModel).value === DataTypeEnum.Int) {\r\n const reg = /^[+\\-]?\\d+$/;\r\n if (isNaN(parseFloat(value))\r\n || !isNaN(parseFloat(value)) && (parseFloat(value) - parseInt(value, 10) !== 0)\r\n || !reg.test(value)) {\r\n retstr = errorString;\r\n }\r\n }\r\n if ((param as ParamInputModel).value === DataTypeEnum.Array) {\r\n if (!Array.isArray(value)) {\r\n retstr = errorString;\r\n }\r\n }\r\n break;\r\n }\r\n case 'NotContains': {\r\n if (value.indexOf((param as ParamInputModel).value) !== -1) {\r\n retstr = errorString;\r\n }\r\n break;\r\n }\r\n case 'Required': {\r\n if (value === null || value === undefined || value === '') {\r\n retstr = errorString;\r\n }\r\n break;\r\n }\r\n case 'RequiredIf': {\r\n if (!(param as ParamInputModel).field || !(param as ParamInputModel).value) {\r\n console.warn('incorrect parameters in RequiredIf attribute');\r\n } else {\r\n if (((param as ParamInputModel).value === dataModel[(param as ParamInputModel).field])\r\n && (value === null || value === undefined || value === '')) {\r\n retstr = errorString;\r\n }\r\n }\r\n break;\r\n }\r\n case 'Pattern': {\r\n const pat = (param as ParamInputModel).value;\r\n if (!pat.test(value)) {\r\n retstr = errorString;\r\n }\r\n break;\r\n }\r\n case 'MinValue': {\r\n if (value < (param as ParamInputModel).value) {\r\n retstr = errorString.replace('{0}', (param as ParamInputModel).value.toString());\r\n }\r\n break;\r\n }\r\n case 'MaxValue': {\r\n if (value > (param as ParamInputModel).value) {\r\n retstr = errorString.replace('{0}', (param as ParamInputModel).value.toString());\r\n }\r\n break;\r\n }\r\n case 'StringLength': {\r\n if (!value || value.length < (param as RangeInputModel).min || value.length > (param as RangeInputModel).max) {\r\n retstr = errorString.replace('{0}', (param as RangeInputModel).min\r\n .toString())\r\n .replace('{1}', (param as RangeInputModel).max.toString());\r\n }\r\n break;\r\n }\r\n case 'Range': {\r\n if (value < (param as RangeInputModel).min || value > (param as RangeInputModel).max) {\r\n retstr = errorString.replace('{0}', (param as RangeInputModel).min\r\n .toString())\r\n .replace('{1}', (param as RangeInputModel).max.toString());\r\n }\r\n break;\r\n }\r\n case 'Email': {\r\n // credits http://emailregex.com/\r\n // tslint:disable-next-line:max-line-length\r\n const emreg = /^(([^<>()\\[\\]\\\\.,;:\\s@\"]+(\\.[^<>()\\[\\]\\\\.,;:\\s@\"]+)*)|(\".+\"))@((\\[[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}])|(([a-zA-Z\\-0-9]+\\.)+[a-zA-Z]{2,}))$/;\r\n if (!emreg.test(value)) {\r\n retstr = errorString;\r\n }\r\n break;\r\n }\r\n default: {\r\n retstr = null;\r\n break;\r\n }\r\n }\r\n\r\n return retstr;\r\n}\r\n\r\nfunction checkLuhn(value: string): boolean {\r\n // credits https://github.com/JamesEggers1/node-luhn\r\n const trimmed = String(value).replace(/[\\s]/g, '');\r\n const length = trimmed.length;\r\n let odd = false;\r\n let total = 0;\r\n let calc;\r\n let calc2;\r\n\r\n if (length === 0) {\r\n return true;\r\n }\r\n\r\n if (!/^[0-9]+$/.test(trimmed)) {\r\n return false;\r\n }\r\n\r\n for (let i = length; i > 0; i--) {\r\n calc = parseInt(trimmed.charAt(i - 1), 10);\r\n if (!odd) {\r\n total += calc;\r\n } else {\r\n calc2 = calc * 2;\r\n\r\n switch (calc2) {\r\n case 10: calc2 = 1; break;\r\n case 12: calc2 = 3; break;\r\n case 14: calc2 = 5; break;\r\n case 16: calc2 = 7; break;\r\n case 18: calc2 = 9; break;\r\n default: calc2 = calc2;\r\n }\r\n total += calc2;\r\n }\r\n odd = !odd;\r\n }\r\n return (total !== 0 && (total % 10) === 0);\r\n}\r\n","// credits to https://github.com/clbond/form-example\n\nimport { ControlValueAccessor, NgControl } from '@angular/forms';\nimport { Injector } from '@angular/core';\n\nexport abstract class ValueAccessorBase<T> implements ControlValueAccessor {\n private innerValue: T;\n private onChange = null;\n private onTouch = null;\n public disabled: boolean;\n private control: NgControl;\n\n protected get formControl(): NgControl {\n if (this.control != null) {\n return this.control;\n }\n\n this.control = this.theInjector.get(NgControl, null);\n return this.control;\n }\n\n get value(): T {\n return this.innerValue;\n }\n\n set value(value: T) {\n if (this.innerValue !== value) {\n this.innerValue = value;\n if (this.onChange) {\n this.onChange(value);\n }\n }\n }\n\n constructor(private theInjector: Injector) {\n }\n\n writeValue(value: T): void {\n this.innerValue = value;\n if (this.onChange) {\n this.onChange(value);\n }\n }\n\n registerOnChange(fn: any): void {\n this.onChange = fn;\n }\n\n registerOnTouched(fn: any): void {\n this.onTouch = fn;\n }\n\n setDisabledState(disabled: boolean): void {\n this.disabled = disabled;\n }\n\n touch() {\n if (this.onTouch) {\n this.onTouch();\n }\n }\n\n}\n","import { AbstractControl, ValidationErrors } from '@angular/forms';\r\nimport { ngxValidate, getDecorators } from './reflector-functions';\r\n\r\nexport function validateControl(control: AbstractControl, dataModel: any): ValidationErrors {\r\n let name: string;\r\n if (control.parent) {\r\n for (const item of Object.keys(control.parent.controls)) {\r\n if (control.parent.controls[item] === control) {\r\n name = item;\r\n }\r\n }\r\n } else {\r\n name = this.field;\r\n }\r\n const attribs = getDecorators(dataModel, name);\r\n const errs: { [validator: string]: string } = {};\r\n\r\n if (attribs.find(x => x.key === 'ReadOnly')) {\r\n this.el.nativeElement.setAttribute('readonly', true);\r\n }\r\n\r\n for (const item of attribs.filter(x => x.key !== 'ReadOnly' && x.key !== 'NoForm')) {\r\n const messg = ngxValidate(item.key, item.value, control.value, dataModel);\r\n if (messg) {\r\n errs[item.key] = messg;\r\n }\r\n }\r\n return errs;\r\n}\r\n","import { Injector, Input, Directive } from '@angular/core';\r\nimport { AbstractControl, NgModel, ValidationErrors } from '@angular/forms';\r\nimport { ValueAccessorBase } from './value-accessor';\r\nimport { validateControl } from './validate';\r\n\r\n@Directive()\r\nexport abstract class ElementBase<T> extends ValueAccessorBase<T> {\r\n protected abstract ngModel: NgModel;\r\n\r\n @Input()\r\n model: any;\r\n\r\n validator: (control: AbstractControl, dataModel: any) => ValidationErrors;\r\n\r\n constructor(protected injector: Injector) {\r\n super(injector);\r\n this.validator = validateControl;\r\n }\r\n\r\n validate(control: AbstractControl): ValidationErrors {\r\n return this.validator(control, this.model);\r\n }\r\n}\r\n","import { Directive, TemplateRef, ViewContainerRef, Input } from '@angular/core';\n\n@Directive({\n // tslint:disable-next-line:directive-selector\n selector: '[ngxCustomTemplateFor]'\n})\nexport class NgxCustomTemplateForDirective {\n\n @Input()\n ngxCustomTemplateFor: string;\n\n constructor(\n public templateRef: TemplateRef<any>,\n private viewContainer: ViewContainerRef) { }\n}\n","import { Component, OnInit, ViewChild, ElementRef, Injector, ContentChildren, QueryList, Input, HostBinding } from '@angular/core';\nimport { NgModel, NG_VALUE_ACCESSOR, NG_VALIDATORS } from '@angular/forms';\nimport { DataTypeEnum } from '../reflect-input.models';\nimport { getDecorators } from '../reflector-functions';\nimport { ElementBase } from '../element-base';\nimport { NgxCustomTemplateForDirective } from '../ngx-custom-template-for.directive';\n\n@Component({\n // tslint:disable-next-line:component-selector\n selector: 'ngx-dropdown-for',\n templateUrl: './ngx-dropdown-for.component.html',\n providers: [{ provide: NG_VALUE_ACCESSOR, useExisting: NgxDropdownForComponent, multi: true },\n { provide: NG_VALIDATORS, useExisting: NgxDropdownForComponent, multi: true }\n ],\n})\nexport class NgxDropdownForComponent extends ElementBase<any> implements OnInit {\n\n DataTypeEnum = DataTypeEnum;\n placeHolder = '';\n name = '';\n template: NgxCustomTemplateForDirective;\n readonly = false;\n\n @HostBinding('class.ngx-dropdown')\n ngxDropdown = true;\n\n @Input()\n itemSource: any[] = [];\n\n @Input()\n field: string;\n\n @Input()\n key: string;\n\n @Input()\n valuePrimitive = true;\n\n @Input()\n text: string;\n\n @ViewChild(NgModel, { static: false })\n ngModel: NgModel;\n\n @Input()\n defaultItem = true;\n\n @ContentChildren(NgxCustomTemplateForDirective, { descendants: false })\n set templates(value: QueryList<NgxCustomTemplateForDirective>) {\n if (this.model) {\n value.forEach((item) => {\n this.template = item;\n });\n }\n }\n\n constructor(public el: ElementRef, protected injector: Injector) {\n super(injector);\n }\n\n ngOnInit() {\n\n if (!this.model) {\n console.error('ngx-validator error! [model] property is not binded!');\n }\n\n if (this.field === null || this.field === undefined) {\n this.field = this.el.nativeElement.getAttribute('name') === null\n ? this.el.nativeElement.getAttribute('id')\n : this.el.nativeElement.getAttribute('name');\n }\n\n if (!this.field) {\n this.field = this.el.nativeElement.getAttribute('formControlName');\n }\n\n const attribs = getDecorators(this.model, this.field);\n\n if (attribs.find(x => x.key === 'Placeholder')) {\n this.placeHolder = attribs.find(x => x.key === 'Placeholder').value;\n }\n\n if (attribs.find(x => x.key === 'ReadOnly')) {\n this.readonly = true;\n }\n\n if (attribs.find(x => x.key === 'Name')) {\n this.name = attribs.find(x => x.key === 'Name').value;\n } else {\n this.name = this.field;\n }\n }\n\n}\n","<select\n [(ngModel)]=\"value\"\n [ngStyle]=\"{'color':'red'}\"\n class=\"ngx-dropdown-child\">\n <option\n value=\"undefined\"\n disabled\n class=\"ngx-dropdown-child-default\"\n selected\n hidden\n *ngIf=\"defaultItem\">\n {{placeHolder}}\n </option>\n <ng-container *ngIf=\"valuePrimitive; else nonPrimitve\">\n <option\n *ngFor=\"let item of itemSource\"\n [ngValue]=\"item[key]\">\n {{item[text]}}\n </option>\n </ng-container>\n <ng-template #nonPrimitve>\n <option\n *ngFor=\"let item of itemSource\"\n [ngValue]=\"item\">\n {{item[text]}}\n </option>\n </ng-template>\n</select>\n","import { Directive, Input, ElementRef } from '@angular/core';\nimport { NG_VALIDATORS, Validator, AbstractControl, ValidationErrors } from '@angular/forms';\nimport { validateControl } from './validate';\n\n@Directive({\n // tslint:disable-next-line:directive-selector\n selector: '[ngx-validator][ngModel],[ngx-validator][formControl],[ngx-validator][formControlName]',\n providers: [\n { provide: NG_VALIDATORS, useExisting: NgxValidatorDirective, multi: true }\n ]\n})\nexport class NgxValidatorDirective implements Validator {\n\n validator: (control: AbstractControl, model: any) => ValidationErrors;\n\n private dataModel: any;\n\n @Input()\n field: string;\n\n @Input('ngx-validator')\n set sk(value: any) {\n this.dataModel = value;\n }\n\n constructor(private el: ElementRef) {\n this.validator = validateControl;\n }\n\n validate(control: AbstractControl): ValidationErrors {\n return this.validator(control, this.dataModel);\n }\n\n}\n","import { Component, Input, HostBinding } from '@angular/core';\n\n@Component({\n // tslint:disable-next-line:component-selector\n selector: 'ngx-validator-for',\n templateUrl: './ngx-validator-for.component.html'\n})\nexport class NgxValidatorForComponent {\n\n messages: any[] = [];\n\n @HostBinding('class.ngx-validator')\n ngxLabel = true;\n\n @Input('errors')\n set errors(value: any) {\n this.messages = [];\n if (value) {\n for (const item of Object.keys(value)) {\n this.messages.push(value[item].toString());\n }\n }\n }\n}\n","<div class=\"ngx-validator-child\">\n <div *ngFor=\"let message of messages\">\n <ng-container *ngIf=\"message\">{{message | translate}}</ng-container>\n </div>\n</div>\n","import { Component, OnInit, Input, HostBinding } from '@angular/core';\nimport { getDecorators } from '../reflector-functions';\n\n@Component({\n // tslint:disable-next-line:component-selector\n selector: 'ngx-label-for',\n templateUrl: './ngx-label-for.component.html'\n})\nexport class NgxLabelForComponent implements OnInit {\n\n @Input()\n model: any;\n\n @Input()\n field: string;\n\n @HostBinding('class.ngx-label')\n ngxLabel = true;\n\n reflectValue = '';\n\n ngOnInit() {\n try {\n this.reflectValue = getDecorators(this.model, this.field).find(x => x.key === 'Name').value;\n } catch {\n this.reflectValue = this.field;\n }\n }\n}\n","<label\r\n for=\"{{field}}\"\r\n class=\"ngx-label-child\">\r\n {{reflectValue | translate}}\r\n</label>\r\n","import { Component, OnInit, Input, ViewChild, ElementRef, TemplateRef, ContentChildren, QueryList,\n HostBinding, Injector, forwardRef, HostListener, Output, EventEmitter } from '@angular/core';\nimport { NgModel, NG_VALUE_ACCESSOR, NG_VALIDATORS, FormControlName } from '@angular/forms';\nimport { getDecorators } from '../reflector-functions';\nimport { DataTypeEnum, ParamInputModel } from '../reflect-input.models';\nimport { NgxCustomTemplateForDirective } from '../ngx-custom-template-for.directive';\nimport { ElementBase } from '../element-base';\n\n@Component({\n // tslint:disable-next-line:component-selector\n selector: 'ngx-input-for',\n templateUrl: './ngx-input-for.component.html',\n providers: [{ provide: NG_VALUE_ACCESSOR, useExisting: forwardRef(() => NgxInputForComponent), multi: true },\n { provide: NG_VALIDATORS, useExisting: NgxInputForComponent, multi: true }\n ]\n})\n\nexport class NgxInputForComponent extends ElementBase<any> implements OnInit {\n\n DataTypeEnum = DataTypeEnum;\n dataType: number;\n placeHolder = '';\n name = '';\n // tslint:disable-next-line:variable-name\n _template: NgxCustomTemplateForDirective;\n autocomplete: string;\n\n @Input()\n dataItems: any[];\n\n @Output()\n blurEvent: EventEmitter<any> = new EventEmitter();\n\n readonly = false;\n @Input()\n field: string;\n\n @ViewChild(NgModel, { static: false })\n ngModel: NgModel;\n\n @ViewChild(FormControlName, { static: false })\n formControlName: FormControlName;\n\n @HostBinding('class.ngx-input')\n ngxInput = true;\n\n @HostListener('focusout') onFocusout() {\n this.blurEvent.emit();\n }\n\n @ContentChildren(NgxCustomTemplateForDirective, { descendants: false })\n set templates(value: QueryList<NgxCustomTemplateForDirective>) {\n if (this.model) {\n value.forEach((item) => {\n this._template = item;\n });\n }\n }\n\n constructor(public el: ElementRef, protected injector: Injector) {\n super(injector);\n }\n\n ngOnInit() {\n\n if (!this.model) {\n console.error('ngx-validator error! [model] property is not binded!');\n }\n\n if (this.field === null || this.field === undefined) {\n this.field = this.el.nativeElement.getAttribute('name') === null\n ? this.el.nativeElement.getAttribute('id')\n : this.el.nativeElement.getAttribute('name');\n }\n\n if (!this.field) {\n this.field = this.el.nativeElement.getAttribute('formControlName');\n }\n\n this.autocomplete = this.el.nativeElement.getAttribute('autocomplete');\n\n const attribs = getDecorators(this.model, this.field);\n if (attribs.find(x => x.key === 'DataType')) {\n this.dataType = (attribs.find(x => x.key === 'DataType').value as ParamInputModel).value;\n }\n\n if (attribs.find(x => x.key === 'Placeholder')) {\n this.placeHolder = attribs.find(x => x.key === 'Placeholder').value;\n }\n\n if (attribs.find(x => x.key === 'ReadOnly')) {\n this.readonly = true;\n }\n\n if (attribs.find(x => x.key === 'Name')) {\n this.name = attribs.find(x => x.key === 'Name').value;\n } else {\n this.name = this.field;\n }\n }\n\n getTemplate(): TemplateRef<any> {\n return this._template.templateRef;\n }\n}\n","<ng-container [ngSwitch]=\"dataType\">\n <ng-container *ngIf=\"!_template; else template\">\n <a\n [href]=\"value\"\n *ngSwitchCase=\"DataTypeEnum.Url\"\n class=\"ngx-input-child-url\"\n [id]=\"field\">\n {{name | translate}}\n </a>\n <input\n type=\"password\"\n *ngSwitchCase=\"DataTypeEnum.Password\"\n [placeholder]=\"placeHolder | translate\"\n [(ngModel)]=\"value\"\n [id]=\"field\"\n autocomplete=\"{{autocomplete}}\"\n [disabled]=\"this.disabled\"\n class=\"ngx-input-child\"\n [readOnly]=\"readonly\">\n <img\n *ngSwitchCase=\"DataTypeEnum.ImageUrl\"\n [src]=\"value\"\n class=\"ngx-input-child-image\"\n [id]=\"field\">\n <input\n type=\"file\"\n *ngSwitchCase=\"DataTypeEnum.Upload\"\n [placeholder]=\"placeHolder | translate\"\n [(ngModel)]=\"value\"\n [id]=\"field\"\n autocomplete=\"{{autocomplete}}\"\n [disabled]=\"this.disabled\"\n class=\"ngx-input-child-upload\"\n [readOnly]=\"readonly\">\n <textarea\n *ngSwitchCase=\"DataTypeEnum.MultilineText\"\n [placeholder]=\"placeHolder | translate\"\n [(ngModel)]=\"value\"\n [id]=\"field\"\n [disabled]=\"this.disabled\"\n class=\"ngx-input-child-textarea\"\n rows=\"5\"\n [readOnly]=\"readonly\"></textarea>\n <input\n *ngSwitchDefault\n type=\"text\"\n [placeholder]=\"placeHolder | translate\"\n [(ngModel)]=\"value\"\n autocomplete=\"{{autocomplete}}\"\n [id]=\"field\"\n [disabled]=\"this.disabled\"\n class=\"ngx-input-child\"\n [readOnly]=\"readonly\"\n [name]=\"field\">\n </ng-container>\n <ng-template #template>\n <ng-container\n [ngTemplateOutlet]=\"getTemplate()\"\n [ngTemplateOutletContext]=\"{$implicit: model}\">\n </ng-container>\n </ng-template>\n</ng-container>\n","import { Component, OnInit, Input, ViewChild, Output, EventEmitter, ContentChildren, QueryList, TemplateRef } from '@angular/core';\r\nimport { NgForm, UntypedFormGroup } from '@angular/forms';\r\nimport { getDecorators } from '../reflector-functions';\r\nimport { CssInputModel } from '../reflect-input.models';\r\nimport { NgxCustomTemplateForDirective } from '../ngx-custom-template-for.directive';\r\n\r\n@Component({\r\n // tslint:disable-next-line:component-selector\r\n selector: 'ngx-form-for-reactive',\r\n templateUrl: './ngx-form-for-reactive.component.html'\r\n})\r\nexport class NgxFormForReactiveComponent implements OnInit {\r\n\r\n // tslint:disable-next-line:variable-name\r\n _model: any;\r\n // tslint:disable-next-line:variable-name\r\n _formGroup: UntypedFormGroup;\r\n\r\n @Input()\r\n cssClasses: CssInputModel;\r\n\r\n @Input()\r\n set model(value: any) {\r\n this._model = value;\r\n }\r\n\r\n\r\n @Input()\r\n set formGroup(value: UntypedFormGroup) {\r\n this._formGroup = value;\r\n for (const item of Object.keys(this._model)) {\r\n const attribs = getDecorators(this._model, item);\r\n if (!attribs.find(x => x.key === 'NoForm') && this._formGroup.controls[item]) {\r\n this.propertyNames.push({ field: item, template: false });\r\n }\r\n }\r\n }\r\n\r\n @Input()\r\n autoComplete: string;\r\n\r\n @ViewChild(NgForm, { static: false })\r\n form: NgForm;\r\n\r\n propertyNames: { field: string, template: boolean }[] = [];\r\n\r\n @Output()\r\n submitForm = new EventEmitter<any>();\r\n\r\n // tslint:disable-next-line:variable-name\r\n _templates: NgxCustomTemplateForDirective[] = [];\r\n\r\n @ContentChildren(NgxCustomTemplateForDirective, { descendants: false })\r\n set templates(value: QueryList<NgxCustomTemplateForDirective>) {\r\n if (this._model) {\r\n value.forEach((item) => {\r\n if (this.propertyNames.find(x => x.field === item.ngxCustomTemplateFor)) {\r\n this._templates.push(item);\r\n this.propertyNames.find(x => x.field === item.ngxCustomTemplateFor).template = true;\r\n } else {\r\n throw (new Error(`Property name bound on NgxCustomTemplateForDirective ${item.ngxCustomTemplateFor} not found.\r\n If it is definity correct, please check if you have initialized it before passing model to ngx-form-for component`));\r\n }\r\n });\r\n }\r\n }\r\n\r\n constructor() {\r\n }\r\n\r\n ngOnInit() {\r\n }\r\n\r\n getTemplate(field: string): TemplateRef<any> {\r\n return this._templates.find(x => x.ngxCustomTemplateFor === field).templateRef;\r\n }\r\n submit() {\r\n this.submitForm.emit(this._model);\r\n }\r\n\r\n controlExists(item: string) {\r\n if (this.formGroup.controls[item]) {\r\n return true;\r\n } else {\r\n return false;\r\n }\r\n }\r\n}\r\n","<form\n #form=\"ngForm\"\n (ngSubmit)=\"submit()\"\n [autocomplete]=\"autoComplete\"\n [formGroup]=\"_formGroup\">\n <div\n [ngClass]=\"cssClasses? cssClasses.group: 'ngx-form-for'\"\n *ngFor=\"let item of propertyNames\">\n <ng-container *ngIf=\"!item.template; else template\">\n <ngx-label-for\n [model]=\"_model\"\n [field]=\"item.field\"\n [ngClass]=\"cssClasses? cssClasses.label:''\"></ngx-label-for>\n <ngx-input-for\n [formControlName]=\"item.field\"\n [model]=\"_model\"\n [ngClass]=\"cssClasses? cssClasses.input:''\"></ngx-input-for>\n <ngx-validator-for\n [errors]=\"_formGroup.get(item.field)?.errors\"\n [ngClass]=\"cssClasses? cssClasses.error: ''\">\n </ngx-validator-for>\n </ng-container>\n <ng-template #template>\n <!-- temporary form validation workaround. custom temlpate is not binded to form's controls and therefore, form validation doesn't work. help needed -->\n <input\n [formControlName]=\"item.field\"\n [ngx-validator]=\"_model\"\n style=\"display:none\">\n <ng-container\n [ngTemplateOutlet]=\"getTemplate(item.field)\"\n [ngTemplateOutletContext]=\"{$implicit: {model: _model, form: form}}\">\n </ng-container>\n </ng-template>\n </div>\n <button\n type=\"submit\"\n [disabled]=\"form.invalid\"\n class=\"btn btn-success\">\n Submit\n </button>\n</form>\n","import { Component, OnInit, Input, TemplateRef, ViewChild, ContentChildren, QueryList, Output, EventEmitter } from '@angular/core';\nimport { NgForm } from '@angular/forms';\nimport { NgxCustomTemplateForDirective } from '../ngx-custom-template-for.directive';\nimport { getDecorators } from '../reflector-functions';\nimport { CssInputModel } from '../reflect-input.models';\n\n@Component({\n // tslint:disable-next-line:component-selector\n selector: 'ngx-form-for',\n templateUrl: './ngx-form-for.component.html'\n})\nexport class NgxFormForComponent implements OnInit {\n\n // tslint:disable-next-line:variable-name\n _model: any;\n\n @Input()\n set model(value: any) {\n this._model = value;\n\n for (const item of Object.keys(this._model)) {\n const attribs = getDecorators(this._model, item);\n if (!attribs.find(x => x.key === 'NoForm')) {\n this.propertyNames.push({ field: item, template: false });\n }\n }\n\n for (const item of Reflect.getMetadataKeys(this._model)) {\n const attribs = getDecorators(this._model, item);\n if (!attribs.find(x => x.key === 'NoForm') && this.propertyNames.find(x => x.field === item) === undefined) {\n this.propertyNames.push({ field: item, template: false });\n }\n }\n }\n\n @Input()\n cssClasses: CssInputModel;\n\n @Input()\n autoComplete: string;\n\n @ViewChild(NgForm, { static: false })\n form: NgForm;\n\n propertyNames: { field: string, template: boolean }[] = [];\n\n @Output()\n submitForm = new EventEmitter<any>();\n\n // tslint:disable-next-line:variable-name\n _templates: NgxCustomTemplateForDirective[] = [];\n\n @ContentChildren(NgxCustomTemplateForDirective, { descendants: false })\n set templates(value: QueryList<NgxCustomTemplateForDirective>) {\n if (this._model) {\n value.forEach((item) => {\n if (this.propertyNames.find(x => x.field === item.ngxCustomTemplateFor)) {\n this._templates.push(item);\n this.propertyNames.find(x => x.field === item.ngxCustomTemplateFor).template = true;\n } else {\n throw (new Error(`Property name bound on NgxCustomTemplateForDirective ${item.ngxCustomTemplateFor} not found.\n If it is definity correct, please check if you have initialized it before passing model to ngx-form-for component`));\n }\n });\n }\n }\n\n constructor() {\n }\n\n ngOnInit() {\n }\n\n getTemplate(field: string): TemplateRef<any> {\n return this._templates.find(x => x.ngxCustomTemplateFor === field).templateRef;\n }\n submit() {\n this.submitForm.emit(this._model);\n }\n}\n","<form\n #form=\"ngForm\"\n (ngSubmit)=\"submit()\"\n [autocomplete]=\"autoComplete\">\n <div\n [ngClass]=\"cssClasses?.group? cssClasses.group : 'ngx-form-for'\"\n *ngFor=\"let item of propertyNames\">\n <ng-container *ngIf=\"!item.template; else template\">\n <ngx-label-for\n [model]=\"_model\"\n [field]=\"item.field\"\n [ngClass]=\"cssClasses?.label ? cssClasses?.label: ''\"></ngx-label-for>\n <ngx-input-for\n [id]=\"item.field\"\n [model]=\"_model\"\n [(ngModel)]=\"_model[item.field]\"\n [ngModelOptions]=\"{ name: item.field }\"\n [field]=\"item.field\"\n [ngClass]=\"cssClasses?.input ? cssClasses.input: ''\"></ngx-input-for>\n <ngx-validator-for\n [errors]=\"form.controls[item.field]?.errors\"\n [ngClass]=\"cssClasses?.error ? cssClasses.error: ''\">\n </ngx-validator-for>\n </ng-container>\n <ng-template #template>\n <!-- temporary form validation workaround. custom temlpate is not binded to form's controls and therefore, form validation doesn't work. help needed -->\n <input\n [name]=\"item.field\"\n [(ngModel)]=\"_model[item.field]\"\n [ngx-validator]=\"_model\"\n style=\"display:none\">\n <ng-container\n [ngTemplateOutlet]=\"getTemplate(item.field)\"\n [ngTemplateOutletContext]=\"{$implicit: {model: _model, form: form}}\">\n </ng-container>\n </ng-template>\n </div>\n <button\n type=\"submit\"\n [disabled]=\"form.invalid\"\n class=\"btn btn-success\">\n Submit\n </button>\n</form>\n","import { NgModule } from '@angular/core';\r\nimport { NgxValidatorForComponent } from './ngx-validator-for/ngx-validator-for.component';\r\nimport { NgxLabelForComponent } from './ngx-label-for/ngx-label-for.component';\r\nimport { NgxInputForComponent } from './ngx-input-for/ngx-input-for.component';\r\nimport { NgxFormForReactiveComponent } from './ngx-form-for-reactive/ngx-form-for-reactive.component';\r\nimport { NgxFormForComponent } from './ngx-form-for/ngx-form-for.component';\r\nimport { NgxDropdownForComponent } from './ngx-dropdown-for/ngx-dropdown-for.component';\r\nimport { NgxValidatorDirective } from './ngx-validator.directive';\r\nimport { NgxCustomTemplateForDirective } from './ngx-custom-template-for.directive';\r\nimport { CommonModule } from '@angular/common';\r\nimport { FormsModule, ReactiveFormsModule } from '@angular/forms';\r\nimport { TranslateModule } from '@ngx-translate/core';\r\n\r\n\r\n\r\n@NgModule({\r\n imports: [\r\n CommonModule,\r\n FormsModule,\r\n ReactiveFormsModule,\r\n TranslateModule\r\n ],\r\n declarations: [\r\n NgxValidatorDirective,\r\n NgxValidatorForComponent,\r\n NgxLabelForComponent,\r\n NgxInputForComponent,\r\n NgxFormForReactiveComponent,\r\n NgxFormForComponent,\r\n NgxDropdownForComponent,\r\n NgxCustomTemplateForDirective\r\n ],\r\n exports: [\r\n NgxValidatorDirective,\r\n NgxValidatorForComponent,\r\n NgxLabelForComponent,\r\n NgxInputForComponent,\r\n NgxFormForReactiveComponent,\r\n NgxFormForComponent,\r\n NgxDropdownForComponent,\r\n NgxCustomTemplateForDirective\r\n ]\r\n})\r\nexport class NgxValidatorModule { }\r\n","/*\r\n * Public API Surface of ngx-validator\r\n */\r\n\r\nexport * from './lib/ngx-validator.service';\r\nexport * from './lib/ngx-dropdown-for/ngx-dropdown-for.component';\r\nexport * from './lib/ngx-form-for-reactive/ngx-form-for-reactive.component';\r\nexport * from './lib/ngx-form-for/ngx-form-for.component';\r\nexport * from './lib/ngx-input-for/ngx-input-for.component';\r\nexport * from './lib/ngx-label-for/ngx-label-for.component';\r\nexport * from './lib/ngx-validator-for/ngx-validator-for.component';\r\nexport * from './lib/ngx-validator.directive';\r\nexport * from './lib/ngx-validator.module';\r\nexport * from './lib/reflector-functions';\r\nexport * from './lib/reflect-input.models';\r\nexport * from './lib/ngx-custom-template-for.directive';","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":["i2","i1","i3","i3.NgxValidatorDirective","i4.NgxValidatorForComponent","i5.NgxLabelForComponent","i6.NgxInputForComponent"],"mappings":";;;;;;;;;;MAKa,mBAAmB,CAAA;AAE9B,IAAA,WAAA,GAAA,GAAiB;8GAFN,mBAAmB,EAAA,IAAA,EAAA,EAAA,EAAA,MAAA,EAAA,EAAA,CAAA,eAAA,CAAA,UAAA,EAAA,CAAA,CAAA,EAAA;AAAnB,IAAA,SAAA,IAAA,CAAA,KAAA,GAAA,EAAA,CAAA,qBAAA,CAAA,EAAA,UAAA,EAAA,QAAA,EAAA,OAAA,EAAA,QAAA,EAAA,QAAA,EAAA,EAAA,EAAA,IAAA,EAAA,mBAAmB,cAFlB,MAAM,EAAA,CAAA,CAAA,EAAA;;2FAEP,mBAAmB,EAAA,UAAA,EAAA,CAAA;kBAH/B,UAAU;AAAC,YAAA,IAAA,EAAA,CAAA;AACV,oBAAA,UAAU,EAAE,MAAM;AACnB,iBAAA,CAAA;;;ICUW,aAWX;AAXD,CAAA,UAAY,YAAY,EAAA;AACpB,IAAA,YAAA,CAAA,YAAA,CAAA,KAAA,CAAA,GAAA,CAAA,CAAA,GAAA,KAAG,CAAA;AACH,IAAA,YAAA,CAAA,YAAA,CAAA,QAAA,CAAA,GAAA,CAAA,CAAA,GAAA,QAAM,CAAA;AACN,IAAA,YAAA,CAAA,YAAA,CAAA,eAAA,CAAA,GAAA,CAAA,CAAA,GAAA,eAAa,CAAA;AACb,IAAA,YAAA,CAAA,YAAA,CAAA,KAAA,CAAA,GAAA,CAAA,CAAA,GAAA,KAAG,CAAA;AACH,IAAA,YAAA,CAAA,YAAA,CAAA,UAAA,CAAA,GAAA,CAAA,CAAA,GAAA,UAAQ,CAAA;AACR,IAAA,YAAA,CAAA,YAAA,CAAA,UAAA,CAAA,GAAA,CAAA,CAAA,GAAA,UAAQ,CAAA;AACR,IAAA,YAAA,CAAA,YAAA,CAAA,aAAA,CAAA,GAAA,CAAA,CAAA,GAAA,aAAW,CAAA;AACX,IAAA,YAAA,CAAA,YAAA,CAAA,MAAA,CAAA,GAAA,CAAA,CAAA,GAAA,MAAI,CAAA;AACJ,IAAA,YAAA,CAAA,YAAA,CAAA,OAAA,CAAA,GAAA,CAAA,CAAA,GAAA,OAAK,CAAA;AACL,IAAA,YAAA,CAAA,YAAA,CAAA,QAAA,CAAA,GAAA,CAAA,CAAA,GAAA,QAAM,CAAA;AACV,CAAC,EAXW,YAAY,KAAZ,YAAY,GAWvB,EAAA,CAAA,CAAA;;ACrBD,SAAS,OAAO,CAAC,GAAG,EAAA;AAChB,IAAA,KAAK,MAAM,GAAG,IAAI,GAAG,EAAE;AACnB,QAAA,IAAI,GAAG,CAAC,cAAc,CAAC,GAAG,CAAC,EAAE;AACzB,YAAA,OAAO,KAAK,CAAC;SAChB;KACJ;AACD,IAAA,OAAO,IAAI,CAAC;AAChB,CAAC;AAGD;AACM,SAAU,UAAU,CAAwC,WAAc,EAAA;IAE5E,OAAO,cAAc,WAAW,CAAA;AAC5B;;AAEG;QACH,OAAO,GAAA;YACH,KAAK,MAAM,IAAI,IAAI,OAAO,CAAC,eAAe,CAAC,IAAI,CAAC,EAAE;gBAC9C,MAAM,OAAO,GAAG,aAAa,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC;gBAC1C,KAAK,MAAM,MAAM,IAAI,OAAO,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,CAAC,GAAG,KAAK,UAAU,IAAI,CAAC,CAAC,GAAG,KAAK,QAAQ,CAAC,EAAE;AAClF,oBAAA,MAAM,KAAK,GAAG,WAAW,CAAC,MAAM,CAAC,GAAG,EAAE,MAAM,CAAC,KAAK,EAAE,IA