PHP群:95885625 Hbuilder+MUI群:81989597 站长QQ:634381967
    您现在的位置: 首页 > 开发编程 > HBuilderX教程 > 正文

    HBuilder mui webview模式选项卡实现滑动切换

    作者:admin来源:网络浏览:时间:2020-09-30 00:07:50我要评论
    导读:关于选项卡切换,相信大家都不陌生。hello mui中提供了多种选项卡切换的实现方式,不过大体分为div模式(单页)以及webviedw模式(多个页...
    关于选项卡切换,相信大家都不陌生。hello mui中提供了多种选项卡切换的实现方式,不过大体分为div模式(单页)以及webviedw模式(多个页面)。div模式中又提供了可左右拖动实现切换的模式,如图:


    在实际开发中,数据量只会多不会少,因此我们通常都会采用webview模式选项卡。与此同时,许多同学依旧希望能够实现滑动来实现选项卡的切换。就像这样:

    可能大家会说,这个滑动并不是那么灵敏。那是因为我控制的角度范围较小(更加精确方便的范围还在进一步测试),实际开发中大家可以根据自己的需求来修改这个范围。
    一、main.html
    在主页面,我们需要做许多事情,创建自窗口对象(不然切什么换),底部选项点击切换(这是基本的切换),自定义事件切换(子窗口滑动事件来触发)。
    其中关键的地方,在于切换。切换,我们要切什么,换什么这才是选项卡切换的核心。
    切,有两种切法,点击和滑动。
    换,换子窗口,换标题,换底部高亮文字。

    <!doctype html>
    <html>
    
        <head>
            <meta charset="UTF-8">
            <title></title>
            <meta name="viewport" content="width=device-width,initial-scale=1,minimum-scale=1,maximum-scale=1,user-scalable=no" />
            <link href="http://ask.dcloud.net.cn/css/mui.min.css" rel="stylesheet" />
        </head>
    
        <body>
            <header class="mui-bar mui-bar-nav">
                <h1 class="mui-title">首页</h1>
            </header>
            <nav class="mui-bar mui-bar-tab">
                <a class="mui-tab-item mui-active" data-index="0">
                    <span class="mui-icon mui-icon-home"></span>
                    <span class="mui-tab-label">首页</span>
                </a>
                <a class="mui-tab-item" data-index="1">
                    <span class="mui-icon mui-icon-phone"></span>
                    <span class="mui-tab-label">电话</span>
                </a>
                <a class="mui-tab-item" data-index="2">
                    <span class="mui-icon mui-icon-email"></span>
                    <span class="mui-tab-label">邮件</span>
                </a>
                <a class="mui-tab-item" data-index="3">
                    <span class="mui-icon mui-icon-gear"></span>
                    <span class="mui-tab-label">设置</span>
                </a>
            </nav>
            <script src="js/mui.min.js"></script>
            <script type="text/javascript">
                mui.init();
                mui.plusReady(function() {
                    /**
                     * 当前窗口对象,即父窗口;
                     * http://www.html5plus.org/doc/zh_cn/webview.html#plus.webview.currentWebview
                     */
                    var self = plus.webview.currentWebview();
                    // 子窗口地址数组
                    var subpages = ["home.html", "phone.html", "email.html", "gear.html"];
                    // 子窗口样式
                    var subStyles = {
                        top: "45px",
                        bottom: "50px"
                    };
                    // 子窗口数量
                    var subLen = subpages.length;
                    // 子窗口对象数组
                    var subWvs = [];
                    // 标题栏
                    var title = document.querySelector(".mui-title");
                    // 底部选项
                    var tabs = document.querySelectorAll(".mui-tab-item");
                    // 底部文字
                    var labels = document.querySelectorAll(".mui-tab-label");
                    // 当前页面索引,初始化为0;
                    var activeIndex = 0;
                    // 目标页面索引,初始化为当前页面索引;
                    var targetIndex = activeIndex;
                    // 创建子页面
                    for(var i = 0; i < subLen; i  ) {
                        /**
                         * 创建窗口对象,并将索引做为额外的参数传递;
                         * http://www.html5plus.org/doc/zh_cn/webview.html#plus.webview.create
                         */
                        var subWv = plus.webview.create(subpages[i], cutWebviewId(subpages[i]), subStyles, {
                            index: i
                        });
                        // 窗口对象添加至数组
                        subWvs.push(subWv);
                        if(i > 0) {
                            /**
                             * 隐藏非第一页的窗口对象
                             * http://www.html5plus.org/doc/zh_cn/webview.html#plus.webview.WebviewObject.hide
                             */
                            subWv.hide("none");
                        }
                        /**
                         * 向父窗口添加子窗口
                         * http://www.html5plus.org/doc/zh_cn/webview.html#plus.webview.WebviewObject.append
                         */
                        self.append(subWv);
                    }
                    // 底部选项卡点击切换事件
                    for(var j = 0, jlen = tabs.length; j < jlen; j  ) {
                        tabs[j].addEventListener("tap", function() {
                            // 获取当前结点的索引
                            targetIndex = this.getAttribute("data-index");
                            // 转换为number类型
                            targetIndex = parseInt(targetIndex, 10);
                            if(targetIndex == activeIndex) {
                                return;
                            }
                            // 切换页面
                            switchPage("tap", activeIndex, targetIndex);
                        });
                    }
                    // 子页面滑动切换事件
                    window.addEventListener("swipe_event", function(event) {
                        // 获取方向以及索引
                        var direction = event.detail.direction;
                        activeIndex = event.detail.index;
                        if(direction == "left") {
                            // 如果是最后一个页面,则不做左滑切换;
                            if(activeIndex == subLen - 1) {
                                console.log("最右边一页了");
                                return;
                            }
                            // 目标页面的索引为后面一位
                            targetIndex = activeIndex   1;
                        } else {
                            // 如果是第一个页面,则不做右滑切换;
                            if(activeIndex == 0) {
                                console.log("最左边一页了");
                                return;
                            }
                            // 目标页面的索引为前面一位
                            targetIndex = activeIndex - 1;
                        }
                        // 切换页面
                        switchPage("switch", activeIndex, targetIndex);
                    });
    
                    /**
                     * 切换页面
                     * @param {String} _event 事件类型
                     * @param {Number} _active 当前页面索引
                     * @param {Number} _target 目标页面索引
                     */
                    function switchPage(_event, _active, _target) {
                        /**
                         * 目标页面展示
                         * http://www.html5plus.org/doc/zh_cn/webview.html#plus.webview.WebviewObject.show
                         */
                        subWvs[_target].show("fade-in");
                        // 顶部文字替换
                        title.innerText = labels[_target].innerText;
                        // 如果是滑动事件,则手动切换高亮选项;
                        if(_event == "switch") {
                            tabs[_active].classList.remove("mui-active");
                            tabs[_target].classList.add("mui-active");
                        }
                        // 之前展示的页面隐藏
                        subWvs[_active].hide("none");
                        // 更新当前页索引
                        activeIndex = _target;
                    }
                });
    
                /**
                 * 截取url地址,获取窗口的id;
                 * @param {String} url html文件的路径
                 * @param {String} wvId webviewObject的id
                 */
                function cutWebviewId(url) {
                    var startIndex = url.lastIndexOf("/");
                    var endIndex = url.lastIndexOf(".html");
                    var wvId = url.substring(startIndex   1, endIndex);
                    return wvId;
                }
            </script>
        </body>
    
    </html>
    

    明确了我们要干什么,我们来看下切换的这个函数:

    /**
     * 切换页面
     * @param {String} _event 事件类型
     * @param {Number} _active 当前页面索引
     * @param {Number} _target 目标页面索引
     */
    function switchPage(_event, _active, _target) {
        /**
         * 目标页面展示
         * http://www.html5plus.org/doc/zh_cn/webview.html#plus.webview.WebviewObject.show
         */
        subWvs[_target].show("fade-in");
        // 顶部文字替换
        title.innerText = labels[_target].innerText;
        // 如果是滑动事件,则手动切换高亮选项;
        if(_event == "switch") {
            tabs[_active].classList.remove("mui-active");
            tabs[_target].classList.add("mui-active");
        }
        // 之前展示的页面隐藏
        subWvs[_active].hide("none");
        // 更新当前页索引
        activeIndex = _target;
    }
    

    _event代表切的方式,_active代表当前展示的窗口索引,_target代表目标窗口的索引。
    首先将目标窗口show出来,然后替换顶部标题的文字内容。然后判定下切的方式,如果是滑动切换,我们需要自己来对classList进行操作,完成选项卡高亮的转换。最后,我们需要把之前展示的选项卡隐藏掉,并且把当前窗口的索引值赋给中间量。
    二、sub.js
    所有的子页面都引入这个JS文件,内容如下:

    mui.init();
    mui.plusReady(function() {
        // 获取当前窗口对象
        var self = plus.webview.currentWebview();
        // 读取传递过来的参数
        var index = self.index;
        /**
         * 获取父窗口对象
         * http://www.html5plus.org/doc/zh_cn/webview.html#plus.webview.WebviewObject.parent
         */
        var parent = self.parent();
        // 左滑事件
        document.addEventListener("swipeleft", function(event) {
            var angle = event.detail.angle;
            angle = Math.abs(angle);
            /**
             * 控制滑动的角度,为避免误操作,可自定义限制滑动角度;
             */
            if(angle > 175 && angle < 185) {
                parentEvent(parent, index, "left");
            }
        });
        // 右滑事件
        document.addEventListener("swiperight", function(event) {
            var angle = event.detail.angle;
            angle = Math.abs(angle);
            /**
             * 控制滑动的角度,为避免误操作,可自定义限制滑动角度;
             */
            if(angle < 4) {
                parentEvent(parent, index, "right");
            }
        });
    });
    
    /**
     * 触发父窗口自定义事件
     * @param {Object} wvobj 目标窗口对象
     * @param {Number} index 索引值
     * @param {String} direction 方向
     */
    function parentEvent(wvobj, index, direction) {
        /**
         * 触发自定义事件
         * http://dev.dcloud.net.cn/mui/event/#customevent
         */
        mui.fire(wvobj, "swipe_event", {
            direction: direction,
            index: index
        });
    }
    

    内容简单明了,就是监听左滑和右滑事件,然后去触发父窗口的自定义切换事件。关键点在于event.detail.angle,这个是mui自己封装的一个属性,用来表示滑动的角度(具体的值,大家可以自己滑动时候多测试测试)。大家也可以尝试下,不对滑动角度进行控制,切换会过于灵敏,影响到其他正常的操作。
    文笔功力有限,有哪些地方不是很明了,还请见谅,也希望能提出您宝贵的意见,我会继续改进。
    最后,老规矩,附上源码,真机运行就能体验效果。

    webviewSwipe.zip


    转载请注明(B5教程网)原文链接:https://b5.mxunkeji.com/content-146-4969-1.html
    相关热词搜索: