2020-12-29 12:21:10 +08:00
|
|
|
|
---
|
|
|
|
|
title: 扩展现有组件
|
|
|
|
|
---
|
|
|
|
|
|
|
|
|
|
除了新增组件,在 amis 中还能扩展和修改现有组件。
|
|
|
|
|
|
2021-01-11 12:00:41 +08:00
|
|
|
|
## 扩展表单验证
|
|
|
|
|
|
2021-01-11 12:14:51 +08:00
|
|
|
|
如果默认的表单检测规则不满足需求,还可以通过代码的方式扩展。
|
|
|
|
|
|
2023-04-07 13:17:56 +08:00
|
|
|
|
### 普通用法
|
|
|
|
|
|
2021-01-11 12:14:51 +08:00
|
|
|
|
JSSDK 中的用法:
|
2021-01-11 12:00:41 +08:00
|
|
|
|
|
|
|
|
|
```javascript
|
|
|
|
|
let amisLib = amisRequire('amis');
|
|
|
|
|
amisLib.addRule(
|
|
|
|
|
// 校验名
|
|
|
|
|
'isZXS',
|
|
|
|
|
// 校验函数,values 是表单里所有表单项的值,可用于做联合校验;value 是当前表单项的值
|
|
|
|
|
(values, value) => {
|
|
|
|
|
if (
|
|
|
|
|
value === '北京' ||
|
|
|
|
|
value === '上海' ||
|
|
|
|
|
value === '天津' ||
|
|
|
|
|
value === '重庆'
|
|
|
|
|
) {
|
2023-04-07 13:17:56 +08:00
|
|
|
|
// return true 表示校验通过
|
2021-01-11 12:00:41 +08:00
|
|
|
|
return true;
|
|
|
|
|
}
|
2023-04-07 13:17:56 +08:00
|
|
|
|
// return false 表示校验不通过,会进行错误提示
|
2021-01-11 12:00:41 +08:00
|
|
|
|
return false;
|
|
|
|
|
},
|
|
|
|
|
// 出错时的报错信息
|
|
|
|
|
'输入的不是直辖市'
|
|
|
|
|
);
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
这样在配置中就能使用下面的验证方法
|
|
|
|
|
|
|
|
|
|
```
|
|
|
|
|
"validations": {
|
|
|
|
|
"isZXS": true
|
|
|
|
|
}
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
在 React 的使用方法是类似的
|
|
|
|
|
|
|
|
|
|
```javascript
|
|
|
|
|
import {addRule} from 'amis';
|
|
|
|
|
```
|
|
|
|
|
|
2023-04-07 13:17:56 +08:00
|
|
|
|
### 更加灵活的提示错误
|
|
|
|
|
|
|
|
|
|
> `2.9.1` 及以上版本
|
|
|
|
|
|
|
|
|
|
如果想在一个验证函数里根据不同情况提示不同的错误信息,需要返回固定格式的结果:
|
|
|
|
|
|
|
|
|
|
```js
|
|
|
|
|
{
|
|
|
|
|
error: true,
|
|
|
|
|
msg: '错误信息'
|
|
|
|
|
}
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
注意,当返回对象时,`error`必须为`true` 才会判定为错误:
|
|
|
|
|
|
|
|
|
|
具体用法如下:
|
|
|
|
|
|
|
|
|
|
```javascript
|
|
|
|
|
let amisLib = amisRequire('amis');
|
|
|
|
|
amisLib.addRule(
|
|
|
|
|
// 校验名
|
|
|
|
|
'isZXS',
|
|
|
|
|
// 校验函数,values 是表单里所有表单项的值,可用于做联合校验;value 是当前表单项的值
|
|
|
|
|
(values, value) => {
|
|
|
|
|
if (value === '新加坡') {
|
|
|
|
|
// 校验不通过,提示:该地区不在国内
|
|
|
|
|
return {
|
|
|
|
|
error: true,
|
|
|
|
|
msg: '该地区不在国内'
|
|
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (
|
|
|
|
|
value === '北京' ||
|
|
|
|
|
value === '上海' ||
|
|
|
|
|
value === '天津' ||
|
|
|
|
|
value === '重庆'
|
|
|
|
|
) {
|
|
|
|
|
// return true 表示校验通过
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 校验不通过,提示:输入的不是直辖市
|
|
|
|
|
return {
|
|
|
|
|
error: true,
|
|
|
|
|
msg: '输入的不是直辖市'
|
|
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
);
|
|
|
|
|
```
|
|
|
|
|
|
2020-12-29 12:21:10 +08:00
|
|
|
|
## 同时支持多种类型编辑
|
|
|
|
|
|
|
|
|
|
在表单编辑中,每个 name 一般对应一种类型,如果这个 name 有多种类型,比如下面的例子中 id 的值有可能是字符串,也有可能是数字,但 type 只能设置为一种类型,这种情况如何处理?
|
|
|
|
|
|
2021-01-07 23:35:03 +08:00
|
|
|
|
```schema: scope="body"
|
2020-12-29 12:21:10 +08:00
|
|
|
|
{
|
|
|
|
|
"type": "form",
|
|
|
|
|
"mode": "horizontal",
|
2021-06-07 10:09:55 +08:00
|
|
|
|
"body": [
|
2020-12-29 12:21:10 +08:00
|
|
|
|
{
|
|
|
|
|
"name": "id",
|
2021-06-07 10:09:55 +08:00
|
|
|
|
"type": "input-text",
|
2020-12-29 12:21:10 +08:00
|
|
|
|
"label": "id"
|
|
|
|
|
}
|
|
|
|
|
]
|
|
|
|
|
}
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
有两种方式:
|
|
|
|
|
|
|
|
|
|
### 使用另一个名称作为状态
|
|
|
|
|
|
2021-01-07 23:35:03 +08:00
|
|
|
|
```schema: scope="body"
|
2020-12-29 12:21:10 +08:00
|
|
|
|
{
|
|
|
|
|
"type": "form",
|
|
|
|
|
"mode": "horizontal",
|
2021-06-07 10:09:55 +08:00
|
|
|
|
"body": [
|
2020-12-29 12:21:10 +08:00
|
|
|
|
{
|
|
|
|
|
"name": "idIsNumber",
|
|
|
|
|
"type": "switch",
|
|
|
|
|
"label": "id 是数字类型"
|
|
|
|
|
},
|
|
|
|
|
{
|
|
|
|
|
"name": "id",
|
2021-06-07 10:09:55 +08:00
|
|
|
|
"type": "input-text",
|
2020-12-29 12:21:10 +08:00
|
|
|
|
"label": "id",
|
|
|
|
|
"hiddenOn": "data.idIsNumber"
|
|
|
|
|
},
|
|
|
|
|
{
|
|
|
|
|
"name": "id",
|
2021-06-07 10:09:55 +08:00
|
|
|
|
"type": "input-number",
|
2020-12-29 12:21:10 +08:00
|
|
|
|
"label": "id",
|
|
|
|
|
"visibleOn": "data.idIsNumber"
|
|
|
|
|
}
|
|
|
|
|
]
|
|
|
|
|
}
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
可以看到在一个 form 中可以有两个 name 相同的组件,通过 hiddenOn 或 visibleOn 来控制同时只显示一个。
|
|
|
|
|
|
|
|
|
|
### 使用 PipeIn/PipeOut 方法
|
|
|
|
|
|
|
|
|
|
如果不想增加一个新的 name,在 JS SDK 或 React 还有更高级的处理方法,可以增加一个 name 同样为 id 的 switch,实现 PipeIn/PipeOut 函数来进行自动识别,下面是个示例:
|
|
|
|
|
|
|
|
|
|
```javascript
|
|
|
|
|
let amis = amisRequire('amis/embed');
|
|
|
|
|
let amisScoped = amis.embed('#root', {
|
|
|
|
|
type: 'page',
|
|
|
|
|
title: '表单页面',
|
|
|
|
|
// 可以通过去掉下面的注释来测试
|
|
|
|
|
// data: {
|
|
|
|
|
// id: 1
|
|
|
|
|
// },
|
|
|
|
|
body: {
|
|
|
|
|
type: 'form',
|
|
|
|
|
mode: 'horizontal',
|
|
|
|
|
api: '/saveForm',
|
2021-06-07 10:09:55 +08:00
|
|
|
|
body: [
|
2020-12-29 12:21:10 +08:00
|
|
|
|
{
|
|
|
|
|
type: 'switch',
|
|
|
|
|
label: 'id 是数字',
|
|
|
|
|
name: 'id',
|
|
|
|
|
// pipeIn 返回的应该是这个组件所需的值,比如 switch 的返回值就应该是 true 或 false
|
|
|
|
|
// 这里的 value 就是初始值,如果不设置将会是 undefined
|
|
|
|
|
pipeIn: (value, data) => {
|
|
|
|
|
if (typeof value === 'undefined') {
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
return typeof value !== 'string';
|
|
|
|
|
},
|
|
|
|
|
// 这里的 value 是点击 switch 之后的值,比如打开就是 true,关闭就是 false
|
|
|
|
|
pipeOut: (value, oldValue, data) => {
|
|
|
|
|
if (value) {
|
|
|
|
|
return 1; // 切换到数字之后的默认值
|
|
|
|
|
} else {
|
|
|
|
|
return 'id1'; // 关闭之后的默认值
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
},
|
|
|
|
|
{
|
|
|
|
|
name: 'id',
|
|
|
|
|
type: 'text',
|
|
|
|
|
label: 'id',
|
|
|
|
|
visibleOn:
|
|
|
|
|
'typeof data.id === "undefined" || typeof data.id === "string"'
|
|
|
|
|
},
|
|
|
|
|
{
|
|
|
|
|
name: 'id',
|
|
|
|
|
type: 'number',
|
|
|
|
|
label: 'id',
|
|
|
|
|
visibleOn: 'typeof data.id === "number"'
|
|
|
|
|
}
|
|
|
|
|
]
|
|
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
不过这种写法的复杂度较高
|
|
|
|
|
|
|
|
|
|
## 修改组件标签
|
|
|
|
|
|
|
|
|
|
有些组件可以设置 `wrapperComponent`,比如 Form 下默认使用 form 标签,在浏览器中会自带回车提交功能,如果想去掉这个功能,可以将 `wrapperComponent` 设置为 `div`。
|