天津投入产出系统安卓前端
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 

704 lines
25 KiB

<template>
<view class="form-container">
<view class="form-box">
<block v-for="(item, index) in formData" :key="item.rules.name">
<view class="form-item flex-row--c">
<!-- 单行文本框 -->
<view class="line" v-if="['text','password','number','code'].includes(item.type)">
<view :class="item.rules.verify ? 'line-left' : 'p-l14 line-left'"
>
<text class="colorRed" v-if="item.rules.verify">*</text>
<text class="num" v-if="num">{{ index + 1 }}.</text>
{{ item.label }}
</view
>
<!-- 发送验证码 -->
<view class="line-right send-code-box" v-if="item.type === 'code'">
<input
:type="item.type"
class="input"
placeholder-class="plaClass"
:placeholder="item.placeholder"
v-model="item.rules.value"
@input="inputVal(index)"
/>
<view style="width:250rpx">
<u-button
size="mini"
type="primary"
:disabled="item.disabled||isSend"
@click="sendCode(item)"
>
{{ codeFont }}
</u-button>
</view>
</view>
<!-- 普通输入框 -->
<view class="line-right" v-else>
<input
:type="item.type"
class="input"
placeholder-class="plaClass"
:placeholder="item.placeholder"
v-model="item.rules.value"
:disabled="item.disabled"
@input="inputVal(index)"
/>
</view>
</view>
<!-- 下拉选择-->
<view class="line" v-else-if="['select','time'].includes(item.type)">
<view :class="item.rules.verify ? 'line-left' : 'p-l14 line-left'"
>
<text class="colorRed" v-if="item.rules.verify">*</text>
<text class="num" v-if="num">{{ index + 1 }}.</text>
{{ item.label }}
</view
>
<view class="line-right">
<input
disabled
type="text"
class="input"
placeholder-class="plaClass"
:placeholder="item.placeholder"
v-model="item.rules.label"
@click="item.show = true"
/>
<view class="select-icon"></view>
</view>
<u-select
v-if="item.type === 'select'"
:title="item.title"
v-model="item.show"
:list="item.list"
value-name="value"
label-name="name"
@confirm="selectConfirm($event,item)"
></u-select>
<!--类型为时间-->
<u-picker v-else-if="item.type === 'time'"
:params="item.params"
mode="time"
v-model="item.show"
@confirm="selectTime($event,item)">
</u-picker>
</view>
<!-- 多行文本框 -->
<view class="textarea-box" v-else-if="item.type == 'textarea'">
<view :class="item.rules.verify ? 'line-left' : 'p-l14 line-left'"
>
<text class="colorRed" v-if="item.rules.verify">*</text>
<text class="num" v-if="num">{{ index + 1 }}.</text>
{{ item.label }}
</view
>
<view class="line-bottom-textarea">
<textarea
rows=""
style="color: #a7a7a7; font-size: 28rpx"
auto-height
:maxlength="-1"
cols=""
placeholder-class="plaClass"
:disabled="item.disabled"
:placeholder="item.placeholder"
v-model="item.rules.value"
@input="inputVal(index)"
>
</textarea>
</view>
</view>
<!-- 上传图片 -->
<view class="img-box flex-col-l" v-else-if="item.type == 'file'">
<view style="font-size:26rpx" :class="item.rules.verify ? '' : 'p-l14 '">
<text class="colorRed" v-if="item.rules.verify">*</text>
<text class="num" v-if="num">{{ index + 1 }}.</text>
{{ item.label }}
</view>
<view class="img-upload p30">
<u-upload
:auto-upload="false"
:fileList="item.rules.fileList"
:disabled="item.disabled"
:accept="item.accept"
:capture="item.capture"
:maxCount="item.maxCount"
:sizeType="item.sizeType"
:compressed="item.compressed"
:camera="item.camera"
:multiple="item.multiple"
:maxSize="item.maxSize"
:previewImage="item.previewImage"
width="150rpx"
height="150rpx"
@on-choose-complete="afterRead($event,item)"
@on-remove="deletePic($event,item)"
></u-upload>
</view>
</view>
<!-- 单选框 -->
<view class="line-col" v-else-if="item.type === 'radio'">
<view :class="item.rules.verify ? 'line-left' : 'p-l14 line-left'"
>
<text class="colorRed" v-if="item.rules.verify">*</text>
<text class="num" v-if="num">{{ index + 1 }}.</text>
{{ item.label }}
<text style="font-size: 20rpx; color: #9e9e9e; margin-left: 23rpx; width: 140rpx">(单选)
</text>
</view
>
<view class="line-bottom-select" :style="{ 'padding-left': num ? '60rpx' : '34rpx' }">
<u-radio-group :currentIndex="index" v-model="item.rules.value"
@change="radioChange($event, index)">
<u-radio
icon-size="35"
label-size="25"
shape="circle"
v-for="(radioItem, radioIndex) in item.list"
:key="radioIndex"
:name="radioItem.value"
:disabled="radioItem.disabled"
>{{ radioItem.label }}
</u-radio
>
</u-radio-group>
</view>
</view>
<!-- 多选框 -->
<view class="line-col" v-else-if="item.type == 'checkbox'">
<view :class="item.rules.verify ? 'line-left' : 'p-l14 line-left'"
>
<text class="colorRed" v-if="item.rules.verify">*</text>
<text class="num" v-if="num">{{ index + 1 }}.</text>
{{ item.label }}
<text style="font-size: 20rpx; color: #9e9e9e; margin-left: 23rpx; width: 140rpx">(多选)
</text>
</view>
<view class="line-bottom-select" :style="{ 'padding-left': num ? '60rpx' : '34rpx' }">
<u-checkbox-group @change="checkboxGroupChange($event,item)">
<u-checkbox
icon-size="35"
label-size="25"
v-model="checkboxItem.checked"
v-for="(checkboxItem, checkboxIndex) in item.list"
:key="checkboxIndex"
:name="checkboxItem.value"
:disabled="checkboxItem.disabled"
>{{ checkboxItem.name }}
</u-checkbox
>
</u-checkbox-group>
</view>
</view>
<!-- 手机输入框 -->
<view class="line" v-else-if="item.type === 'mobile'">
<view :class="item.rules.verify ? 'line-left' : 'p-l14 line-left'"
>
<text class="colorRed" v-if="item.rules.verify">*</text>
<text class="num" v-if="num">{{ index + 1 }}.</text>
{{ item.label }}
</view
>
<view class="line-right">
<input
type="number"
v-model="item.rules.value"
:placeholder="item.placeholder"
@input="inputVal(index)"
class="input"
:maxlength="11"
/>
<view style="width:250rpx">
<u-button
v-if="item.oneKeyPhone"
size="mini"
type="primary"
open-type="getPhoneNumber"
@getphonenumber="getphonenumber"
:disabled="item.disabled"
>一键获取
</u-button>
</view>
</view>
</view>
</view>
</block>
</view>
</view>
</template>
<script>
import mixins from "./mixins";
export default {
name: "activeForm",
mixins: [mixins],
data() {
return {
submitData: "",
selectBox: [],
currentSelectIndex: "",
currentSelectValue: "",
codeFont: "获取验证码",
wait: 60,
isSend: false,
sendColor: "color:#ff5b01",
};
},
props: {
//是否展示序号
num: {
type: Boolean,
default: false,
},
formData: {
type: Array,
default: () => {
return [];
},
},
},
computed: {
// formData: {
// get() {
// // checkbox回显
// this.value.forEach(item => {
// if (item.type === "checkbox") {
// item.list.forEach(item2 => {
// item2.checked = item.rules.value.includes(item2.value)
// })
// }
// })
// console.log("this.formData", this.value)
// return this.value
// },
// set(nval) {
// this.$emit("input", nval);
// }
// }
},
methods: {
//input输入框的值传给父组件
inputVal(index) {
const data = {
val: this.formData[index].rules.value,
index: index,
};
if (String(data.val) != "" && String(data.index) != "") {
this.formData[data.index].rules.value = data.val;
}
this.$emit("input", this.formData);
},
// 单选 下拉框点击确定
selectConfirm($event, item) {
item.rules.label = $event[0].label;
item.rules.value = $event[0].value;
this.$emit("input", this.formData);
// console.log("this.formData", this.formData)
},
selectTime({year, month, day, hour, minute, second}, item) {
let date = ''
if (year) {
date += year + '-'
}
if (month) {
date += month + '-'
}
if (day) {
date += day
}
if (hour) {
date += ' ' + hour
}
if (minute) {
date += ':' + minute
}
if (second) {
date += ':' + second
}
item.rules.value = date
item.rules.label = date;
this.$emit("input", this.formData);
console.log("this.formData", this.formData)
},
//单选 点击触发
radioChange($event, index) {
this.$emit("input", this.formData);
console.log("this.formData", this.formData)
},
//复选框 点击触发
checkboxGroupChange($event, item) {
console.log("param; :>> ", $event, item);
item.rules.value = $event;
this.$emit("input", this.formData);
},
// 删除图片
deletePic($event, item) {
item.rules.fileList.splice($event.index, 1)
this.$emit('input', this.formData)
console.log("this.formData", this.formData)
},
// 新增图片
afterRead($event, item) {
// 当设置 mutiple 为 true 时, file 为数组格式,否则为对象格式
console.log("$event, item", $event, item)
item.rules.fileList = item.multiple ? $event : $event
this.$emit('input', this.formData)
console.log("this.formData", this.formData)
},
// 发送验证码
sendCode(item) {
let setTime = 0;
this.sendCodeCallback(item)
if (!this.isSend) {
this.isSend = true;
setTime = setInterval(() => {
this.wait--;
this.codeFont = this.wait + "重新发送";
if (this.wait === 0) {
clearInterval(setTime);
this.codeFont = "获取验证码";
this.isSend = false;
this.wait = 60;
}
}, 1000);
}
},
//校验
$vervify() {
return new Promise((resolve, reject) => {
this.formData.forEach((item) => {
if (item.rules.verify) {
switch (item.type) {
case "checkbox":
if (item.rules.value.length === 0) {
uni.showToast({
title: item.rules.errMess || "请选择" + item.label,
duration: 2000,
icon: "none",
});
reject(false)
// throw Error(); //终止函数
}
break;
case "file":
if (item.rules.fileList.length === 0) {
uni.showToast({
title: item.rules.errMess || "请选择" + item.label,
duration: 2000,
icon: "none",
});
reject(false)
// throw Error(); //终止函数
}
break;
case "mobile":
if (!item.rules.value) {
uni.showToast({
title: item.rules.errMess || "手机号不能为空",
duration: 2000,
icon: "none",
});
reject(false)
// throw Error(); //终止函数
}
if (!/^\s{0}$|^1\d{10}$/.test(item.rules.value)) {
uni.showToast({
title: "手机格式错误",
duration: 2000,
icon: "none",
});
reject(false)
// throw Error(); //终止函数
}
break;
default:
if ([null, undefined, ''].includes(item.rules.value)) {
uni.showToast({
title: item.rules.errMess || item.label + "不能为空",
duration: 2000,
icon: "none",
});
reject(false)
// throw Error(); //终止函数
}
if (item.rules.regexp && !(new RegExp(item.rules.regexp).test(item.rules.value))) {
uni.showToast({
title: item.label + "格式不正确",
duration: 2000,
icon: "none",
});
reject(false)
// throw Error(); //终止函数
}
break;
}
}
});
resolve(this.$submitForm())
})
},
// 提交序列化的表单
$submitForm() {
const formData = this.formData
let submitData = {};
for (let i = 0; i < formData.length; i++) {
if (formData[i].type === 'file') {
submitData[formData[i].rules.name] = formData[i].rules.fileList;
break;
}
submitData[formData[i].rules.name] = formData[i].rules.value;
}
return submitData;
},
//重置表单
resetForm() {
// for (let key in this.formData) {
// if (this.formData.hasOwnProperty(key)) {
// switch (typeof this.formData[key]) {
// case "object":
// this.formData[key] = []
// break
// case "number":
// this.formData[key] = ''
// break
// case "string":
// this.formData[key] = ''
// break
// }
// }
// }
// this.$emit("input", this.formData);
for (let item of this.formData) {
item.rules.value =""
}
this.$emit("input", this.formData);
}
},
};
</script>
<style lang="scss" scoped>
.img-box{
padding-top: 30rpx;
.img-upload{
padding-top: 30rpx;
}
}
// 弹框
.select-modal {
position: fixed;
left: 0;
top: 0;
width: 100%;
height: 100%;
z-index: 300000;
.select-bg {
width: 100%;
height: 100%;
background: rgba(0, 0, 0, 0.3);
}
.select-box {
position: absolute;
left: 0;
bottom: -1000upx;
width: 100%;
background: #fff;
max-height: 50%;
// height: 0%;
overflow: auto;
.select-title {
display: flex;
justify-content: space-between;
height: 80rpx;
background: #f5f5f5;
line-height: 80rpx;
padding: 0 30rpx;
}
.select-item {
font-size: 28rpx;
color: #333;
border-bottom: 1px solid #eee;
height: 75rpx;
line-height: 75rpx;
padding: 0 30rpx;
i {
display: block;
float: right;
border-bottom: 4rpx solid #1ca032;
border-right: 4rpx solid #1ca032;
width: 12rpx;
height: 26rpx;
transform: rotate(45deg);
margin-top: 24.5rpx;
}
}
}
}
// 下拉icon
.select-icon {
float: right;
border-bottom: 2rpx solid #999;
border-right: 2rpx solid #999;
width: 16rpx;
height: 16rpx;
transform: rotate(-45deg);
margin-right: 30rpx;
}
.color-999 {
color: #999;
}
.plaClass {
text-align: right;
font-size: 26rpx;
}
.form-container {
.form-box {
width: 100%;
box-sizing: border-box;
}
.colorRed {
color: red;
padding: 0 10rpx;
}
.line-right {
flex: 1;
height: 100%;
display: flex;
align-items: center;
justify-content: space-between;
position: relative;
}
.line-bottom-select {
padding-top: 40rpx;
}
.line-bottom-textarea {
padding-top: 20rpx;
textarea {
min-height: 100rpx;
}
}
.line-left {
display: flex;
min-width: 22%;
align-items: center;
height: 100%;
letter-spacing: 0.5px;
font-size: 26rpx;
// font-weight: 550;
color: #000000;
box-sizing: border-box;
}
.p-l14 {
padding-left: 34rpx;
}
.textarea-box {
// display: flex;
width: 100%;
border-bottom: 1px solid #ededed;
padding-top: 20rpx;
// align-items: center;
textarea {
padding-left: 32rpx;
height: 100rpx;
font-size: 25rpx;
color: #333;
}
}
.line {
padding: 27rpx 0;
// min-height: 100rpx;
display: flex;
align-items: center;
width: 100%;
margin: 0 auto;
border-bottom: 1px solid #ededed;
overflow: hidden;
.input {
padding-right: 20rpx;
padding-left: 20rpx;
height: 100%;
width: 100%;
text-align: left;
font-size: 28rpx;
color: #333;
border: none;
overflow: hidden;
text-overflow: ellipsis;
outline: none;
}
}
.line-col {
padding: 27rpx 0;
// min-height: 100rpx;
display: flex;
flex-direction: column;
width: 100%;
margin: 0 auto;
border-bottom: 1px solid #ededed;
overflow: hidden;
.input {
padding-right: 20rpx;
height: 100%;
width: 100%;
text-align: left;
font-size: 28rpx;
color: #333;
border: none;
overflow: hidden;
text-overflow: ellipsis;
outline: none;
}
}
.num {
margin-right: 8rpx;
}
}
</style>