说在前面
🎈表单是我们平时在很多情况下都会用到的,那么重复的编写表单代码会不会让你感到厌烦呢?如果将其封装成一个可配置组件的话是不是会减少我们很多的工作量。
组件效果
具体效果如上图,组件主要包括三部分,分别是上面头部标题,中间的表单主体以及下面的操作按钮三大部分。
组件实现
组件可以具体划分为这么几部分进行实现:
1、弹窗遮罩
使用一个fixed定位的view元素覆盖整个页面,设置合适的背景颜色、层级和透明度即可。
- wxml
<view bindtap="hideModal" catchtouchmove="preventTouchMove" class="modal-mask" wx:if="{{!hiddenmodalput}}"></view>
- wxss
.modal-mask {
width: 100%;
height: 100%;
position: fixed;
top: 0;
left: 0;
background: #000;
opacity: 0.5;
overflow: hidden;
z-index: 9000;
color: #fff;
}
2、表单组件
2.1 配置规则定义
我们是希望可以通过传入配置信息到组件中,组件就可以生成我们想要的对应的表单呈现出来,那么我们需要先将配置信息的相关规则定义好,如下:
formData:[
{
name:'platform',
cname:'平台|软件',
value:'',
type:'input',
hide:false,
placeholder:'平台|软件',
},
{
name:'account',
cname:'账号',
value:'',
type:'input',
hide:false,
placeholder:'账号',
},
{
name:'password',
cname:'密码',
value:'',
type:'input',
hide:false,
placeholder:'密码',
},
{
name:'mark',
cname:'备注',
value:'',
type:'textarea',
hide:false,
placeholder:'备注',
}
],
上面是我自己定义的一个配置信息规则的例子,这里的配置项主要有6项,分别是:\name
:该表单项的字段名;\cname
:该表单项的中文名;\value
:该表单项的值;\type
:该表单项的展示类型;\hide
:是否展示该表单项;\placeholder
:该表单项的默认提示内容;\
这是我结合自己的需求做出的一个配置,大家可以根据自己的实际需求来制定自己的配置信息。
2.2 配置规则处理
定义好了自己组件的一个配置规则之后,我们就需要在组件中对其进行适配处理了,下面还是以我上面制定的规则为例,简单描述一下处理过程:
- 参数定义
先在组件的properties
中定义好需要父组件传入的参数。
properties: {
formData:Array,
hiddenmodalput:Boolean,
tip:String
},
2.2.1 表单渲染
我们需要根据父组件传入的配置表生成对应的表单项,我们可以根据配置项的type
字段来确定需要生成的表单项类型,如input
为输入框、textarea
为多行文本输入框、date
为日期选择框、time
为时间选择框……更多的类型可以自由扩展,我们只需要在这里进行一次处理,后面调用的时候传入对应的类型即可自动生成,这样可以省去我们很多重复的代码工作,具体实现代码如下:
<view catchtouchmove="preventTouchMove" class="modal-dialog" wx:if="{{!hiddenmodalput}}">
<view class="modal-title">{{tip}}</view>
<view class="modal-content">
<view wx:for="{{showFormData}}" wx:key="index">
<view wx:if="{{!item.hide && item.type=='input'}}" class="modal-input">
<input data-ind="{{index}}" bindinput="inputItem" class="input" maxlength="20" placeholder="{{item.placeholder}}" placeholderClass="input-holder" type="text" value="{{item.value}}"></input>
</view>
<view wx:if="{{!item.hide && item.type=='textarea'}}" class="modal-input">
<textarea data-ind="{{index}}" bindinput="inputItem" class="input" maxlength="20" placeholder="{{item.placeholder}}" placeholderClass="input-holder" type="text" value="{{item.value}}"></textarea>
</view>
<view wx:if="{{!item.hide && item.type=='date'}}" class="modal-input">
<picker data-ind="{{index}}" bindchange="inputItem" class="input-holder" end="2100-01-01" mode="date" start="{{item.value}}" value="{{item.value}}">
<input class="input" disabled="ture" maxlength="20" placeholder="{{item.placeholder}}" placeholderClass="input-holder" type="text" value="{{item.value}}"></input>
</picker>
</view>
<view wx:if="{{!item.hide && item.type=='time'}}" class="modal-input">
<picker data-ind="{{index}}" bindchange="inputItem" class="in" mode="time" start="">
<input class="input" maxlength="20" placeholder="{{item.placeholder}}" placeholderClass="input-holder" type="text" value="{{item.value}}"></input>
</picker>
</view>
</view>
</view>
<view class="modal-footer">
<view bindtap="cancel" class="btn-cancel" data-status="cancel">取消</view>
<view bindtap="confirm" class="btn-confirm" data-status="confirm">确定</view>
</view>
</view>
2.2.2 表单项数据监听
将表单项渲染展示出来之后,我们还需要可以对其进行数据处理,所以我们要监听每一个表单项的数值变化,并实时传递给父组件,父组件也可以及时根据表单项数值的变化进行一些相关的逻辑处理,这里我是这样处理的,我们以input
类型的表单项来举例,代码如下:
<view wx:if="{{!item.hide && item.type=='input'}}" class="modal-input">
<input data-ind="{{index}}" bindinput="inputItem" class="input" maxlength="20" placeholder="{{item.placeholder}}" placeholderClass="input-holder" type="text" value="{{item.value}}"></input>
</view>
看完上面代码可以发现,我们在组件的input事件上绑定了一个函数inputItem
,通过这个函数来进行数据处理,那么让我们继续看看这个函数又进行了什么操作。
inputItem:function(e){
let ind = e.target.dataset.ind;
let val = e.detail.value;
this.triggerEvent("inputItem", {ind:ind,val:val});
},
其实这个函数并没有进行什么特殊的处理,只是将数组变化的表单项下标和变化后的数组传递给父组件。
3、底部按钮
表单在填写完之后往往需要进行一个提交的操作,所以这里我也将确认按钮封装到了组件中。
<view class="modal-footer">
<view bindtap="cancel" class="btn-cancel" data-status="cancel">取消</view>
<view bindtap="confirm" class="btn-confirm" data-status="confirm">确定</view>
</view>
confirm:function(){
this.triggerEvent("confirm",{});
},
cancel:function(){
this.triggerEvent("cancel",{});
}
组件使用
组件封装完了之后我们就该来使用一下试试效果了,那么具体该怎么使用呢?
1、组件引入
需要现在需要使用组件的页面json文件中引入组件
"usingComponents": {
"modalDialog": "../../../components/modalDialog/modalDialog"
},
2、页面中使用
引入之后我们就该在页面中使用了,我们可以直接使用引入时定义的名称作为标签名,将相关的配置信息和事件绑定到组件上即可,代码如下:
- wxml页面
<modalDialog bind:inputItem="inputItem"
bind:cancel="cancel"
bind:confirm="confirm"
hiddenmodalput="{{hiddenmodalput}}"
formData="{{formData}}"
tip="{{tip}}">
</modalDialog>
- 表单配置项
formData:[
{
name:'platform',
cname:'平台|软件',
value:'',
type:'input',
placeholder:'平台|软件',
},
{
name:'account',
cname:'账号',
value:'',
type:'input',
placeholder:'账号',
},
{
name:'password',
cname:'密码',
value:'',
type:'input',
placeholder:'密码',
},
{
name:'mark',
cname:'备注',
value:'',
type:'textarea',
placeholder:'备注',
}
],
tip:'添加信息',
hiddenmodalput:true,
- 表单项数据监听
inputItem:function(e){
let formData = this.data.formData;
formData[e.detail.ind].value = e.detail.val;
this.setData({
formData:formData
});
},
- 取消按钮
cancel: function() {
this.setData({
hiddenmodalput: true
});
this.clearFormData();
},
- 确认按钮
confirm: function() {
this.setData({
hiddenmodalput: true
});
this.clearFormData();
},
源码地址
该组件是在我的一个开源项目中封装使用的,需要查看源码的可以到该项目中查看:\
Gitee源码:https://gitee.com/zheng_yongtao/me-and-my-doodle/tree/master/miniprogram/components/modalDialog
觉得有帮助的同学可以帮忙给我点个star,感激不尽~~~\
有什么想法或者改良可以给我提个pr,十分欢迎~~~\
有什么问题都可以在评论告诉我~~~
说在后面
🎉这里是JYeontu,现在是一名前端工程师,有空会刷刷算法题,平时喜欢打羽毛球🏸 ,平时也喜欢写些东西,既为自己记录📋,也希望可以对大家有那么一丢丢的帮助,写的不好望多多谅解🙇,写错的地方望指出,定会认真改进😊,在此谢谢大家的支持,我们下文再见🙌。