从邻接列表生成megamenu

时间:2013-12-09 14:49:48

标签: php mysql recursion menu megamenu

我在下面有一个数组:

Array
(
    [0] => Array
        (
            [id] => 1
            [name] => Electronics
            [parent] => 0
            [description] => Large amount of electronics in our store
            [columns] => 6
            [products] => 5
            [subcat] => Array
                (
                    [0] => Array
                        (
                            [id] => 7
                            [name] => Moble phones
                            [parent] => 1
                            [description] => 
                            [columns] => 0
                            [products] => 5
                            [subcat] => Array
                                (
                                )

                        )

                    [1] => Array
                        (
                            [id] => 16
                            [name] => Computers
                            [parent] => 1
                            [description] => 
                            [columns] => 0
                            [products] => 0
                            [subcat] => Array
                                (
                                    [0] => Array
                                        (
                                            [id] => 37
                                            [name] => Desktops
                                            [parent] => 16
                                            [description] => 
                                            [columns] => 0
                                            [products] => 0
                                            [subcat] => Array
                                                (
                                                )

                                        )

                                    [1] => Array
                                        (
                                            [id] => 17
                                            [name] => Car Electronics
                                            [parent] => 16
                                            [description] => 
                                            [columns] => 0
                                            [products] => 0
                                            [subcat] => Array
                                                (
                                                    [0] => Array
                                                        (
                                                            [id] => 43
                                                            [name] => GPS & Navigation
                                                            [parent] => 17
                                                            [description] => 
                                                            [columns] => 0
                                                            [products] => 0
                                                            [subcat] => Array
                                                                (
                                                                )

                                                        )

                                                )

                                        )

                                )

                        )

                    [2] => Array
                        (
                            [id] => 18
                            [name] => TV & Video
                            [parent] => 1
                            [description] => 
                            [columns] => 0
                            [products] => 2
                            [subcat] => Array
                                (
                                    [0] => Array
                                        (
                                            [id] => 48
                                            [name] => LED TVs
                                            [parent] => 18
                                            [description] => 
                                            [columns] => 0
                                            [products] => 2
                                            [subcat] => Array
                                                (
                                                )

                                        )

                                    [1] => Array
                                        (
                                            [id] => 49
                                            [name] => Plasma TVs
                                            [parent] => 18
                                            [description] => 
                                            [columns] => 0
                                            [products] => 0
                                            [subcat] => Array
                                                (
                                                )

                                        )

                                )

                        )

                )

        )

    [1] => Array
        (
            [id] => 14
            [name] => Video Games
            [parent] => 0
            [description] => 
            [columns] => 0
            [products] => 0
            [subcat] => Array
                (
                    [0] => Array
                        (
                            [id] => 30
                            [name] => Nintendo Wii
                            [parent] => 14
                            [description] => 
                            [columns] => 0
                            [products] => 0
                            [subcat] => Array
                                (
                                )

                        )

                )

        )

)

我有一个php递归函数将此数组转换为html菜单:

private function buildNavHTML($nav, $tabs = "") {

        $html = !strlen($tabs) ? 
                $tabs.'<ul class="navs">' : 
                $tabs.'<ul>';

        foreach($nav as $page) {

            $html .= $tabs."    ".'<li>';

            (isset($page['subcategories'][0])) ? 
        $html .= '<a class="subcat" href="cat?cid='.$page['id'].'">'.$page['name'].'</a>' : 
        $html .= '<a href="cat?cid='.$page['id'].'">'.$page['name'].'</a>';

            if(isset($page['subcat'][0])) {
                $html .= self::buildNavHTML($page['subcat'], $tabs."        ");
            }
            $html .= '</li>';
        }
        $html .= $tabs.'</ul>';

        return $html;
    }

此函数将输出HTML树:

 <ul class="navs">
       <li class="">
          <a class="shop_subcat" href="cat?cid=1">Electronics</a>
             <ul>
                <li>
                   <a href="cat?cid=7">Moble phones</a>
                </li>            
                <li>
                   <a class="shop_subcat" href="cat?cid=16">Computers</a>
                     <ul>
                       <li>
                          <a href="cat?cid=37">Desktops</a>
                       </li>
                       <li>
                          <a class="shop_subcat" href="cat?cid=17">Car Electronics</a>                      
                             <ul>
                                <li>
                                   <a href="cat?cid=43">GPS &amp; Navigation</a>
                                </li>
                             </ul>
                        </li>
                     </ul>
                   </li>
                   <li>
                      <a class="shop_subcat" href="cat?cid=18">TV &amp; Video</a>              
                        <ul>
                           <li>
                              <a href="cat?cid=48">LED TVs</a>
                           </li>
                           <li>
                              <a href="cat?cid=49">Plasma TVs</a>
                           </li>
                         </ul>
                    </li>
                 </ul> 
             </li>
             <li class="">
                <a class="shop_subcat" href="cat?cid=14">Video Games</a>
                   <ul>
                      <li>
                         <a href="cat?cid=30">Nintendo Wii</a>
                      </li>
                   </ul>
              </li>
            </ul>

但我需要得到类似的东西:_http://vasterad.com/plugins/responsive_css3_mega_menu/#

由于我在数据库中有一个列字段,因此按列分隔。如何修复递归函数? 谢谢!

3 个答案:

答案 0 :(得分:2)

1.首先,您应该在页面中添加此css:

<style>
   @import url("icons.css"); .menu{display:block;position:relative}.menu,.menu ul{margin:0;padding:0;list-style:none;position:relative}.menu ul a{float:left}.menu ul ul a{float:none}.menu .mega-menu a{float:none;padding:0}.menu ul ul,.menu .mega-menu,.menu .mega-menu ol li{opacity:0;visibility:hidden;display:none ! important/9;-webkit-transition:opacity 150ms ease-in-out;-moz-transition:opacity 150ms ease-in-out;-o-transition:opacity 150ms ease-in-out;-ms-transition:opacity 150ms ease-in-out;transition:opacity 150ms ease-in-out}.menu li:hover>ul,.menu li:hover>.mega-menu,.menu li:hover>.mega-menu ol li{opacity:1;visibility:visible;display:block ! important/9}.menu ul:after{content:"";clear:both;display:block}.menu ul li{float:left;-webkit-transition:all 150ms ease-in-out;-moz-transition:all 150ms ease-in-out;-o-transition:all 150ms ease-in-out;-ms-transition:all 150ms ease-in-out;transition:all 150ms ease-in-out}.menu ul li a{display:block;padding:14px 20px 15px 20px;color:#fff;font-weight:700;text-decoration:none}.menu .arrow:after{content:"";float:right;text-align:right;width:0;height:0;display:block;border-left:3px solid rgba(0,0,0,0);border-right:3px solid rgba(0,0,0,0);border-top:3px solid #fff;top:9px;margin:0 0 0 5px;position:relative;border-left:3px solid transparent/9;border-right:3px solid transparent/9}.menu ul li ul li .arrow:after{border-top:3px solid transparent;border-bottom:3px solid transparent;border-left:3px solid #bbb;margin:-2px 0 0 5px}.menu i{font-size:14px;font-weight:400;font-style:normal;float:left;margin:4px 4px 0 -2px;line-height:14px;padding:0}.menu .right{float:right}.menu .right ul,.menu .right .mega-menu{right:0}.menu ul ul{background:#fff;border:1px solid #e0e0e0;border-top:0;border-bottom:0;position:absolute;top:100%;width:170px;-webkit-box-shadow:0 1px 1px rgba(0,0,0,.04);box-shadow:0 1px 1px rgba(0,0,0,.04)}.menu ul ul ul{position:absolute;left:100%;border-top:1px solid #e0e0e0;top:-1px}.menu ul ul li a{font-weight:400;padding:8px 12px;color:#777;border-bottom:1px solid #e4e4e4}.menu ul ul li{float:none;position:relative;-webkit-transition:none;-moz-transition:none;-o-transition:none;-ms-transition:none;transition:none}.menu ul ul li a:active,.menu ul ul li:hover{background:#f5f5f5!important}.menu ul ul li{background:#fff!important}.mega-menu{position:absolute;top:100%;padding:18px 11px;background-color:#fff;border:1px solid #e0e0e0;border-top:none;color:#777;-webkit-box-shadow:0 1px 1px rgba(0,0,0,.04);box-shadow:0 1px 1px rgba(0,0,0,.04);-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}.mega-menu ol{list-style:none;padding:0}.mega-menu ol li{width:100%}.mega-menu ol li:hover,.mega-menu ol li a{color:#777;font-size:12px;padding:0;font-weight:400;background-color:#fff;background-image:none}.mega-menu ol li a:hover{color:#505050}.mega-menu div h4{font-size:14px;font-weight:700;color:#404040;border-bottom:1px solid #e4e4e4;padding:0 0 8px 0;margin:0 0 10px 0}.mega-menu .col-1{width:135px}.mega-menu .col-2{width:288px}.mega-menu .col-3{width:441px}.mega-menu .col-4{width:594px}.mega-menu .col-5{width:747px}.mega-menu .col-6{width:900px}.mega-menu .col-1,.mega-menu .col-2,.mega-menu .col-3,.mega-menu .col-4,.mega-menu .col-5,.mega-menu .col-6{float:left;margin:0 9px}.mega-menu.full-width{left:0;width:100%;padding:18px 0}.full-width .col-1{width:14.1%}.full-width .col-2{width:30.4%}.full-width .col-3{width:46.7%}.full-width .col-4{width:63%}.full-width .col-5{width:79.3%}.full-width .col-6{width:95.6%}.full-width .col-1,.full-width .col-2,.full-width .col-3,.full-width .col-4,.full-width .col-5,.full-width .col-6{float:left;margin:0 0 0 2.2%}@media only screen and (max-width: 767px){.menu ul li{width:100%;cursor:pointer}.menu ul li{position:relative}.menu .mega-menu ol li{height:0}.menu li:hover>.mega-menu ol li{height:auto}.mega-menu,.menu ul ul{z-index:100}.menu ul ul{width:100%;-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}.menu ul ul ul{left:0}.menu ul ul li:hover>ul{position:relative;border:none;border-top:1px solid #e4e4e4;-webkit-box-shadow:none;box-shadow:none}.menu ul li ul li .arrow:after{border-left:3px solid transparent;border-right:3px solid transparent;border-top:3px solid #bbb;margin:0}.mega-menu{padding:18px 0}.mega-menu ol li:last-child{margin:0 0 20px 0}.menu .col-1,.full-width .col-1,.menu .col-2,.full-width .col-2,.menu .col-3,.full-width .col-3,.menu .col-4,.full-width .col-4,.menu .col-5,.full-width .col-5,.menu .col-6,.full-width .col-6{float:left;margin:0 0 0 5%;width:90%}} .style-1.menu, .style-1.menu ul li { background-color: #2b2a28; background-image: linear-gradient(bottom, rgba(0,0,0, 0) 50%, rgba(255,255,255, 0.04) 0%); background-image: -o-linear-gradient(bottom, rgba(0,0,0, 0) 50%, rgba(255,255,255, 0.04) 0%); background-image: -moz-linear-gradient(bottom, rgba(0,0,0, 0) 50%, rgba(255,255,255, 0.04) 0%); background-image: -webkit-linear-gradient(bottom, rgba(0,0,0, 0) 50%, rgba(255,255,255, 0.04) 0%); background-image: -ms-linear-gradient(bottom, rgba(0,0,0, 0) 50%, rgba(255,255,255, 0.04) 0%); } .style-1.menu ul li:hover { background-color: #eb4e01; background-image: linear-gradient(bottom, rgba(0,0,0, 0) 50%, rgba(255,255,255, 0.08) 0%); background-image: -o-linear-gradient(bottom, rgba(0,0,0, 0) 50%, rgba(255,255,255, 0.08) 0%); background-image: -moz-linear-gradient(bottom, rgba(0,0,0, 0) 50%, rgba(255,255,255, 0.08) 0%); background-image: -webkit-linear-gradient(bottom, rgba(0,0,0, 0) 50%, rgba(255,255,255, 0.08) 0%); background-image: -ms-linear-gradient(bottom, rgba(0,0,0, 0) 50%, rgba(255,255,255, 0.08) 0%); }
  </style>

你应该把你的功能放到这个位置:

 <div class="container">
    <div class="menu style-1">
     <ul class="menu">
           <!--head of your tabs-->
                <li>
                   <a class="arrow" href="#">
                       <i class="icon-folder-open"></i>
                                       Electronics
                      </a>
                              <!--subtabs of your head tabs-->
                                  <ul>
                                      <li>
                                          <a href="#">Moble phones</a>
                                      </li>
                                  </ul>
                  </li>
          </ul>

注意:您应该了解有关css http://www.w3schools.com/css/的更多信息 最好的问候

答案 1 :(得分:0)

您的标记确实很好,您应该使用HTMLCSS设置菜单样式。

我创造了一个帮助你的小提琴。这是您的菜单,周围有<nav>标记,可以让样式更容易。

小提琴here

希望这会让你前进!

答案 2 :(得分:-1)

要么我误解了这个问题,要么你只是在寻找生成的HTML代码的标记。快速浏览后看起来你的递归函数很好......它看起来很奇怪。 布局和外观实际上不是PHP处理的东西。为此,您希望使用css和常规HTML

关于递归函数中实际代码的一句话......内联HTML实际上并不是真正的方法。如果您使用正确的视图,我相信您将能够更好地识别您的“问题”。