用vue写的一个级联选择器
<!DOCTYPE html><html lang="en"><head><meta charset="UTF-8"><title></title><style>*
·
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title></title>
<style>
* {
padding: 0;
margin: 0;
}
* {
padding: 0;
margin: 0;
box-sizing: border-box;
}
a {
text-decoration: none;
}
.clearfix:before,
.clearfix:after {
content: ' ';
display: table;
}
.clearfix:after {
clear: both;
}
input {
outline: none;
}
ol,
ul {
list-style: none;
}
body {
padding: 20px;
}
.select-box {
position: relative;
}
.select-box .curr {
width: 240px;
padding-left: 15px;
padding-right: 30px;
border: 1px solid #ddd;
border-radius: 5px;
height: 40px;
line-height: 40px;
font-size: 14px;
position: relative;
z-index: 15;
background-color: white;
}
.select-box .curr:hover {
border-color: #aaa;
cursor: pointer;
}
.arrow {
position: absolute;
right: 10px;
top: 17px;
display: block;
width: 10px;
height: 10px;
border-left: 1px solid #aaa;
border-top: 1px solid #aaa;
transform: rotate(225deg);
transform-origin: 2px 2px;
transition: 200ms;
}
.on .arrow {
transform: rotate(45deg);
}
.list-box {
position: absolute;
top: 30px;
left: 0;
border: 1px solid #ddd;
box-shadow: 0px 0px 8px 0px #ccc;
padding: 5px 0;
z-index: 10;
transition: 200ms;
}
.on .list-box {
top: 50px;
}
.list-box .list {
float: left;
width: 180px;
height: 204px;
overflow: auto;
border-left: 1px solid #ccc;
}
.list-box .list.first {
border: none;
}
.list .item {
height: 38px;
line-height: 38px;
padding-left: 15px;
font-size: 14px;
cursor: pointer;
position: relative;
}
.list .item:hover {
background-color: rgb(245, 247, 250);
}
.list .item.active {
color: #409EFF;
font-weight: bold;
}
.list .icon {
position: absolute;
top: -6px;
left: 30px;
width: 10px;
height: 10px;
border-left: 1px solid #ddd;
border-top: 1px solid #ddd;
z-index: 20;
transform: rotate(45deg);
background-color: white;
}
.list .arrow-icon {
position: absolute;
right: 10px;
top: 17px;
display: block;
width: 10px;
height: 10px;
border-left: 1px solid #aaa;
border-top: 1px solid #aaa;
transform: rotate(135deg);
transform-origin: 2px 2px;
transition: 200ms;
}
</style>
<script type="text/javascript" src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
</head>
<body>
<div id="app" :class="{'on':isVisibleFirst}">
<div class="select-box" @click="showFirstLayer">
<div class="curr" :class="{'on':isVisibleFirst}"><span v-if="selectionBoxDisplay">请选择</span><span v-else>{{theString}}</span><span class="arrow"></span></div>
<div class="list-box clearfix" v-if="isVisibleFirst">
<div class="list">
<div class="item" v-for="(theitem,index) in list" @click="givenValueOfCurr(index)" :class="{'active':index==curr}">{{theitem.name}}
</div>
</div>
<div class="list" v-if="isVisibleSecond">
<div class="item" V-for="(theSeItem,index1) in list[curr].children" @click="clickingSecondLayer(index1)" :class="{'active':index1==currSec}">
{{theSeItem.name}}</div>
</div>
<div class="icon"></div>
</div>
</div>
</div>
<script>
var vm = new Vue({
el: '#app',
data: {
list: [{
name: '粤菜',
children: [{
name: '清蒸桂花鱼'
}, {
name: '梅菜扣肉'
}]
}, {
name: '湘菜',
children: [{
name: '小炒肉'
}, {
name: '剁椒鱼头'
}, {
name: '水煮鱼'
}]
}, {
name: '甜品',
children: [{
name: '西米露'
}, {
name: '双皮奶'
}, {
name: '凉粉'
}]
}],
curr: -1,
currSec: -1,
firstTimeClick: 0,
isVisibleFirst: false,
isVisibleSecond: false,
theString: "",
selectionBoxDisplay: true,
},
methods: {
showFirstLayer() {
this.isVisibleFirst = true;
this.firstTimeClick += 1;
if (this.firstTimeClick > 1) {
this.isVisibleSecond = true;
}
this.selectionBoxDisplay = false;
},
givenValueOfCurr(index) {
this.curr = index;
console.log(this.list[this.curr].children);
this.isVisibleSecond = true;
this.currSec = -1;
this.theString = this.list[this.curr].name + "\/";
},
clickingSecondLayer(index1) {
this.isVisibleFirst = false;
this.currSec = index1;
console.log(this.isVisibleFirst);
this.isVisibleSecond = false;
event.stopPropagation();
this.theString += this.list[this.curr].children[this.currSec].name;
}
}
})
</script>
</body>
</html>
这是成品的图,主要的技术的话,一个是v-if会让点击后的一级菜单显示出来,然后v-if点击一级菜单中的某个元素后,在v-for里面用上一个下标,把下标传入,然后会相应的把数据放到二级菜单中。
选中变色的话是 v-bind:class的应用, :class的效果就是选中后让curr(也就是当前选中的值)对应的Index的值得那个标签添加上一个类,类会变蓝色。
还有就是注意到冒泡事件,所以要阻止一下冒泡事件
更多推荐
已为社区贡献1条内容
所有评论(0)