html自定義垂直導航菜單(增強版--自定義傳入menu參數,支持JSONArray、JSArray、JSONObject、JSObject)

在上一篇中我簡單寫了個html自定義垂直導航菜單,缺點很明顯,裏面的數據是固定死的,不能動態更改數據。javascript

這裏我重寫了一個修改版的垂直二級導航菜單,將原先的menuBox.init(config);修改成menuBox.init(config, dataObj);,這裏的dataObj就是要傳入的菜單的數據,能夠傳入的類型有JSONArray、JSArray、JSONObject、JSObject,其實JSONObject就是JSONArray中的一個元素,JSObject也是JSArray中的一個元素。css

先上效果圖:html

怎麼樣,還能夠吧(做爲一名菜雞,作個二級菜單不容易,吹一波不過度),順便附上源碼:menuBox1.1.zipjava

你徹底能夠按照你的需求修改對應的css樣式,打造屬於你本身的二級菜單。jquery

上代碼:web

JSObjectchrome

{
    name: "spMenu1",
    iconClasses: "fa fa-chrome",
    subMenus: [{
        name: "subMenu11",
        url: "#"
    }, {
        name: "subMenu12",
        url: "#"
    }, {
        name: "subMenu13",
        url: "#"
    }, {
        name: "subMenu14",
        url: "#"
    }]
}

 

這裏須要解釋下:json

上面的js就是一級菜單的JSObject元素(固然,你也能夠轉化爲標準的json字符串格式),屬性分別是:數組

name:當前一級菜單的名稱app

iconClasses:在效果圖中你們能夠看到,每一個一級菜單前面是有圖標的,這裏使用的是fontawesome(舊版本,你能夠使用新版本,將font-awesome文件夾替換掉就能夠使用新的class樣式圖標了),這裏的iconClasses就是<i></i>的class,你能夠添加屬於本身的圖標,若是你想添加書籤的圖標,你能夠傳入字符串"fa fa-bookmark",挺簡潔的。

subMenus:這個就是二級菜單的數組集合了,這裏默認二級菜單沒有圖標,只有名稱和url(點擊跳轉或者切換內容區域的url)

 

html

<!DOCTYPE html>
<html>

    <head>
        <meta charset="UTF-8">
        <link rel="stylesheet" href="font-awesome/css/font-awesome.css" />
        <link rel="stylesheet" href="css/menuBox-1.1.css" />
        <script type="text/javascript" src="js/json2.js"></script>
        <script type="text/javascript" src="js/jquery-1.9.1.js"></script>
        <script type="text/javascript" src="js/checkutil.js"></script>
        <script type="text/javascript" src="js/menuBox-1.1.js"></script>
        <title></title>
    </head>
    <style>
        .menuBox {
            margin: 20px;
        }
    </style>

    <body>
        <div id="menuBox01" class="menuBox">

        </div>
        <div id="menuBox02" class="menuBox">

        </div>
        <div id="menuBox03" class="menuBox">

        </div>
        <div id="menuBox04" class="menuBox">

        </div>
    </body>
    <script>
        var dataObj01 = [{
            name: "spMenu1",
            iconClasses: "fa fa-chrome",
            subMenus: [{
                name: "subMenu11",
                url: "#"
            }, {
                name: "subMenu12",
                url: "#"
            }, {
                name: "subMenu13",
                url: "#"
            }, {
                name: "subMenu14",
                url: "#"
            }]
        }, {
            name: "spMenu2",
            iconClasses: "fa fa-firefox",
            subMenus: [{
                name: "subMenu21",
                url: "#"
            }, {
                name: "subMenu22",
                url: "#"
            }, {
                name: "subMenu23",
                url: "#"
            }, {
                name: "subMenu34",
                url: "#"
            }]
        }, {
            name: "spMenu3",
            iconClasses: "fa fa-internet-explorer",
            subMenus: [{
                name: "subMenu31",
                url: "#"
            }, {
                name: "subMenu32",
                url: "#"
            }, {
                name: "subMenu33",
                url: "#"
            }, {
                name: "subMenu34",
                url: "#"
            }]
        }];

        var config01 = {
            menuBoxId: "#menuBox01",
            multiple: true,
            openIndex: []
        }
        menuBox.init(config01, dataObj01);

        var dataObj02 = JSON.stringify(dataObj01);

        var config02 = {
            menuBoxId: "#menuBox02",
            multiple: false,
            openIndex: []
        }
        menuBox.init(config02, dataObj02);

        var dataObj03 = {
            name: "spMenu1",
            iconClasses: "fa fa-chrome",
            subMenus: [{
                name: "subMenu11",
                url: "#"
            }, {
                name: "subMenu12",
                url: "#"
            }, {
                name: "subMenu13",
                url: "#"
            }, {
                name: "subMenu14",
                url: "#"
            }]
        };
        var config03 = {
            menuBoxId: "#menuBox03",
            multiple: false,
            openIndex: []
        }
        menuBox.init(config03, dataObj03);

        var dataObj04 = JSON.stringify(dataObj03);
        var config04 = {
            menuBoxId: "#menuBox04",
            multiple: true,
            openIndex: []
        }
        menuBox.init(config04, dataObj04);
    </script>

</html>

menuBox-1.1.css

body {
    margin: 0;
}

ul {
    list-style: none;
    padding: 0;
    margin: 0;
}


/**菜單box**/

.menuBox {
    width: 300px;
    margin: 5px;
}


/**默認不顯示二級菜單**/

.menuBox .subMenuBox {
    display: none;
}


/**一級菜單樣式**/

.spMenuBox>*>.spMenu {
    align-items: center;
    background: darkslateblue;
    border-bottom: 1px solid lightgray;
    cursor: pointer;
    color: white;
    /**flexbox兼容**/
    display: -webkit-box;
    /* OLD - iOS 6-, Safari 3.1-6 */
    display: -moz-box;
    /* OLD - Firefox 19- (doesn't work very well) */
    display: -ms-flexbox;
    /* TWEENER - IE 10 */
    display: -webkit-flex;
    /* NEW - Chrome */
    display: flex;
    /**flexbox兼容**/
    -webkit-box-orient: horizontal;
    -webkit-flex-direction: row;
    -moz-flex-direction: row;
    -ms-flex-direction: row;
    -o-flex-direction: row;
    flex-direction: row;
    /**flexbox兼容**/
    -webkit-justify-content: space-around;
    -webkit-box-pack: space-around;
    -moz-box-pack: space-around;
    -ms-flex-pack: space-around;
    justify-content: space-around;
    /**user-select兼容**/
    -webkit-user-select: none;
    -moz-user-select: none;
    -ms-user-select: none;
    -o-user-select: none;
    user-select: none;
}


/**最後一個一級菜單樣式**/

.spMenuBox>*:last-child>.spMenu {
    align-items: center;
    background: darkslateblue;
    border-bottom: 0px;
    color: white;
    cursor: pointer;
    /**flexbox兼容**/
    display: -webkit-box;
    /* OLD - iOS 6-, Safari 3.1-6 */
    display: -moz-box;
    /* OLD - Firefox 19- (doesn't work very well) */
    display: -ms-flexbox;
    /* TWEENER - IE 10 */
    display: -webkit-flex;
    /* NEW - Chrome */
    display: flex;
    /**flexbox兼容**/
    -webkit-box-orient: horizontal;
    -webkit-flex-direction: row;
    -moz-flex-direction: row;
    -ms-flex-direction: row;
    -o-flex-direction: row;
    flex-direction: row;
    /**flexbox兼容**/
    webkit-justify-content: space-around;
    -webkit-box-pack: space-around;
    -moz-box-pack: space-around;
    -ms-flex-pack: space-around;
    justify-content: space-around;
    /**user-select兼容**/
    -webkit-user-select: none;
    -moz-user-select: none;
    -ms-user-select: none;
    -o-user-select: none;
    user-select: none;
}


/**箭頭切換用動畫實現**/

.spMenuItem>.spMenu>.fa-angle-down {
    -webkit-transition: all 0.5s ease;
    -moz-transition: all 0.5s ease;
    -ms-transition: all 0.5s ease;
    -o-transition: all 0.5s ease;
    transition: all 0.5s ease;
}

.spMenuItem.active>.spMenu>.fa-angle-down {
    -webkit-transform: rotate(-180deg);
    -moz-transform: rotate(-180deg);
    -ms-transform: rotate(-180deg);
    -o-transform: rotate(-180deg);
    transform: rotate(-180deg);
}


/**二級菜單樣式*/

.subMenuBox>*>.subMenu {
    color: darkgray;
    align-items: center;
    background: darkgreen;
    border-bottom: 1px solid lightyellow;
    cursor: pointer;
    padding: 5px 10px;
    /**flexbox兼容**/
    display: -webkit-box;
    /* OLD - iOS 6-, Safari 3.1-6 */
    display: -moz-box;
    /* OLD - Firefox 19- (doesn't work very well) */
    display: -ms-flexbox;
    /* TWEENER - IE 10 */
    display: -webkit-flex;
    /* NEW - Chrome */
    display: flex;
    /**flexbox兼容**/
    -webkit-box-orient: horizontal;
    -webkit-flex-direction: row;
    -moz-flex-direction: row;
    -ms-flex-direction: row;
    -o-flex-direction: row;
    flex-direction: row;
    /**user-select兼容**/
    -webkit-user-select: none;
    -moz-user-select: none;
    -ms-user-select: none;
    -o-user-select: none;
    user-select: none;
}


/**最後一個二級菜單樣式**/

.subMenuBox>*:last-child>.subMenu {
    color: darkgray;
    align-items: center;
    background: #darkgreen;
    border-bottom: 0px;
    cursor: pointer;
    padding: 5px 10px;
    /**flexbox兼容**/
    display: -webkit-box;
    /* OLD - iOS 6-, Safari 3.1-6 */
    display: -moz-box;
    /* OLD - Firefox 19- (doesn't work very well) */
    display: -ms-flexbox;
    /* TWEENER - IE 10 */
    display: -webkit-flex;
    /* NEW - Chrome */
    display: flex;
    /**flexbox兼容**/
    -webkit-box-orient: horizontal;
    -webkit-flex-direction: row;
    -moz-flex-direction: row;
    -ms-flex-direction: row;
    -o-flex-direction: row;
    flex-direction: row;
    /**user-select兼容**/
    -webkit-user-select: none;
    -moz-user-select: none;
    -ms-user-select: none;
    -o-user-select: none;
    user-select: none;
}

menuBox-1.1.js:

/**
 * 須要用到的js:
 *         jquery.js
 *         json2.js
 *         checkutil.js
 * 示例:
 *      var dataObj01 = [{
 *          name: "spMenu1",
 *          iconClasses: "fa fa-chrome",
 *          subMenus: [{
 *              name: "subMenu11",
 *              url: "#"
 *          }, {
 *              name: "subMenu12",
 *              url: "#"
 *          }, {
 *              name: "subMenu13",
 *              url: "#"
 *          }, {
 *              name: "subMenu14",
 *              url: "#"
 *          }]
 *      }, {
 *          name: "spMenu2",
 *          iconClasses: "fa fa-firefox",
 *          subMenus: [{
 *              name: "subMenu21",
 *              url: "#"
 *          }, {
 *              name: "subMenu22",
 *              url: "#"
 *          }, {
 *              name: "subMenu23",
 *              url: "#"
 *          }, {
 *              name: "subMenu34",
 *              url: "#"
 *          }]
 *      }, {
 *          name: "spMenu3",
 *          iconClasses: "fa fa-internet-explorer",
 *          subMenus: [{
 *              name: "subMenu31",
 *              url: "#"
 *          }, {
 *              name: "subMenu32",
 *              url: "#"
 *          }, {
 *              name: "subMenu33",
 *              url: "#"
 *          }, {
 *              name: "subMenu34",
 *              url: "#"
 *          }]
 *      }];
 *  
 *      var config01 = {
 *          menuBoxId: "#menuBox01",
 *          multiple: true,
 *          openIndex: []
 *      }
 *      menuBox.init(config01, dataObj01);
 *  
 *      var dataObj02 = JSON.stringify(dataObj01);
 *  
 *      var config02 = {
 *          menuBoxId: "#menuBox02",
 *          multiple: false,
 *          openIndex: []
 *      }
 *      menuBox.init(config02, dataObj02);
 *  
 *      var dataObj03 = {
 *          name: "spMenu1",
 *          iconClasses: "fa fa-chrome",
 *          subMenus: [{
 *              name: "subMenu11",
 *              url: "#"
 *          }, {
 *              name: "subMenu12",
 *              url: "#"
 *          }, {
 *              name: "subMenu13",
 *              url: "#"
 *          }, {
 *              name: "subMenu14",
 *              url: "#"
 *          }]
 *      };
 *      var config03 = {
 *          menuBoxId: "#menuBox03",
 *          multiple: false,
 *          openIndex: []
 *      }
 *      menuBox.init(config03, dataObj03);
 *  
 *      var dataObj04 = JSON.stringify(dataObj03);
 *      var config04 = {
 *          menuBoxId: "#menuBox04",
 *          multiple: true,
 *          openIndex: []
 *      }
 *      menuBox.init(config04, dataObj04);
 *  
 * @author DarkRanger
 * http: //www.cnblogs.com/wrcold520/
 */

! function($, JSON, checkutil) {
    "use strict";

    var menuBox = function() {};
    //要配置的menuBox的菜單id
    menuBox.menuBoxId = undefined;
    //是否能夠顯示多個上級菜單的子菜單
    menuBox.multiple = false;
    //默認關閉全部一級菜單
    menuBox.openIndex = [];

    //menuBox初始化方法
    menuBox.init = function(config, data) {

        var cntMenuBox = new menuBox();

        var menuBoxEle;
        //定義上級菜單spMenu數組
        var spMenus;

        var boxId = config.menuBoxId;
        var menuBoxEle = $(boxId);

        if(boxId == undefined) {
            console.warn("Your menuBox config has not key['menuBoxId'], configure failed!!!\nPlease configure your unique menuBox by MenuBoxId!");
            return;
        } else if(menuBoxEle.length == 0) {
            console.warn("Cannot find your menuBox[id: " + boxId + "], configure failed!!! ");
            return;
        } else {
            cntMenuBox.menuBoxId = $(config.menuBoxId) ? config.menuBoxId : undefined;
            menuBoxEle = $(cntMenuBox.menuBoxId);
            if(data) {
                genDomByData(menuBoxEle, data);
            }
        }

        if(config.multiple == undefined) {
            console.warn("Your config has not key['multiple'], default value is false that means you could open one spMenu at most at the same time!");
        } else {
            cntMenuBox.multiple = config.multiple;
        }

        if(config.openIndex == undefined) {
            console.warn("your config has not key['openIndex'] , default value is a Number Array which's length is 0!");
        } else if(!config.openIndex instanceof Array) {
            throw new Error("your config 'openIndex' should be a number Array");
        } else {
            cntMenuBox.openIndex = unique(config.openIndex, false);
        }

        //肯定對應的menuBox
        cntMenuBox.menuBoxId = config.menuBoxId;
        //是否打開其餘某一個的時候關閉其餘選項
        var closeOthers = !cntMenuBox.multiple;
        //初始化點擊事件
        initClickEvent(cntMenuBox, closeOthers);
        //肯定上級菜單數組
        spMenus = $(cntMenuBox.menuBoxId + " .spMenu");
        //打開傳入的數組
        for(var i in cntMenuBox.openIndex) {
            var index = cntMenuBox.openIndex[i];
            var spMenu = spMenus[index];
            if(spMenu) {
                openSpMenu(cntMenuBox.menuBoxId, index);
                if(!cntMenuBox.multiple) {
                    break;
                }
            }
        }
    };
    /**
     * 循環建立dom樹
     * @param {Object} menuBoxEle menuBoxEle的根元素(Jquery對象元素)
     * @param {Object} data
     */
    function genDomByData(menuBoxEle, data) {
        var dataObj;
        //JS Object or JS Array
        if(checkutil.isArray(data)) {
            dataObj = data;
        } else if(checkutil.isObject(data)) {
            dataObj = [data];
        }
        //JSONString
        else if(checkutil.isString(data)) {
            var menuObj;
            try {
                var menuJson = JSON.parse(data);
                if(checkutil.isArray(menuJson)) {
                    menuObj = menuJson;
                } else if(checkutil.isObject(menuJson)) {
                    menuObj = [menuJson];
                }
                dataObj = menuObj;
            } catch(e) {
                throw new Error("Please modify your data to a standard jsonString or Array!!!\n請修改您傳入的data爲標準的json字符串或者數組!!!");
            }
        }

        //建立ul
        var spMenuBoxEle = $("<ul>", {
            "class": "spMenuBox",
        });
        //循環建立li
        $.each(dataObj, function(index, spMenuItem) {

            var spMenuItemEle = $("<li>", {
                "class": "spMenuItem"
            });
            //建立li下面的div
            var spMenuDiv = $("<div>", {
                "class": "spMenu",
            });

            //建立div下面文本前面的icon
            var iconBefore = $("<i>", {
                "class": spMenuItem.iconClasses,
            });
            //建立文本
            var menuSpan = $("<span>", {
                text: spMenuItem.name,
            });
            //建立div下面文本後面的icon
            var iconAfter = $("<i>", {
                "class": "fa fa-2x fa-angle-down"
            });

            iconBefore.appendTo(spMenuDiv);
            menuSpan.appendTo(spMenuDiv);
            iconAfter.appendTo(spMenuDiv);

            spMenuDiv.appendTo(spMenuItemEle);
            //建立子menu的ul
            var subMenuBox = $("<ul>", {
                "class": "subMenuBox",
            })
            $.each(spMenuItem.subMenus, function(index, subMenu) {
                //<li><span class="subMenu">菜單1.1</span></li>
                var subMenuItem = $("<li>", {})
                var subMenuSpan = $("<a>", {
                    "class": "subMenu",
                    "href": subMenu.url,
                    text: subMenu.name
                })
                subMenuSpan.appendTo(subMenuItem);
                subMenuItem.appendTo(subMenuBox);
            });
            subMenuBox.appendTo(spMenuItemEle);

            spMenuItemEle.appendTo(spMenuBoxEle);
        });
        spMenuBoxEle.appendTo(menuBoxEle);
    }

    function unique(arr) {
        var result = [],
            hash = {};
        for(var i = 0, elem;
            (elem = arr[i]) != null; i++) {
            if(!hash[elem]) {
                result.push(elem);
                hash[elem] = true;
            }
        }
        return result;
    }

    //初始化點擊事件
    function initClickEvent(menuBox, closeOthers) {
        $(menuBox.menuBoxId + " .spMenu").on("click", function() {
            var cntSpMenu$ = $(this);
            //要切換的元素
            cntSpMenu$.next().slideToggle();
            cntSpMenu$.parent().toggleClass("active")

            var cntSpMenu = cntSpMenu$['context'];
            if(closeOthers == true) {
                var spMenus = $(menuBox.menuBoxId + " .spMenu");
                $.each(spMenus, function(index, spMenu) {
                    if(cntSpMenu != spMenu) {
                        closeSpMenu(menuBox.menuBoxId, index);
                    }
                });
            }
        });
    }

    //打開某一個item
    function openSpMenu(menuBoxId, index) {
        //要切換的元素
        var spItem = $(menuBoxId + " .spMenu:eq(" + index + ")");
        spItem.next().slideDown();
        spItem.parent().addClass("active")
    }
    //關閉某一個item
    function closeSpMenu(menuBoxId, index) {
        //要切換的元素
        var spItem = $(menuBoxId + " .spMenu:eq(" + index + ")");
        spItem.next().slideUp();
        spItem.parent().removeClass("active")
    }
    //切換某一個item
    function toggleSpMenu(menuBoxId, index) {
        //要切換的元素
        var spItem = $(menuBoxId + " .spMenu:eq(" + index + ")");
        spItem.next().slideToggle();
        spItem.parent().toggleClass("active")
    }

    window.menuBox = menuBox;
}($, JSON, checkutil);

 源碼下載地址:menuBox1.1.zip

相關文章
相關標籤/搜索