// 地区选择器
<template>
<view class="addressSelector">
<main>
<view class="provinceTree">
<view @click="getCityList(item, index)" :id="item.code" :class="item.checked === false ? 'provinceBox' : 'provinceBox provinceHeightLight'" v-for="(item, index) in provinceList" :key="item.code">
<span>{{item.name}}</span>
<i v-if="item.number !== ''">{{item.number}}</i>
</view>
</view>
<view class="cityTree">
<view @click="getAreaList(item, index)" :id="item.code" :class="item.checked === false ? 'cityBox' : 'cityBox cityHeightLight'" v-for="(item, index) in cityList" :key="item.code">
<span>{{item.name}}</span>
<i v-if="item.number !== ''">{{item.number}}</i>
</view>
</view>
<view class="areaTree">
<view @click="clickAreaList(item, index)" :id="item.code" :class="item.checked === false ? 'areaBox' : 'areaBox areaHeightLight'" v-for="(item, index) in areaList" :key="item.code">{{ item.name }}</view>
</view>
</main>
<u-top-tips z-index="99999" ref="uTips"></u-top-tips>
</view>
</template>
<script>
import { addressPartListApi } from '../../../api/api'
export default {
data() {
return {
// 省级城市编码
pcode: '',
// 市级城市编码
ccode: '110000',
// 省份列表
provinceList: [],
// 市级列表
cityList: [],
// 区县列表
areaList: [],
// 存储选中的省份列表
checkedProvinceList: [],
// 存储选中的市级列表
checkedCityList: [],
// 存储选中的区县级列表
checkedAreaList: []
}
},
onShow() {
// 获取省份列表
this.getProvinceList().then(() =>{
// 获取默认市级列表
this.getCityList({ code:'110000', pcode: '000000' }, 0)
})
},
methods: {
// 获取省份列表
async getProvinceList() {
const { data: res } = await addressPartListApi('000000')
if (res.code !== 0) return this. refs.uTips.show({ title: res.msg, type: 'error', duration: '2000'})
// 设置默认值
this.cityList = []
res.data.list.forEach((item, index) =>{
this.cityList.push({
id: item.id, // 地区id
name: item.name, // 地区名称
code: item.code, // 地区编码
pcode: item.pcode, // 父级地区编码
checked: false, // 选择状态
switch: false, // 切换状态
number: '', // 子级选中的值
index: index // 当前地区的下标
})
})
// 2.市级高亮
this.checkedCityList.forEach((checkCity, checkIndex) =>{
this.cityList.forEach((allCity, allIndex) =>{
if (checkCity.code === allCity.code) {
this.cityList[allIndex].checked = true
this.cityList[allIndex].number = this.checkedCityList[checkIndex].number
}
})
})
// 3.直接将所有区县级列表清空
this.areaList = []
// 4.将所有省份switch改为false,同时将当前选中的省份switch改为true
this.provinceList.forEach(zResult =>{
zResult.switch = false
})
this.provinceList[index].switch = true
return false
// 如果当前省级已经被点击过,但是不是第一次点击时
} else if (alreadyCheck === true &&value.switch === true) {
// 除了移除省级code还要移除对应省级下的所有市级code(移除对应的高亮状态,默认会重置)
// 将省级code和市级级pcode比较如果相同则移除(第一层)
if (this.checkedCityList.length !== 0) {
// --------------移除对应的市级code
let newCheckedCityList = []
this.checkedCityList.forEach((val, index) =>{
if (value.code !== val.pcode) {
newCheckedCityList.push(val)
} else {
// 将对应的市级code和区县级pcode比较如果相同则移除(第二层)
if (this.checkedAreaList.length !== 0) {
let newCheckedAreaList = []
this.checkedAreaList.forEach((keys, index) =>{
if (val.code !== keys.pcode) {
newCheckedAreaList.push(keys)
}
})
this.checkedAreaList = newCheckedAreaList
}
}
})
this.checkedCityList = newCheckedCityList
}
this.checkedProvinceList.splice(alreadyIndex, 1)
} else {
this.checkedProvinceList.push({ code: value.code, pcode: value.pcode, number: '全' })
}
console.log(this.checkedProvinceList, '省', this.checkedCityList, '市', this.checkedAreaList,'区县')
// 改变当前点击的省份高亮状态
this.provinceList[index].checked = !this.provinceList[index].checked
// 改变当前点击省份的全选状态
if (this.provinceList[index].number === '') {
this.provinceList[index].number = '全'
} else {
this.provinceList[index].number = ''
}
this.pcode = value.code
const { data: res } = await addressPartListApi(this.pcode)
if (res.code !== 0) return this. refs.uTips.show({ title: res.msg, type: 'error', duration: '2000'})
// 设置默认值
this.areaList = []
res.data.list.forEach((item, index) =>{
this.areaList.push({
id: item.id, // 地区id
name: item.name, // 地区名称
code: item.code, // 地区编码
pcode: item.pcode, // 父级地区编码
checked: false, // 选择状态
switch: false, // 切换状态
number: '', // 子级选中的值
index: index // 当前地区的下标
})
})
// 2.区县高亮
this.checkedAreaList.forEach((checkArea, checkIndex) =>{
this.areaList.forEach((allArea, allIndex) =>{
if (checkArea.code === allArea.code) {
this.areaList[allIndex].checked = true
}
})
})
// 3.将所有市级switch改为false,同时将当前选中的市级switch改为true
this.cityList.forEach(zResult =>{
zResult.switch = false
})
this.cityList[index].switch = true
return false
// 如果当前市级已经被点击过,但是不是第一次点击时
} else if (alreadyCheck === true &&value.switch === true) {
this.checkedCityList.splice(alreadyIndex, 1)
// 除了移除市级code还要移除对应市级下的所有区县级code同时移除对应的高亮状态
// 将市级code和区县级pcode比较如果相同则移除
if (this.checkedAreaList.length !== 0) {
let newCheckedAreaList = []
this.checkedAreaList.forEach((val, index) =>{
if (value.code !== val.pcode) {
newCheckedAreaList.push(val)
}
})
this.checkedAreaList = newCheckedAreaList
}
// 当市级已经被勾选时,找到对应的省级,省级后缀的数字得-1
this.provinceList.forEach((result, index) =>{
if (result.code === value.pcode) {
result.number = (result.number - 1) + ''
}
if (result.number === '0') result.number = '全'
// 不仅要改list的number还要改对应的checkedList上的number★~~~~~
if (this.checkedProvinceList.length !== 0) {
this.checkedProvinceList.forEach((redus, rIndex) =>{
if (redus.code === result.code) {
this.checkedProvinceList[rIndex].number = result.number
}
})
}
})
} else {
this.checkedCityList.push({ code: value.code, pcode: value.pcode, number: '全' })
// 勾选时点击当前市级地区时判断当前省级是否勾选,如果未勾选则勾选上(checked选择状态及高亮)
// 判断当前省级是否勾选
this.provinceList.forEach((result, index) =>{
// 找到对应的省级
if (result.code === value.pcode) {
// 如果省级未勾选,则勾选上省级
if (result.checked === false) {
result.checked = true
result.number = '全'
this.checkedProvinceList.push({ code: value.pcode, pcode: '000000', number: '1' })
}
// 到这一步肯定省级肯定是被勾选上了
// 如果市级被勾选,省级后缀的数字都得+1
if (result.number === '全') {
result.number = '1'
} else {
result.number = (result.number - 0 + 1) + ''
}
// 不仅要改list的number还要改对应的checkedList上的number★~~~~~
if (this.checkedProvinceList.length !== 0) {
this.checkedProvinceList.forEach((redus, rIndex) =>{
if (redus.code === result.code) {
this.checkedProvinceList[rIndex].number = result.number
}
})
}
}
})
}
// 改变当前点击的市级高亮状态
this.cityList[index].checked = !this.cityList[index].checked
// 改变当前点击市级的全选状态
if (this.cityList[index].number === '') {
this.cityList[index].number = '全'
} else {
this.cityList[index].number = ''
}
this.ccode = value.code
console.log(this.checkedProvinceList, '省', this.checkedCityList, '市', this.checkedAreaList,'区县')
const { data: res } = await addressPartListApi(this.ccode)
if (res.code !== 0) return this.$refs.uTips.show({ title: res.msg, type: 'error', duration: '2000'})
// 设置默认值
this.areaList = []
res.data.list.forEach((item, index) =>{
this.areaList.push({
id: item.id, // 地区id
name: item.name, // 地区名称
code: item.code, // 地区编码
pcode: item.pcode, // 父级地区编码
checked: false, // 选择状态
switch: false,// 切换状态
index: index // 当前地区的下标
})
})
// ------------------------------------------------------------------------------------------------(再获取完区县级列表后点击市级重置区县级高亮)
// 用所有被勾选的区县级code和所有区县列表进行比较如果相同则高亮
if (this.checkedAreaList.length !== 0 &&this.areaList.length !== 0) {
this.checkedAreaList.forEach((val, valIndex) =>{
this.areaList.forEach((keys, keysIndex)=>{
if (val.code === keys.code) {
this.areaList[keysIndex].checked = true
}
})
})
}
},
// 点击区县触发
clickAreaList(value, index) {
// 存储被点击的区县code(判断如果已经存在被点击过则去除)
let alreadyCheck = false
let alreadyIndex = ''
if (this.checkedAreaList.length !== 0) {
this.checkedAreaList.forEach((item, index) =>{
if (item.code === value.code) {
alreadyCheck = true
alreadyIndex = index
return false
}
})
}
// 如果当前县区级已经被勾选则去除
if (alreadyCheck === true) {
this.checkedAreaList.splice(alreadyIndex, 1)
// 去除的时候市级肯定是勾选状态
this.cityList.forEach((result, index) =>{
// 找到对应的市级,市级后缀的数字得-1
if (result.code === value.pcode) {
result.number = (result.number - 1) + ''
}
if (result.number === '0') result.number = '全'
// 不仅要改list的number还要改对应的checkedList上的number★~~~~~
if (this.checkedCityList.length !== 0) {
this.checkedCityList.forEach((redus, rIndex) =>{
if (redus.code === result.code) {
this.checkedCityList[rIndex].number = result.number
}
})
}
})
} else {
// 如果当前县区级如果未被勾选
this.checkedAreaList.push({ code: value.code, pcode: value.pcode })
// 勾选时点击当前区县地区时判断当前市级是否勾选,如果未勾选则勾选上(checked选择状态及高亮)
// 判断当前市级是否勾选
this.cityList.forEach((result, index) =>{
// 找到对应的市级
if (result.code === value.pcode) {
// 如果市级未勾选,则勾选上市级
if (result.checked === false) {
result.checked = true
result.number = '全'
this.checkedCityList.push({ code: value.pcode, pcode: '000000' })
//
}
// 到这一步肯定是被勾选上了
// 如果县区被勾选,市级后缀的数字都得+1
if (result.number === '全') {
result.number = '1'
} else {
result.number = (result.number - 0 + 1) + ''
}
// 不仅要改list的number还要改对应的checkedList上的number★~~~~~
if (this.checkedCityList.length !== 0) {
this.checkedCityList.forEach((redus, rIndex) =>{
if (redus.code === result.code) {
this.checkedCityList[rIndex].number = result.number
}
})
}
}
})
}
console.log(this.checkedProvinceList, '省', this.checkedCityList, '市', this.checkedAreaList,'区县')
// 改变当前点击的区县高亮状态
this.areaList[index].checked = !this.areaList[index].checked
}
}
}
</script>
<style lang="less">
.addressSelector{
main {
display: flex
width: 100%
background-color: #F5F5F5
.provinceTree, .cityTree, .areaTree {
flex: 1
height: 100vh
border-right: 1.81rpx solid #E4E4E4
overflow-y: auto
.provinceBox, .cityBox, .areaBox {
position: relative
height: 90.57rpx
line-height: 90.57rpx
text-align: center
i {
position: absolute
top: 30.8rpx
right: 30.79rpx
width: 28.98rpx
height: 28.98rpx
background-color: #188AFA
border-radius: 50%
line-height: 25.98rpx
color: #FFFFFF
font-size: 21.73rpx
}
}
// 省级高亮样式
.provinceHeightLight {
background: linear-gradient(270deg, #F5F5F5 0%, #D1E9FF 100%)
color: #188AFA
}
// 市级高亮样式
.cityHeightLight {
background-color: #F5F5F5
color: #188AFA
}
// 区县高亮样式
.areaHeightLight {
background-color: #F5F5F5
color: #188AFA
}
}
.cityTree, .areaTree {
background-color: #FFFFFF
}
}
}
</style>
小程序官网关于picker的介绍
小程序官网提供了5中选择器,分别是:
普通选择器
多列选择器
时间选择器
日期选择器
省市区选择器
以下仅列举省市区选择器的用法:
index.wxml
index.js
多看文档,不然又要自己封装了。。。
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)