主要参考官方文档和Github
另一插件:ng-dynamic-forms
Example
Expression Properties
根据model的值是否disable等
expressionProperties: {'templateOptions.disabled': '!model.text',}
Form State
options: FormlyFormOptions = {formState: {disabled: true,},}fields: FormlyFieldConfig[] = [{key: 'city',expressionProperties: {// apply expressionProperty for disabled based on formState'templateOptions.disabled': 'formState.disabled',},}];
Default Value
默认值
1. Default the model (preferred)
model = {lastName: 'Smith',};
- Use the defaultValue option on the field
defaultValue: 'This is a default value'
Hide Fields
隐藏表单域hideExpression: '!model.name',
modelOptions
验证方式fields: FormlyFieldConfig[] = [{key: 'city',modelOptions: {debounce: {default: 2000,},modelOptions: {updateOn: 'blur',}modelOptions: {updateOn: 'submit',}}}];
export function RequiredValidatorMessage(err, field: FormlyFieldConfig) {return `"This required field was validated after ${field.formControl.updateOn}"`;}FormlyModule.forRoot({validationMessages: [{name: 'required',message: RequiredValidatorMessage,},],})
Reset Model
作用就是,每当updateInitialValue,之后进行resetModel,model值就恢复为这次updateInitialValue的值。
<button (click)="options.resetModel()">Reset</button><button (click)="options.updateInitialValue()">Update Intial Values</button>
Built-in validations
Angular内置验证
required, min, max, minLength, maxLength, pattern等
{key: 'ip',type: 'input',templateOptions: {label: 'IP Address (pattern = /(\d{1,3}\.){3}\d{1,3}/)',pattern: /(\d{1,3}\.){3}\d{1,3}/,required: true,},validation: {messages: {pattern: (error, field: FormlyFieldConfig) => `"${field.formControl.value}" is not a valid IP Address`,},}
validation
四种方式,主要区别在于是在 FormlyModule.forRoot 中定义,还是field中定义。
文档中的’[As the case above]’一般是指与前面一种方式的定义相同,例如message的定义。
一般采用方式三。
Custom validation
- IP Address (using custom validation declared in ngModule)
IP Address (using custom validation through
validators.validationproperty)IP Address (using custom validation through
validators.expressionproperty)###Validation message
Name (custom validation message declared in ngModule)
- IP Address (custom validation message through
validationproperty)
- IP Address (custom validation message through
validatorsproperty)Async validation and updateOn
``typescript fields: FormlyFieldConfig[] = [ { key: 'text', type: 'input', templateOptions: { label: 'Username (validated onblur`)’, placeholder: ‘Username’, required: true, }, modelOptions: { updateOn: ‘blur’, }, asyncValidators: { uniqueUsername: {
}, }, }, ];expression: (control: FormControl) => {return new Promise((resolve, reject) => {setTimeout(() => {resolve(this.existingUsers.indexOf(control.value) === -1);}, 1000);});},message: 'This username is already taken.',
<a name="PMDue"></a>## Matching Two Fields确认密码<br />主要是 `fieldMatch` 和 `fieldGroup` 两个属性<a name="fk7N0"></a>## Force showing error state初始就显示格式不对```typescriptvalidation: {show: true,}
Toggle required field
Disable submit button
<button [disabled]="!form.valid">Submit</button>
Bind Observables to Select
可以直接用可观察对象赋值给templateOptions,但是不能同步设置model
因此可能还是需要异步处理。
Formly Expressions
You can use hideExpression to hide fields dynamically and Expression Properties for allows you to dynamically change many properties of a field.
export class AppComponent {options = {formState: {// formState.mainModel指向这个表单的modelmainModel: this.model,}}}fields: FormlyFieldConfig[] = [{key: 'country',type: 'input',templateOptions: {label: 'field 2',placeholder: ''},expressionProperties: {'templateOptions.disabled': (model: any, formState: any, field: FormlyFieldConfig) => {// access to the main model can be through `this.model` or `formState` or `modelreturn !formState.mainModel.text},}}]
fields: FormlyFieldConfig[] = [{key: 'country',type: 'input',templateOptions: {label: 'City',placeholder: 'set to 123'},hideExpression: (model: any, formState: any, field: FormlyFieldConfig) => {// access to the main model can be through `this.model` or `formState` or `modelif (formState.mainModel && formState.mainModel.city) {return formState.mainModel.city !== "123"}return true;}}]
关于model和value
- model用于初始化formly的时候的默认值
- html渲染出表单之前,value与model是相同的;渲染之后,value进行了初始化赋值,与model不同了
可以采用setTimeout获得真正的value值
- 对formly克隆,用cloneDeep无法克隆到form(修改克隆的表单,也会触发原表单的modelChange),需要new Group({})才能脱离与原来formly的关系。
关于modelChange
modelChange是对Angular的valueChanges进行的过滤。valueChanges会在form的每个field变更时触发,formly版本5.5.8修改了modelChange,只触发一次。但是何时触发会有一些问题,例如表单重构项目中材质成分字段,修改时不能触发modelChange.
- formly.form.value会在nextTick才更新,用formly.model
- 不能存到ngxs,ngxs为单向数据流,会把对象变为不可扩展

- 多个config导入问题
Extension not called in production mode. #1624
- formly类型和angular类型不一致
API
```typescript /**- An object with a few useful properties
validation.messages: A map of message names that will be displayed when the field has errors.
validation.show: A boolean you as the developer can set to force displaying errors whatever the state of field. This is useful when you’re trying to call the user’s attention to some fields for some reason. */ validation?: { messages?: { [messageProperties: string]: string | ((error: any, field: FormlyFieldConfig) => string); }; show?: boolean;
[additionalProperties: string]: any;
};
/**
- Used to set validation rules for a particular field.
- Should be an object of key - value pairs. The value can either be an expression to evaluate or a function to run.
- Each should return a boolean value, returning true when the field is valid. See Validation for more information. *
- {
- validation?: (string | ValidatorFn)[];
- [key: string]: ((control: AbstractControl, field: FormlyFieldConfig) => boolean) | ({ expression: (control: AbstractControl, field: FormlyFieldConfig) => boolean, message: string | ((error, field: FormlyFieldConfig) => string) });
- } */ validators?: any; ```
