PHP / MySQL导航菜单

时间:2011-04-11 23:26:27

标签: php mysql

我正在尝试为分层导航菜单栏创建一个函数。

我希望能够拥有这样的东西......

<ul id="navigation">
<li><a href="#">Menu Item 1</a></li>
<li><a href="#">Menu Item 2</a></li>
    <ul>
        <li><a href="#">Sub Menu Item 1</a></li>
        <li><a href="#">Sub Menu Item 1</a></li>
    </ul>
<li><a href="#">Menu Item 3</a></li>
<li><a href="#">Menu Item 4</a></li>
</ul>

我正在使用这个功能,但它不像我想的那样正常工作。它显示主要的父链接,但不显示子链接。

function build_navbar($pid,$sub=0)
{
    global $db;

    $query = $db->simple_select("navbar", "*", "pid='".$pid."'", array("order_by" => "disporder"));
    $menu_build = "<ul id=\"navigation\">\n";
    while($menu = $db->fetch_array($query))
    {   
        if($sub == 1)
        {
           $menu_build .= "<ul>\n";
           $menu_build .= "<li><a href=\"#\">".$menu['title']."</a></li>\n";
           $menu_build .= "</ul>\n";
        }
        else
        {
           $menu_build .= "<li><a href=\"#\">".$menu['title']."</a></li>\n";
        }
        build_navbar($menu['id'],1);
    }
    $menu_build .= "</ul>\n";

    return $menu_build;
}

也许有人可以帮我解决这个问题?感谢。

---新更新---

Andy Groff,这就是你的代码输出的内容:

<ul id="navigation">
    <li><a href="#">Home</a></li>
    <ul>
        <li><a href="#">Child Link</a></li>
        <li><a href="#">Child 2</a></li>
    </ul>
    <li><a href="#">Parent</a></li>
</ul>

但是,我需要对其进行修改,以便输出如下:

<ul id="navigation">
    <li><a href="#">Home</a>
        <ul>
            <li><a href="#">Child Link</a></li>
            <li><a href="#">Child 2</a></li>
        </ul>
    </li>
    <li><a href="#">Parent</a></li>
</ul>

这就是它现在输出的内容,Andy:

<ul id="navigation">
    </li>
    <li><a href="#">Home</a>
    </li>
    <ul>
        <li>
        <a href="#">Child Link</a>
        </li>
        <li><a href="#">Child 2</a>
    </ul>
    </li>
    <li><a href="#">Parent</a>
</ul>

2 个答案:

答案 0 :(得分:1)

我认为你的问题可能与你的函数是递归的这个事实有关,但你正在构建的字符串每次都会在函数的顶部重置,而不是再次传递给函数。此外,我没有看到sub将在最后一次迭代中被设置为零。此外,您似乎不需要查询每一行。查询一次并构建整个菜单会更有效。我认为递归可以被抛弃。另外,我建议在数据中存储“sub”标志,而不是使用一些难以理解的php逻辑来确定给定行是否是子菜单。我根据这些概念进行了修改,不知道它是否有效,但因为我没有/想要创建数据来测试它:

function build_navbar()
{
    global $db;
    //first things first, i'd recommend putting a "sub" flag in your database. This example will use it.

    //start off by getting all of the rows. No need for recursion.
    $query = $db->simple_select("navbar", "*", "1", array("order_by" => "disporder"));
    $menu_build = "<ul id=\"navigation\">\n";

    //keep track of what level we're at
    $level = 1;

    while($menu = $db->fetch_array($query))
    {
      //get sub from data
      $sub = $menu['sub']

      //we need to go back to root level
      if($sub == 0 && $level == 2){
        $level--;
        $menu_build .= "</ul></li>\n";
      }
      else $menu_build .= "</li>\n";

      //we need to go up one level
      if($sub == 1 && $level == 1)
      {
        $level++;
        $menu_build .= "<ul><li>\n";
      }
      else $menu_build .= "<li>";
      //always print out a link
      $menu_build .= "<a href=\"#\">".$menu['title']."</a>\n";
    }
    $menu_build .= "</ul>\n";

    return $menu_build;
}

答案 1 :(得分:0)

更新:

试试这个:

function build_navbar($pid, $sub=0)
{
    global $db;

    $class = $sub ? "sub" : "navigation";

    $menu_build = "<ul class=\"$class\">\n";

    $query = $db->simple_select("navbar", "*", "pid='".$pid."'");
    while($menu = $db->fetch_array($query))
    {
        $menu_build .= "<li><a href=\"#\">".$menu['title']."</a>\n";

        // build child links
        $menu_build .= build_navbar($menu['id'],1);
    }

    $menu_build .= "</ul>";

    return $menu_build;
}

我们在这里做的是允许每个函数构建一个<ul><li>组,$sub变量将确定<ul>的ID将是什么,允许您对每个不同的。


编辑:

我找到了它!

这一行

build_navbar($menu['id'],1);

需要更改为:

$menu_build = build_navbar($menu['id'],1);

它看起来应该对我有用。

我要做的是添加一些显示每次执行的SQL查询的echo语句,然后您可以将其复制到phpmyadmin(或者您使用的db浏览器)。看看它是否也返回null结果。如果是这样,您的数据也可能出现问题。

所以例如:

echo "SELECT FROM navbar * WHERE pid='$pid' ORDER_BY disporder;<br>";