微信小程序多列下拉框的实现(树形数据结构和单数组数据结构形式)

  • Post author:
  • Post category:小程序




多列下拉框实现介绍

利用微信小程序api,实现不同传输数据格式下的多列下拉框实现

首先了解一下picker中的事件

在这里插入图片描述

这里是官方文档,具体意思就是 当你滑动多列中的某一列的时候,

bindcolumnchange

事件就会触发。当选择完毕点击确定的时候

bindchange

事件就会触发



微信小程序的多列下拉框是真的反人类

vue什么的就是传个数据就行了,它这样搞,麻烦。不知道读者有没有简单的办法,有的可以留言评论,反正我是想不出来了。



成果

在这里插入图片描述

在这里插入图片描述



情况一:后端返回的数据是 一层一个数组,没有树形结构

如:

[[第一层数据],[第二层数据],[第三层数据]]



实现思路

定义三个数组,分别把每一层的数据放在对应数组中,用于更新,

定义一个只有三的元素的数组

multiIndex

表示每一层对应的下标。

需要注意的是

areapicker1/2/3

是所在层的所有数据



areaArry

是用于展示在页面上的数据,它的格式是

[[第一层],[第二层],[第三层]]


流程是用户滚动多列下拉框,程序通过

bindcolumnchange

事件,对

areaArry

里的数据进行实时更改,同时更改

multiIndex

的值(它代表的现在所选值在areaArry数组中对应的每一层的下标有几层

multiIndex

就有几个元素,两层就只有两个元素)



wxml
<picker mode="multiSelector" class="input_item_right" bindchange="bindpatrolquestiontype" value="{{multiIndex}}" range="{{areaArry}}" bindcolumnchange="bindMultiPickerColumnChange" bindchange="bindAreaChange" range-key='text'>
          <view class="picker">
            <view>
              <view wx:if="{{rqstAreaCode==''}}">请选择区域</view>
            </view>
            <view>
              {{rqstAreaCode}}
            </view>

          </view>
</picker>



js
var areapicker1 = []; //地区选择的第一列数据总数组
var areapicker2 = []; //地区选择的第二列数据总数组
var areapicker3 = []; //地区选择的第三列数据总数组

page({
    data: {
        multiIndex: [0, 0, 0],
        areaArry: []//展示在页面上的数据
        areaCodeArry:[],//对应的code值
    },
    //注意拿到数据之后进行对areaArry初始化...
    
    
    bindMultiPickerColumnChange: function (e) {
    	var that = this;
        switch (e.detail.column) {
            case 0:
                //用临时数组存储
                var list=[],//表示第二列展示的数据(只有name值)
                    list2 = [],//第三列的展示数据(只有name值)
                    codelist=[],//表示第二列value的值(只有code值)
                    codelist2=[],//表示第三列value的值(只有code值)
                	newpicker2=[],//临时的第二列数据(item的所有属性都有)
                 //从所有第二列的内容中取出与第一列选中状态的值对应的数据用于实时生成第二列
                for (var i = 0; i < areapicker2.length; i++) {
                    if (areapicker2[i].parentGuid == areapicker1[e.detail.value].id) {
                        //若第二列的父亲跟这个相同,则push
                        newpicker2.push(areapicker2[i]);
                        list.push(areapicker2[i].areaName)
                        codelist.push(areapicker2[i].areaCode)
                    }
                }
                
                if (areapicker3.length > 0) {
                    for (var i = 0; i < areapicker3.length; i++) {
                        if (newpicker2.length > 0) {
                            if (areapicker3[i].parentGuid == newpicker2[0].id) {
                                list2.push(areapicker3[i].areaName)
                                codelist2.push(areapicker3[i].areaCode)
                            }
                        }

                    }
                }
                //实时修改第二列,并且把第二列设置到第一个展示
                that.setData({
                    "areaArry[1]": list,
                    "areaArry[2]": list2,
                    "areaCodeArry[1]": codelist,
                    "areaCodeArry[2]": codelist2,
                    "multiIndex[0]": e.detail.value,
                    "multiIndex[1]": 0
                })
                console.log(that.data.multiIndex);
                break;
            case 1:
                //同上
               var list2 = [],//第三列展示值
                   codelist2 = [];//第三列value值

                var multiIndex1 = that.data.multiIndex[0],
                    newpicker2 = [];//第二列的临时数组,用于第三列的比较
                //从所有第二列的内容中取出与第一列选中状态的值对应的数据 用于第三列的判断
                for (var i = 0; i < areapicker2.length; i++) {
                    if (areapicker2[i].parentGuid == areapicker1[multiIndex1].id) {
                        newpicker2.push(areapicker2[i]);
                    }
                }

                //从所有第三列的内容中取出与第一列选中状态的值对应的数据用于实时生成第三列
                if (areapicker3.length > 0) {
                    for (var i = 0; i < areapicker3.length; i++) {
                        if (areapicker3[i].parentGuid == newpicker2[e.detail.value].id) {
                            list2.push(areapicker3[i].areaName)
                            codelist2.push(areapicker3[i].areaCode)
                        }
                    }
                    that.setData({
                        "areaArry[2]": list2,
                        "areaCodeArry[2]": codelist2,
                        "multiIndex[1]": e.detail.value,
                        "multiIndex[2]": 0
                    })
                    console.log(that.data.multiIndex);
                }
                break;
        }
    },
    
    //点击确定后的操作,用来最后提交的值 利用multiIndex
    bindAreaChange: function (e) {
    	var that = this;
        var result = e.detail.value;//这里的value 就是 multiIndex
        if (result.length > 2) {
            var reslutname = that.data.areaArry[0][result[0]] + that.data.areaArry[1][result[1]] + (that.data.areaArry[2][result[2]] == undefined ? '' : that.data.areaArry[2][result[2]]);
            var reslutcode = that.data.areaCodeArry[2][result[2]] == undefined ? '' : that.data.areaCodeArry[2][result[2]];
        } else {
            var reslutname = that.data.areaArry[0][result[0]] + that.data.areaArry[1][result[1]];
            var reslutcode = that.data.areaCodeArry[1][result[1]];
        }

        this.setData({
            rqstAreaCode: reslutname,
            realrqstAreaCode: reslutcode
        })
    },
})



情况二:后端返回的数据是树形结构

如图

在这里插入图片描述



实现思路

同上,这个相对于上面的简单点,不需要

areapicker

来存储数据



wxml同上


js
var arrayList = [];

page({
    data: {
        multiIndex: [0, 0, 0],
        areaArry: []
    },

 //初始化
 //获取诉求类型和诉求区域
getEvent: function (accesstoken) {
    app.fetch({
      url: '...',
      token: '',
      params: {},
    }).then(res => {
      var list = res.custom.jsonList
      arrayList = list;
      self.setData({
        //拿到数据之后初始化列表
        areaArry: [arrayList, arrayList[0].children, arrayList[0].children[0].children]
      })
    })
  },  
      
        
 bindMultiPickerColumnChange: function (e) {
 	var that = this;
    console.log("多级联动控制", e);
    var that = this;
    //获取当前滚动的是哪一列,通过判断哪一列来实时控制下一列的变化
    console.log("第", e.detail.column + 1, '列。第', e.detail.value + 1, '个数据');
    switch (e.detail.column) {
      case 0://第一列
        var list2 = [],
          list3 = [];
        //选择第一列的这个值然后找到它的儿子
        list2 = that.data.areaArry[e.detail.value].children;
        //实时修改第二列,并且把第二列设置到第一个展示
        list3 = list2[0].children
        that.setData({
          "areaArry[1]": list2,
          "areaArry[2]": list3,
          "multiIndex[0]": e.detail.value,
          "multiIndex[1]": 0,
          "multiIndex[2]": 0,
        })
        console.log(that.data.multiIndex);
        break;
      case 1://第二列
        var list3 = [];
        //从所有第二列的内容中取出与第一列选中状态的值对应的数据用于实时生成第二列  ?????
        list3 = that.data.areaArry[1][e.detail.value].children
        that.setData({
          "areaArry[2]": list3,
          "multiIndex[1]": e.detail.value,
          "multiIndex[2]": 0
        })
        break;
      case 2://第三列
        that.setData({
          "multiIndex[2]": e.detail.value
        })
        break;
    }
    console.log(that.data.areaArry)

  },

bindAreaChange: function (e) {
    var that = this;
    var result = e.detail.value;
    var multiIndex = that.data.multiIndex
    result = arrayList[multiIndex[0]].children[multiIndex[1]].children[multiIndex[2]];
    that.setData({
      rqstAreaCode: result.text,
      realrqstAreaCode: result.value
    })
    console.log('已选择的区域名称', that.data.rqstAreaCode);
    console.log('已选择的区域代码', that.data.realrqstAreaCode);
  },
})



版权声明:本文为weixin_49376462原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。