地区组件改造完成
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
<template>
|
||||
<section class="AiAreaPicker">
|
||||
<ai-search-popup mode="bottom" ref="areaSelector">
|
||||
<ai-search-popup mode="bottom" ref="areaSelector" length="85%">
|
||||
<div slot="btn" @tap="handleInit">
|
||||
<slot v-if="$slots.default"/>
|
||||
<div v-else class="areaSelector">
|
||||
@@ -10,14 +10,31 @@
|
||||
</div>
|
||||
<div class="areaSelector">
|
||||
<div class="fixedTop">
|
||||
<span v-for="(area, i) in fullArea" :key="area.id" v-text="area.name" :class="{ current: area.id == index }"
|
||||
@click="selectNode(area, i)"/>
|
||||
<b>选择地区</b>
|
||||
<em>选择区域</em>
|
||||
<div class="selectedArea" v-if="hasSelected">
|
||||
<p v-for="area in fullArea" :key="area.id" v-text="area.name"/>
|
||||
</div>
|
||||
<div/>
|
||||
<span v-if="all" v-text="`全国`" @click="selectNode({}, -1)"/>
|
||||
<span v-for="(area,i) in fullArea" :key="area.id" v-text="area.levelLabel" @click="selectNode(area, i)"/>
|
||||
</div>
|
||||
<span v-text="currentArea.name"/>
|
||||
<!--用来作为占位的-->
|
||||
<div class="fixedPlaceholder">
|
||||
<b>选择地区</b>
|
||||
<em>选择区域</em>
|
||||
<div class="selectedArea" v-if="hasSelected"/>
|
||||
<span v-text="'行政区域'"/>
|
||||
</div>
|
||||
<!--end-->
|
||||
</div>
|
||||
<div class="pendingItem flexRow" flex v-for="op in list" :key="op.id">
|
||||
<div class="fill" :class="{ self: index == op.id }" v-html="op.name" @tap="handleSelect(op)"/>
|
||||
<u-icon v-if="index != op.id" name="arrow-right" color="#ddd" @click="getChild(op)"/>
|
||||
<div class="pendingItem flexRow" flex v-for="op in pending" :key="op.id" @tap="getChild(op)">
|
||||
<div class="fill" :class="{ self: index == op.id }" v-html="op.name"/>
|
||||
<u-icon v-if="index == op.id" name="checkbox-mark" color="#4181FF"/>
|
||||
</div>
|
||||
<div class="bottomBtns">
|
||||
<div @click="closePopup">取消</div>
|
||||
<div class="primary fill" @click="handleSelect(currentArea)">确定</div>
|
||||
</div>
|
||||
</ai-search-popup>
|
||||
</section>
|
||||
@@ -57,12 +74,19 @@ export default {
|
||||
locationIcon() {
|
||||
return this.$cdn + this.icon
|
||||
},
|
||||
pending() {
|
||||
return this.list.map(e => ({...e, levelLabel: this.levelLabels[e.type]}))
|
||||
},
|
||||
hasSelected() {
|
||||
return this.fullArea?.length > 0
|
||||
}
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
fullArea: [{name: '全部', id: 0}],
|
||||
fullArea: [],
|
||||
index: '',
|
||||
list: [],
|
||||
levelLabels: ["省", "市", "县/区", "镇/街道", "村/社区"]
|
||||
}
|
||||
},
|
||||
watch: {
|
||||
@@ -73,31 +97,28 @@ export default {
|
||||
methods: {
|
||||
getFullArea() {
|
||||
let areaId = this.areaId || (this.all ? '' : this.$areaId)
|
||||
areaId &&
|
||||
this.$http
|
||||
.post('/admin/area/getAllParentAreaId', null, {
|
||||
return areaId && this.$http.post('/admin/area/getAllParentAreaId', null, {
|
||||
withoutToken: true,
|
||||
params: {areaId},
|
||||
})
|
||||
.then((res) => {
|
||||
}).then((res) => {
|
||||
if (res?.data) {
|
||||
res.data.forEach(e => {
|
||||
e.levelLabel = this.levelLabels[e.type]
|
||||
})
|
||||
if (res.data.length > 1) {
|
||||
this.fullArea = res.data.reverse().slice(this.dataRange)
|
||||
} else {
|
||||
this.fullArea = res.data
|
||||
}
|
||||
this.fullArea.unshift({name: '全部', id: 0})
|
||||
return this.fullArea
|
||||
}
|
||||
})
|
||||
},
|
||||
getChildAreas(id) {
|
||||
id &&
|
||||
this.$http
|
||||
.post('/admin/area/queryAreaByParentId', null, {
|
||||
id && this.$http.post('/admin/area/queryAreaByParentId', null, {
|
||||
withoutToken: true,
|
||||
params: {id},
|
||||
})
|
||||
.then((res) => {
|
||||
}).then((res) => {
|
||||
if (res?.data) {
|
||||
this.list = res.data
|
||||
let self = this.fullArea.find((e) => e.id == this.index)
|
||||
@@ -113,18 +134,18 @@ export default {
|
||||
})
|
||||
},
|
||||
handleSelect(op) {
|
||||
if (op.id != this.index) {
|
||||
this.fullArea.push(op)
|
||||
this.index = op.id
|
||||
}
|
||||
this.$emit('select', op)
|
||||
this.$emit('update:name', this.currentArea.name)
|
||||
this.$refs.areaSelector?.handleSelect()
|
||||
this.closePopup()
|
||||
},
|
||||
getChild(op) {
|
||||
this.fullArea.push(op)
|
||||
this.index = op.id
|
||||
this.getChildAreas(op.id)
|
||||
if (op.id != this.index) {
|
||||
if (op.type < 5 && (/0{3}$/g.test(this.index)||!this.index)) {
|
||||
this.fullArea.push(op)
|
||||
this.getChildAreas(op.id)
|
||||
}
|
||||
this.index = op.id
|
||||
}
|
||||
},
|
||||
selectNode(area, i) {
|
||||
this.fullArea.splice(i + 1, this.fullArea.length - i)
|
||||
@@ -137,15 +158,16 @@ export default {
|
||||
}
|
||||
},
|
||||
handleInit() {
|
||||
this.index = this.currentArea.id
|
||||
if (this.all && !this.currentArea.id) this.getProvinces()
|
||||
else this.getChildAreas(this.currentArea.id)
|
||||
this.index = this.areaId
|
||||
this.getFullArea().then(() => {
|
||||
if (this.all && !this.currentArea.id) this.getProvinces()
|
||||
else this.getChildAreas(this.currentArea.id)
|
||||
})
|
||||
},
|
||||
},
|
||||
created() {
|
||||
this.index = this.areaId
|
||||
this.getFullArea()
|
||||
},
|
||||
closePopup() {
|
||||
this.$refs.areaSelector?.handleSelect()
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
@@ -158,21 +180,57 @@ export default {
|
||||
span {
|
||||
cursor: pointer;
|
||||
color: #333;
|
||||
font-weight: bold;
|
||||
line-height: 112px;
|
||||
margin-right: 80px;
|
||||
position: relative;
|
||||
|
||||
&:first-of-type:before {
|
||||
content: '';
|
||||
padding: 0;
|
||||
}
|
||||
&:last-of-type {
|
||||
margin-right: 0;
|
||||
|
||||
&:before {
|
||||
color: #333;
|
||||
content: '/';
|
||||
padding: 0 16px;
|
||||
&:after {
|
||||
content: " ";
|
||||
display: block;
|
||||
position: absolute;
|
||||
bottom: -26px;
|
||||
left: 50%;
|
||||
transform: translate(-50%, 100%);
|
||||
width: 40px;
|
||||
height: 8px;
|
||||
background: #4181FF;
|
||||
border-radius: 4px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.current {
|
||||
color: #3f8df5;
|
||||
b {
|
||||
display: block;
|
||||
width: 100%;
|
||||
line-height: 96px;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
em {
|
||||
font-style: normal;
|
||||
font-size: 24px;
|
||||
font-weight: 400;
|
||||
color: #999999;
|
||||
line-height: 34px;
|
||||
}
|
||||
|
||||
.selectedArea {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
width: fit-content;
|
||||
padding: 0 32px;
|
||||
height: 80px;
|
||||
background: #ECF2FF;
|
||||
border-radius: 40px;
|
||||
font-size: 32px;
|
||||
font-family: PingFangSC-Medium, PingFang SC;
|
||||
font-weight: 500;
|
||||
color: #4181FF !important;
|
||||
margin: 16px 0 32px;
|
||||
}
|
||||
|
||||
.fixedTop {
|
||||
@@ -184,30 +242,26 @@ export default {
|
||||
border-bottom: 4px solid #f5f5f5;
|
||||
z-index: 1;
|
||||
text-align: start;
|
||||
padding: 0 16px;
|
||||
padding: 0 32px;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
}
|
||||
|
||||
::v-deep.u-drawer-content {
|
||||
position: fixed;
|
||||
border-radius: 32px 32px 0 0;
|
||||
overflow: hidden;
|
||||
padding: 0 32px 90px;
|
||||
|
||||
.areaSelector {
|
||||
padding: 0 16px;
|
||||
box-sizing: border-box;
|
||||
border-bottom: 16px solid #f5f5f5;
|
||||
|
||||
span {
|
||||
line-height: 100px;
|
||||
}
|
||||
border-bottom: 1px solid #f5f5f5;
|
||||
}
|
||||
}
|
||||
|
||||
::v-deep.pendingItem {
|
||||
color: #333;
|
||||
margin-left: 32px;
|
||||
padding-right: 32px;
|
||||
height: 104px;
|
||||
border-bottom: 1px solid #ddd;
|
||||
text-align: start;
|
||||
|
||||
.self {
|
||||
@@ -215,6 +269,33 @@ export default {
|
||||
}
|
||||
}
|
||||
|
||||
::v-deep.bottomBtns {
|
||||
position: fixed;
|
||||
left: 0;
|
||||
bottom: 0;
|
||||
width: 100vw;
|
||||
display: flex;
|
||||
text-align: center;
|
||||
height: 88px;
|
||||
font-size: 34px;
|
||||
font-family: PingFangSC-Medium, PingFang SC;
|
||||
font-weight: 500;
|
||||
color: #3671EE;
|
||||
background: #fff;
|
||||
|
||||
& > div {
|
||||
padding: 0 92px;
|
||||
line-height: 88px;
|
||||
border-top: 1px solid #A0C0FF;
|
||||
|
||||
&.primary {
|
||||
color: #fff;
|
||||
background: #4181FF;
|
||||
border-color: #4181FF;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.location {
|
||||
width: 28px;
|
||||
height: 80px;
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<template>
|
||||
<section class="AiSearchPopup">
|
||||
<u-popup v-model="show" length="100%" closeable :mode="mode">
|
||||
<u-popup v-model="show" :length="length" closeable :mode="mode">
|
||||
<slot v-if="$slots.default"/>
|
||||
<div class="searchPane" v-else>
|
||||
<div class="title">{{ title }}</div>
|
||||
@@ -24,7 +24,8 @@ export default {
|
||||
placeholder: {default: "请搜索"},
|
||||
ops: {default: () => ({label: 'label', search: 'name'})},
|
||||
url: String,
|
||||
mode: {default: "right"}
|
||||
mode: {default: "right"},
|
||||
length: {default: "100%"}
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
@@ -33,6 +34,11 @@ export default {
|
||||
list: []
|
||||
}
|
||||
},
|
||||
watch: {
|
||||
show(v) {
|
||||
!v && this.$emit('close')
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
getList() {
|
||||
this.url && this.$instance.post(this.url, null, {
|
||||
|
||||
15
src/main.js
15
src/main.js
@@ -33,7 +33,18 @@ const app = new Vue({
|
||||
...App
|
||||
});
|
||||
store.dispatch("agentSign").then(config => {
|
||||
store.commit("getConfig", {...config, latlng: [config.lat, config.lng]})
|
||||
app.$mount();
|
||||
const init = (c = 0) => {
|
||||
if (config) {
|
||||
store.commit("getConfig", {...config, latlng: [config.lat, config.lng]})
|
||||
app.$mount();
|
||||
} else {
|
||||
if (c < 5) {
|
||||
setTimeout(() => {
|
||||
init(++c)
|
||||
}, 300)
|
||||
}
|
||||
}
|
||||
}
|
||||
init()
|
||||
})
|
||||
|
||||
|
||||
Reference in New Issue
Block a user