140 lines
3.9 KiB
Vue
140 lines
3.9 KiB
Vue
<template>
|
|
<common-cell :name="name" :required="required">
|
|
<view class="form-content__wrapper" @click="showPopup()">
|
|
<view class="w-0 flex-grow leading-normal text-base line-clamp-2">
|
|
{{ valueStr || '' }}
|
|
</view>
|
|
<!-- <view class="flex-main-content truncate" :class="value ? '' : 'form__placeholder'">
|
|
{{ valueStr || '' }}
|
|
</view> -->
|
|
<uni-icons class="form-arrow" type="arrowright"></uni-icons>
|
|
</view>
|
|
</common-cell>
|
|
<view v-if="show" class="teleport-container">
|
|
<uni-popup ref="popup" type="center" :mask-click="false">
|
|
<view class="bg-white rounded overflow-hidden" style="width: 690rpx;">
|
|
<view class="flex items-center justify-between px-15 py-12 border-b">
|
|
<view class="text-lg font-semibold text-dark">请选择</view>
|
|
<uni-icons type="closeempty" :size="24" color="#999" @click="close"></uni-icons>
|
|
</view>
|
|
<scroll-view scroll-y="true" class="popup-content-scroll">
|
|
<view class="px-15 py-12">
|
|
<view class="flex flex-wrap">
|
|
<view v-for="(i, idx) in range" :key="idx" class="mt-10 mr-5 px-10 py-5 text-base rounded-sm"
|
|
:class="selectMap[idx] ? 'bg-primary border-primary text-white' : 'border'" @click="toggle(i)">
|
|
{{ i }}
|
|
</view>
|
|
</view>
|
|
<view v-if="hasOther" class="mt-10 px-10 py-5 border rounded-sm">
|
|
<input v-model="otherText" class="text-base" placeholder-class="text-base" @input="changeOther($event)" />
|
|
</view>
|
|
<view class="w-full pt-15"></view>
|
|
</view>
|
|
</scroll-view>
|
|
</view>
|
|
</uni-popup>
|
|
</view>
|
|
|
|
</template>
|
|
<script setup>
|
|
import { computed, ref } from 'vue';
|
|
import useDebounce from '@/utils/useDebounce';
|
|
|
|
import commonCell from '../common-cell.vue';
|
|
|
|
const emits = defineEmits(['change']);
|
|
const props = defineProps({
|
|
form: {
|
|
type: Object,
|
|
default: () => ({})
|
|
},
|
|
name: {
|
|
default: ''
|
|
},
|
|
range: {
|
|
type: Array,
|
|
default: () => []
|
|
},
|
|
required: {
|
|
type: Boolean,
|
|
default: false
|
|
},
|
|
disableChange: {
|
|
type: Boolean,
|
|
default: false
|
|
},
|
|
title: {
|
|
default: ''
|
|
}
|
|
})
|
|
|
|
const popup = ref(null);
|
|
const show = ref(false);
|
|
const otherText = ref('');
|
|
const value = computed(() => props.form && Array.isArray(props.form[props.title]) ? props.form[props.title] : [])
|
|
const valueStr = computed(() => value.value.filter(i => i !== '其他').join(','));
|
|
const hasOther = computed(() => value.value.includes('其他'));
|
|
const hasNo = computed(() => value.value.includes('无'));
|
|
const selectMap = computed(() => (props.range || []).map(i => value.value.includes(i)))
|
|
|
|
|
|
const changeOther = useDebounce(() => {
|
|
let val = value.value.filter(i => (props.range || []).includes(i));
|
|
if (otherText.value) {
|
|
val.push(otherText.value);
|
|
}
|
|
emits('change', {
|
|
title: props.title,
|
|
value: val
|
|
})
|
|
})
|
|
|
|
function close() {
|
|
popup.value?.close();
|
|
show.value = false;
|
|
}
|
|
|
|
function showPopup() {
|
|
if (props.disableChange) return;
|
|
show.value = true;
|
|
const others = value.value.filter(i => !props.range.includes(i));
|
|
otherText.value = others.length ? others.join(',') : '';
|
|
setTimeout(() => {
|
|
popup.value?.open();
|
|
}, 750)
|
|
}
|
|
|
|
function toggle(i) {
|
|
let val = [...value.value];
|
|
if (i === '无') {
|
|
val = hasNo.value ? [] : ['无'];
|
|
} else if (i === '其他') {
|
|
if (hasOther.value) {
|
|
val = val.filter(v => v !== '其他');
|
|
otherText.value = '';
|
|
} else {
|
|
val = val.filter(v => v !== '无');
|
|
val.push('其他');
|
|
otherText.value = '';
|
|
}
|
|
} else if (val.includes(i)) {
|
|
val = val.filter(v => v !== i);
|
|
} else {
|
|
val = val.filter(v => v !== '无');
|
|
val.push(i);
|
|
}
|
|
emits('change', {
|
|
title: props.title,
|
|
value: val
|
|
})
|
|
console.log(value.value);
|
|
}
|
|
|
|
</script>
|
|
<style>
|
|
@import '../cell-style.css';
|
|
|
|
.popup-content-scroll {
|
|
max-height: 65vh;
|
|
}
|
|
</style> |