小程序模板网

秀杰实战教程系列《三》:下拉筛选菜单WXDropDownMenu组件

发布时间:2018-03-20 14:02 所属栏目:小程序开发教程

适用于商品列表筛选与功能菜单跳转

 
 
 
先来看下效果图:
 
思路与步骤:
 
布局方面,整体使用dl来写,二级包在dd中,用ul li来写;交互方面,点击某一级菜单,关闭兄弟子菜单,点击某子菜单关闭所有菜单。
 
1.使用dt做出第一级菜单
 
2.使用dd嵌套第二级菜单,初始隐藏、position为absolute,使用z-index浮出页面层
 
/*总菜单容器*/
.menu {
     display: block;
    height: 38px;
}
 
/*一级菜单*/
.menu dt {
    font-size: 15px;
    float: left;
    /*hack*/
    width: 33%;
    height: 38px;
    border-right: 1px solid #d2d2d2;
    border-bottom: 1px solid #d2d2d2;
    text-align: center;
    background-color: #f4f4f4;
    color: #5a5a5a;
    line-height: 38px;
}
 
/*二级菜单外部容器样式*/
.menu dd{
    position: absolute;
    width: 100%;
    /*hack*/
    top:39px;
    left:0;
    z-index:999;
}
 
/*二级菜单普通样式*/
.menu li{
    font-size: 14px;
    line-height: 34px;
    color: #575757;
    height: 34px;
    display: block;
    padding-left: 8px;
    background-color: #fff;
    border-bottom: 1px solid #dbdbdb;
}
查看效果,接下来实现点击事件。
 
 
3.dt绑定点击事件tapMainMenu,flag控制显隐toggle,提供2个class,hidden与show,来控制显隐。注:dt也是可以bindTap的,不单是view。
 
/* 显示与隐藏 */
.show {
    display: block;
}
 
.hidden {
    display: none;
}
4.关闭所有一级菜单,每个一级菜单都有一个index标识,由tapMainMenu事件传递过去,与数组subMenuDisplay一一对应,当前元素subMenuDisplay[index]视原来状态决定是显示或隐藏。
 
核心代码:
 
<dl class="menu">
    <dt data-index="0" bindtap="tapMainMenu">价格</dt>
    <dd class="{{subMenuDisplay[0]}}">
        <ul><li>sub1</li><li>sub2</li></ul>
    </dd>
</dl>
// 使用function初始化array,相比var initSubMenuDisplay = [] 既避免的引用复制的,同时方式更灵活,将来可以是多种方式实现,个数也不定的
function initSubMenuDisplay() {
    return ['hidden', 'hidden', 'hidden'];
}
 
Page({
    data:{
        subMenuDisplay:initSubMenuDisplay()
    },
    tapMainMenu: function(e) {
//        获取当前显示的一级菜单标识
        var index = parseInt(e.currentTarget.dataset.index);
        // 生成数组,全为hidden的,只对当前的进行显示
        var newSubMenuDisplay = initSubMenuDisplay();
//        如果目前是显示则隐藏,反之亦反之。同时要隐藏其他的菜单
        if(this.data.subMenuDisplay[index] == 'hidden') {
            newSubMenuDisplay[index] = 'show';
        } else {
            newSubMenuDisplay[index] = 'hidden';
        }
        // 设置为新的数组
        this.setData({
            subMenuDisplay: newSubMenuDisplay
        });
    }
});
5.选中二级菜单当前项,但给个系统icon及改变背景色,文本加粗,同样改变一级菜单标题,demo中给出一个弹窗
 
声明tapSubMenu方法,监听二级点击事件
 
    tapSubMenu: function(e) {
        //        获取当前显示的一级菜单标识
        var index = parseInt(e.currentTarget.dataset.index);
        console.log(index);
        // 隐藏所有一级菜单
        this.setData({
            subMenuDisplay: initSubMenuDisplay()
        });
    }
加highlight效果
 
/*二级菜单高亮样式*/
.menu li.highlight{
    background-color: #f4f4f4;
}
与一级菜单不同,使用二维数组的方式实现点击高亮,这样才能定位到是某一级的某二级菜单,再决定显示隐藏。 布局文件改成:
 
    <dd class="{{subMenuDisplay[0]}}">
        <ul>
            <li class="{{subMenuHighLight[0][0]}}" data-index="0-0" bindtap="tapSubMenu">100以内</li>
            <li class="{{subMenuHighLight[0][1]}}" data-index="0-1" bindtap="tapSubMenu">100-500</li>
            <li class="{{subMenuHighLight[0][2]}}" data-index="0-2" bindtap="tapSubMenu">500-1000</li>
            <li class="{{subMenuHighLight[0][3]}}" data-index="0-3" bindtap="tapSubMenu">1000-3000</li>
            <li class="{{subMenuHighLight[0][4]}}" data-index="0-4" bindtap="tapSubMenu">3000以上</li>
        </ul>
    </dd>
效果如图

 
 
相应的js代码要写成:
 
//声明初始化高亮状态数组
function initSubMenuHighLight() {
    return [
        ['','','','',''],
        ['',''],
        ['','','']
    ];
}
点击事件
 
tapSubMenu: function(e) {
        // 隐藏所有一级菜单
        this.setData({
            subMenuDisplay: initSubMenuDisplay()
        });
        // 处理二级菜单,首先获取当前显示的二级菜单标识
        var indexArray = e.currentTarget.dataset.index.split('-');
        console.log("indexArray : " + indexArray);
        var newSubMenuHighLight = initSubMenuHighLight();
        // 与一级菜单不同,这里不需要判断当前状态,只需要点击就给class赋予highlight即可
        newSubMenuHighLight[indexArray[0]][indexArray[1]] = 'highlight';
        console.log(newSubMenuHighLight);
        // 设置为新的数组
        this.setData({
            subMenuHighLight: newSubMenuHighLight
        });
    }
这样就实现了高亮与取消高亮。但还没完,与一级菜单不同,这里与兄弟子菜单是非互斥的,也就是说点击了本菜单,是不能一刀切掉兄弟菜单的高亮状态的。于是我们改进js代码。
 
声明方式,改用变量形式,方便存储。
 
//定义初始化数据,用于运行时保存
var initSubMenuHighLight = [
        ['','','','',''],
        ['',''],
        ['','','']
    ];
点击事件
 
    tapSubMenu: function(e) {
        // 隐藏所有一级菜单
        this.setData({
            subMenuDisplay: initSubMenuDisplay()
        });
        // 处理二级菜单,首先获取当前显示的二级菜单标识
        var indexArray = e.currentTarget.dataset.index.split('-');
        // 初始化状态
        // var newSubMenuHighLight = initSubMenuHighLight;
        for (var i = 0; i < initSubMenuHighLight.length; i++) {
            // 如果点中的是一级菜单,则先清空状态,即非高亮模式,然后再高亮点中的二级菜单;如果不是当前菜单,而不理会。经过这样处理就能保留其他菜单的高亮状态
            if (indexArray[0] == i) {
                for (var j = 0; j < initSubMenuHighLight[i].length; j++) {
                    // 实现清空
                    initSubMenuHighLight[i][j] = '';
                }
                // 将当前菜单的二级菜单设置回去
            }
        }
 
        // 与一级菜单不同,这里不需要判断当前状态,只需要点击就给class赋予highlight即可
        initSubMenuHighLight[indexArray[0]][indexArray[1]] = 'highlight';
        // 设置为新的数组
        this.setData({
            subMenuHighLight: initSubMenuHighLight
        });
    }
有待完善功能点:
 
1.显示与隐藏带动画下拉
 
2.抽象化,使用回调函数,将监听每个二级菜单的点击
 
3.数据源与显示应当是分离的,一级与二级菜单的key value应该是独立在外,系统只认index,然后对相应点击作处理,跳转页面,筛选结果等
 
4.点击二级菜单时,会将全部组的清除,有待修复


易优小程序(企业版)+灵活api+前后代码开源 码云仓库:starfork
本文地址:https://www.eyoucms.com/wxmini/doc/course/22767.html 复制链接 如需定制请联系易优客服咨询:800182392 点击咨询
QQ在线咨询