用vue实现两级联动select

本文介绍了如何使用Vue来实现两级联动的select选择器。通过监听一级分组的选择,动态加载对应的二级分组数据,最终展示选定分组的常用短信内容。涉及到的关键技术包括计算属性(computed)和v-show指令。

最近客户有一个需求:讲“常用短信”按照按照分组进行管理,选择一级分组的名称,显示这个父级分组的底下的所有常用短信内容,再选择子分组,精确显示这个子分组底下的常用短信。
先贴代码吧:

<template>
    <div>
        <headertop :leftFont="$router.name" ></headertop> 
        <h3>{{sort}}</h3>
        <table class="am-table am-table-compact am-table-bordered">
            <tr>
                    <td colspan="3">
                        <select v-model="defaultGroup">
                            <option value="all">所有</option>
                            <option v-for="option in comGroups" :value="option.id">
                                {{ option.gname }}
                            </option>
                        </select>
                        <select v-show="defaultGroup!='all'" v-model='finalChoose' >
                            <option value="">请选择</option>
                            <option v-for="option in selection" :value="option.id">
                                {{ option.gname }}
                            </option>
                        </select>
                    </td>
            </tr>
            <tbody>
                <tr v-for="(item,index) in commonSms" v-show="defaultGroup=='all'?true:(finalChoose!=''?item.gid==finalChoose:commonSms[index].gid==defaultGroup)">
                    <td>{{item.sms_content}}</td>
                    <td><input type="checkbox" name="" :id="item.gid"></td>
                </tr>
            </tbody>
        </table>
    </div>
</template>
<script>
import headertop from '@/components/headertop'
export default {
    name:"sort",
    props:{
        title:{
            type:String,
            default:""
        }
    },
    watch:{
        defaultGroup:function(oldVua,newVua){
            this.finalChoose='';
        }
    },
    computed:{
        selection:function(){
            if(this.defaultGroup=='all'){
                return [];
            }else{
                return this.comGroups.filter((item)=>{
                    return item.id == this.defaultGroup
                })[0].twoStageGroup
            }

        }
    },
    data () {
        return {
            sort: 'sort',
            defaultGroup:'all',
            finalChoose:'',
            commonSms:[{"id":"302","gid":"75","sms_content":"\u8fd9\u662f111 \u7684\u77ed\u4fe1","gname":"111"},{"id":"303","gid":"73","sms_content":"\u8fd9\u662f\u5206\u7ec48\u7684\u77ed\u4fe1","gname":"\u5206\u7ec48"},{"id":"304","gid":"11","sms_content":"\u8fd9\u662f\u5206\u7ec46\u7684\u77ed\u4fe1","gname":"\u5206\u7ec46"},{"id":"305","gid":"6","sms_content":"\u8fd9\u662f\u5206\u7ec41 \u7684\u77ed\u4fe1","gname":"\u5206\u7ec41"},{"id":"309","gid":"8","sms_content":"\u6d4b\u8bd51","gname":"\u5206\u7ec43"},{"id":"311","gid":"11","sms_content":"\u662f\u5426\u6536\u5230\u8fc7\u8bd5\u8bd5","gname":"\u5206\u7ec46"},{"id":"312","gid":"10","sms_content":"\u6d4b\u8bd54","gname":"\u5206\u7ec45"},{"id":"313","gid":"11","sms_content":"\u6d4b\u8bd5\u516d","gname":"\u5206\u7ec46"},{"id":"314","gid":"70","sms_content":"\u6d4b\u8bd5\u5341\u4e8c","gname":"\u5206\u7ec412"},{"id":"315","gid":"71","sms_content":"\u6d4b\u8bd5\u5206\u7ec4","gname":"\u6d4b\u8bd5\u5206\u7ec4"},{"id":"316","gid":"72","sms_content":"\u6d4b\u8bd5\u4e03","gname":"\u5206\u7ec47"},{"id":"317","gid":"73","sms_content":"\u6d4b\u8bd5\u516b","gname":"\u5206\u7ec48"},{"id":"318","gid":"73","sms_content":"\u6d4b\u8bd58\u7684\u77ed\u4fe1","gname":"\u5206\u7ec48"},{"id":"236","gid":"11","sms_content":"\u8fd9\u662f\u7b56\u5212i\r\n\u653e\u8361\u7b2c\u4e09\u4e2a\r\n\u53d7\u5230\u5e7f\u6cdb\u662f\u5fb7\u56fd\u963f\u4e09\r\n\u662f\u5fb7\u56fd\u662f","gname":"\u5206\u7ec46"}],
            comGroups:JSON.parse('[{"id":"6","gname":"分组1","registry_code":"101100-WEB-HUAX-761107","pid":"0","twoStageGroup":[{"id":"10","gname":"分组5","registry_code":"101100-WEB-HUAX-761107","pid":"6"},{"id":"75","gname":"111","registry_code":"101100-WEB-HUAX-761107","pid":"6"}]},{"id":"8","gname":"分组3","registry_code":"101100-WEB-HUAX-761107","pid":"0","twoStageGroup":[{"id":"70","gname":"分组12","registry_code":"101100-WEB-HUAX-761107","pid":"8"}]},{"id":"9","gname":"分组4","registry_code":"101100-WEB-HUAX-761107","pid":"0","twoStageGroup":[{"id":"71","gname":"测试分组","registry_code":"101100-WEB-HUAX-761107","pid":"9"}]},{"id":"11","gname":"分组6","registry_code":"101100-WEB-HUAX-761107","pid":"0","twoStageGroup":[{"id":"74","gname":"ddd","registry_code":"101100-WEB-HUAX-761107","pid":"11"}]},{"id":"72","gname":"分组7","registry_code":"101100-WEB-HUAX-761107","pid":"0","twoStageGroup":[{"id":"73","gname":"分组8","registry_code":"101100-WEB-HUAX-761107","pid":"72"}]},{"id":"80","gname":"这是一个非常非常非常非常非常长长的分组","registry_code":"101100-WEB-HUAX-761107","pid":"0"},{"id":"81","gname":"豆腐干地方","registry_code":"101100-WEB-HUAX-761107","pid":"0"},{"id":"82","gname":"复古风格","registry_code":"101100-WEB-HUAX-761107","pid":"0","twoStageGroup":[{"id":"90","gname":"分组15","registry_code":"101100-WEB-HUAX-761107","pid":"82"}]},{"id":"84","gname":"的地方","registry_code":"101100-WEB-HUAX-761107","pid":"0"},{"id":"85","gname":"是的是的","registry_code":"101100-WEB-HUAX-761107","pid":"0","twoStageGroup":[{"id":"83","gname":"打发打发","registry_code":"101100-WEB-HUAX-761107","pid":"85"}]}]')

        }
    },
    components:{headertop},
    mounted:function(){
        console.log(this.finalChoose=='')
    }
}
</script>
<style type="text/css" lang="less" scoped>

</style>

这里commonSmscomGroups都是测试数据!
整理一下思路:

1.先说第一个select:
默认是显示所有常用短信,所以这个model的默认值是“all”,他的option就应该是遍历所有一级分组,先不用管json数据comGroups中“twoStageGroup”这个字段,循环代码:

<select v-model="defaultGroup">
        <option value="all">所有</option>
        <option v-for="option in comGroups" :value="option.id">
            {{ option.gname }}
        </option>
</select>

2.再说第二个select:
这个select里的数据是要根据第一个选中的分组来决定的,这里用到动态计算computed,代码片段如下:

computed:{
        selection:function(){
            if(this.defaultGroup=='all'){
                return [];
            }else{
                return this.comGroups.filter((item)=>{
                    return item.id == this.defaultGroup
                })[0].twoStageGroup
            }

        }
    },

这里会根据一级选择动态的返回当前一级分组底下的二级分组数组,所以二级分组的遍历代码如下:

<select v-show="defaultGroup!='all'" v-model='finalChoose' >
    <option value="">请选择</option>
    <option v-for="option in selection" :value="option.id">
        {{ option.gname }}
    </option>
</select>

现在二级联动select就实现了!然后就是表格各行的动态显示了!
3.我们都知道v-show这个属性,当表达式为“真”时就显示,反之不显示。
逻辑分析:

if(defaultGroup=='all'){
     return true;
}else{
    if(finalChoose==''){
        return commonSms[index].gid==defaultGroup;
    }else{
        return item.gid==finalChoose;
    }
 }

这里把他转成三元运算:

defaultGroup=='all'?true:(finalChoose!=''?item.gid==finalChoose:commonSms[index].gid==defaultGroup)

最终表格的遍历如下:

<tr v-for="(item,index) in commonSms" v-show="defaultGroup=='all'?true:(finalChoose!=''?item.gid==finalChoose:commonSms[index].gid==defaultGroup)">
    <td>{{item.sms_content}}</td>
    <td><input type="checkbox" name="" :id="item.gid"></td>
</tr>

这样就实现了功能了!
其实还有关键的一步是后台的数据结构要正确!
分析一下json的数据:

comGroups

[{
    "id": "302",
    "gid": "75",
    "sms_content": "这是111 的短信",
    "gname": "111"
}, {
    "id": "303",
    "gid": "73",
    "sms_content": "这是分组8的短信",
    "gname": "分组8"
}, {
    "id": "304",
    "gid": "11",
    "sms_content": "这是分组6的短信",
    "gname": "分组6"
}, {
    "id": "305",
    "gid": "6",
    "sms_content": "这是分组1 的短信",
    "gname": "分组1"
}, {
    "id": "309",
    "gid": "8",
    "sms_content": "测试1",
    "gname": "分组3"
}, {
    "id": "311",
    "gid": "11",
    "sms_content": "是否收到过试试",
    "gname": "分组6"
}, {
    "id": "312",
    "gid": "10",
    "sms_content": "测试4",
    "gname": "分组5"
}, {
    "id": "313",
    "gid": "11",
    "sms_content": "测试六",
    "gname": "分组6"
}, {
    "id": "314",
    "gid": "70",
    "sms_content": "测试十二",
    "gname": "分组12"
}, {
    "id": "315",
    "gid": "71",
    "sms_content": "测试分组",
    "gname": "测试分组"
}, {
    "id": "316",
    "gid": "72",
    "sms_content": "测试七",
    "gname": "分组7"
}, {
    "id": "317",
    "gid": "73",
    "sms_content": "测试八",
    "gname": "分组8"
}, {
    "id": "318",
    "gid": "73",
    "sms_content": "测试8的短信",
    "gname": "分组8"
}, {
    "id": "236",
    "gid": "11",
    "sms_content": "这是策划i\r\n放荡第三个\r\n受到广泛是德国阿三\r\n是德国是",
    "gname": "分组6"
}]

主要是gid这个字段是这条常用短信所属分组的id。与短信分组里边的组id对应。

commonSms

[{
    "id": "6",
    "gname": "分组1",
    "registry_code": "101100-WEB-HUAX-761107",
    "pid": "0",
    "twoStageGroup": [{
        "id": "10",
        "gname": "分组5",
        "registry_code": "101100-WEB-HUAX-761107",
        "pid": "6"
    }, {
        "id": "75",
        "gname": "111",
        "registry_code": "101100-WEB-HUAX-761107",
        "pid": "6"
    }]
}, {
    "id": "8",
    "gname": "分组3",
    "registry_code": "101100-WEB-HUAX-761107",
    "pid": "0",
    "twoStageGroup": [{
        "id": "70",
        "gname": "分组12",
        "registry_code": "101100-WEB-HUAX-761107",
        "pid": "8"
    }]
}, {
    "id": "9",
    "gname": "分组4",
    "registry_code": "101100-WEB-HUAX-761107",
    "pid": "0",
    "twoStageGroup": [{
        "id": "71",
        "gname": "测试分组",
        "registry_code": "101100-WEB-HUAX-761107",
        "pid": "9"
    }]
}, {
    "id": "11",
    "gname": "分组6",
    "registry_code": "101100-WEB-HUAX-761107",
    "pid": "0",
    "twoStageGroup": [{
        "id": "74",
        "gname": "ddd",
        "registry_code": "101100-WEB-HUAX-761107",
        "pid": "11"
    }]
}, {
    "id": "72",
    "gname": "分组7",
    "registry_code": "101100-WEB-HUAX-761107",
    "pid": "0",
    "twoStageGroup": [{
        "id": "73",
        "gname": "分组8",
        "registry_code": "101100-WEB-HUAX-761107",
        "pid": "72"
    }]
}, {
    "id": "80",
    "gname": "这是一个非常非常非常非常非常长长的分组",
    "registry_code": "101100-WEB-HUAX-761107",
    "pid": "0"
}, {
    "id": "81",
    "gname": "豆腐干地方",
    "registry_code": "101100-WEB-HUAX-761107",
    "pid": "0"
}, {
    "id": "82",
    "gname": "复古风格",
    "registry_code": "101100-WEB-HUAX-761107",
    "pid": "0",
    "twoStageGroup": [{
        "id": "90",
        "gname": "分组15",
        "registry_code": "101100-WEB-HUAX-761107",
        "pid": "82"
    }]
}, {
    "id": "84",
    "gname": "的地方",
    "registry_code": "101100-WEB-HUAX-761107",
    "pid": "0"
}, {
    "id": "85",
    "gname": "是的是的",
    "registry_code": "101100-WEB-HUAX-761107",
    "pid": "0",
    "twoStageGroup": [{
        "id": "83",
        "gname": "打发打发",
        "registry_code": "101100-WEB-HUAX-761107",
        "pid": "85"
    }]
}]

这是分组信息的json数据,id为这个组的id对应常用短信内容的gid字段。当pid为0时表示他是父级分组,twoStageGroup是他的子分组。

评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值