Build dynamic menu with PHP

Asked

Viewed 74 times

-3

I’m trying to dynamically assemble a menu with submenus with data coming from a database table, but I couldn’t get a result that worked.

I have this code to create the menu and submenu on another site, but the way to create the menu of the other site was different (only ul and li more simply) and could not adapt to reach the result I hope (end of the question).

<?php
$items = array ( 1 => array ( 'parent' => '0', 'tit_pag' => 'Inicial', 'url_pag' => '/', 'target_url' => '_self', 'id' => '1', ), 2 => array ( 'parent' => '0', 'tit_pag' => 'Principal 1', 'url_pag' => '/', 'target_url' => '_self', 'id' => '2', 'child' => array ( 3 => array ( 'parent' => '2', 'tit_pag' => 'Item 1', 'url_pag' => 'link1.html', 'target_url' => '_self', 'id' => '3', ), 4 => array ( 'parent' => '2', 'tit_pag' => 'Item 2', 'url_pag' => 'link2.html', 'target_url' => '_self', 'id' => '4', ), 5 => array ( 'parent' => '2', 'tit_pag' => 'Item 3', 'url_pag' => 'link3.html', 'target_url' => '_self', 'id' => '5', ), ), ), 6 => array ( 'parent' => '0', 'tit_pag' => 'Principal 2', 'url_pag' => '#', 'target_url' => '_self', 'id' => '6', 'child' => array ( 7 => array ( 'parent' => '6', 'tit_pag' => 'Item 4', 'url_pag' => 'link4.html', 'target_url' => '_self', 'id' => '7', ), 8 => array ( 'parent' => '6', 'tit_pag' => 'Item 5', 'url_pag' => 'link5.html', 'target_url' => '_self', 'id' => '8', ), 9 => array ( 'parent' => '6', 'tit_pag' => 'Item 6', 'url_pag' => 'link6.html', 'target_url' => '_self', 'id' => '9', ), ), ), 10 => array ( 'parent' => '0', 'tit_pag' => 'Principal 3', 'url_pag' => 'link7.html', 'target_url' => '_self', 'id' => '10', ), 11 => array ( 'parent' => '0', 'tit_pag' => 'Principal 4', 'url_pag' => 'link8.html', 'target_url' => '_self', 'id' => '11', ), );

function get_menu($items) {
    $html = "<ul>";
    foreach($items as $key=>$value) {
        $html.= '<li><a href="/'.$value['url_pag'].'" target="'.$value['target_url'].'">'.$value['tit_pag'].'</a>';
        if(array_key_exists('child',$value)) {
            $html .= get_menu($value['child'],'child');
        }
            $html .= "</li>";
    }
    $html .= "</ul>";
    return $html;
}
print get_menu($items);
?>

The above code generates the following result:

<ul>
    <li><a href="//" target="_self">Inicial</a></li>
    <li>
        <a href="//" target="_self">Principal 1</a>
        <ul>
            <li><a href="/link1.html" target="_self">Item 1</a></li>
            <li><a href="/link2.html" target="_self">Item 2</a></li>
            <li><a href="/link3.html" target="_self">Item 3</a></li>
        </ul>
    </li>
    <li>
        <a href="/#" target="_self">Principal 2</a>
        <ul>
            <li><a href="/link4.html" target="_self">Item 4</a></li>
            <li><a href="/link5.html" target="_self">Item 5</a></li>
            <li><a href="/link6.html" target="_self">Item 6</a></li>
        </ul>
    </li>
    <li><a href="/link7.html" target="_self">Principal 3</a></li>
    <li><a href="/link8.html" target="_self">Principal 4</a></li>
</ul>

But the result I needed was this:

<ul class="nav navbar-nav">
    <li><a href="//" target="_self">Inicial</a></li>
    <li class="dropdown submenu">
        <a href="//" target="_self" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-haspopup="true" aria-expanded="false">Principal 1 <i class="fa fa-angle-down" aria-hidden="true"></i></a>
        <ul class="dropdown-menu">
            <li><a href="link1.html" target="_self">Item 1</a></li>
            <li><a href="link2.html" target="_self">Item 2</a></li>
            <li><a href="link3.html" target="_self">Item 3</a></li>
        </ul>
    </li>
    <li class="dropdown submenu">
        <a href="/#" target="_self" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-haspopup="true" aria-expanded="false">Principal 2 <i class="fa fa-angle-down" aria-hidden="true"></i></a>
        <ul class="dropdown-menu">
            <li><a href="/link4.html" target="_self">Item 4</a></li>
            <li><a href="/link5.html" target="_self">Item 5</a></li>
            <li><a href="/link6.html" target="_self">Item 6</a></li>
        </ul>
    </li>
    <li><a href="/link7.html" target="_self">Principal 3</a></li>
    <li><a href="/link8.html" target="_self">Principal 4</a></li>
</ul>
  • Important you [Dit] your question and explain objectively and punctually the difficulty found, accompanied by a [mcve] of the problem and attempt to solve. To better enjoy the site, understand and avoid closures and negativations worth understanding What is the Stack Overflow and read the Stack Overflow Survival Guide (summarized) in Portuguese.

  • 1

    Your menu is basically <ul> and <li>, I didn’t understand what the difficulty was. What was the HTML generated by this code for the data you presented? What is the difference with the desired HTML?

  • I edited the question, see that the result that PHP generates is different from the result I needed, but I could not edit the code so I could leave it equal.

  • @Woss but the question depends on the result of the database that at each insertion can change the result of the items. As I said this result is php yes, because I use it on another site and it is working and generates this result. The variable items will receive the data from the database

  • @Woss a doubt, is appearing to you the image of the print of the database? Why the data items are in the picture

  • 1

    Give a var_dump($items) before calling the function and include the result of that in the question.

  • I put the value of $itemsin the personal code and I took the reference to the bank, forgive my ignorance

  • I edited the question, leaving only the part that matters. Result that generates PHP and expected result!

  • 1

    Note that in your data no item has the Child key, so it never enters the if inside the function.

  • @bfavaretto the code returns the correct result, the problem is on how to add the other information I need to make it equal to the second code posted.

Show 5 more comments

1 answer

0

I managed to arrive at the result that I hoped creating a new function to generate the submenus, this way it was like this:

<?php
    $items = array ( 1 => array ( 'parent' => '0', 'tit_pag' => 'Inicial', 'url_pag' => '/', 'target_url' => '_self', 'id' => '1', ), 2 => array ( 'parent' => '0', 'tit_pag' => 'Principal 1', 'url_pag' => '/', 'target_url' => '_self', 'id' => '2', 'child' => array ( 3 => array ( 'parent' => '2', 'tit_pag' => 'Item 1', 'url_pag' => 'link1.html', 'target_url' => '_self', 'id' => '3', ), 4 => array ( 'parent' => '2', 'tit_pag' => 'Item 2', 'url_pag' => 'link2.html', 'target_url' => '_self', 'id' => '4', ), 5 => array ( 'parent' => '2', 'tit_pag' => 'Item 3', 'url_pag' => 'link3.html', 'target_url' => '_self', 'id' => '5', ), ), ), 6 => array ( 'parent' => '0', 'tit_pag' => 'Principal 2', 'url_pag' => '#', 'target_url' => '_self', 'id' => '6', 'child' => array ( 7 => array ( 'parent' => '6', 'tit_pag' => 'Item 4', 'url_pag' => 'link4.html', 'target_url' => '_self', 'id' => '7', ), 8 => array ( 'parent' => '6', 'tit_pag' => 'Item 5', 'url_pag' => 'link5.html', 'target_url' => '_self', 'id' => '8', ), 9 => array ( 'parent' => '6', 'tit_pag' => 'Item 6', 'url_pag' => 'link6.html', 'target_url' => '_self', 'id' => '9', ), ), ), 10 => array ( 'parent' => '0', 'tit_pag' => 'Principal 3', 'url_pag' => 'link7.html', 'target_url' => '_self', 'id' => '10', ), 11 => array ( 'parent' => '0', 'tit_pag' => 'Principal 4', 'url_pag' => 'link8.html', 'target_url' => '_self', 'id' => '11', ), );
    
    function get_submenu($items) {
        $html2 = '<ul class="dropdown-menu">';
        foreach($items as $key=>$value) {
            $html2.= '<li><a href="/'.$value['url_pag'].'" target="'.$value['target_url'].'">'.$value['tit_pag'].'</a>';
            if(array_key_exists('child',$value)) {
                $html2 .= get_submenu($value['child'],'child');
            }
                $html2 .= "</li>";
        }
        $html2 .= '</ul>';
        return $html2;
    }               
    
    function get_menu($items) {
        $html = '<ul class="nav navbar-nav">';
        foreach($items as $key=>$value) {
            if(array_key_exists('child',$value)) {
            $html.= '<li class="dropdown submenu"><a href="/'.$value['url_pag'].'" target="'.$value['target_url'].'" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-haspopup="true" aria-expanded="false">'.$value['tit_pag'].' <i class="fa fa-angle-down" aria-hidden="true"></i></a>';
            }else{
            $html.= '<li><a href="/'.$value['url_pag'].'" target="'.$value['target_url'].'">'.$value['tit_pag'].'</a>';}
            if(array_key_exists('child',$value)) {
                $html .= get_submenu($value['child'],'child');
            }
                $html .= "</li>";
        }
        $html .= '</ul>';
        return $html;
    }
    print get_menu($items);
?>

RESULT

<ul class="nav navbar-nav">
    <li><a href="//" target="_self">Inicial</a></li>
    <li class="dropdown submenu">
        <a href="//" target="_self" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-haspopup="true" aria-expanded="false">Principal 1 <i class="fa fa-angle-down" aria-hidden="true"></i></a>
        <ul class="dropdown-menu">
            <li><a href="/link1.html" target="_self">Item 1</a></li>
            <li><a href="/link2.html" target="_self">Item 2</a></li>
            <li><a href="/link3.html" target="_self">Item 3</a></li>
        </ul>
    </li>
    <li class="dropdown submenu">
        <a href="/#" target="_self" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-haspopup="true" aria-expanded="false">Principal 2 <i class="fa fa-angle-down" aria-hidden="true"></i></a>
        <ul class="dropdown-menu">
            <li><a href="/link4.html" target="_self">Item 4</a></li>
            <li><a href="/link5.html" target="_self">Item 5</a></li>
            <li><a href="/link6.html" target="_self">Item 6</a></li>
        </ul>
    </li>
    <li><a href="/link7.html" target="_self">Principal 3</a></li>
    <li><a href="/link8.html" target="_self">Principal 4</a></li>
</ul>

Browser other questions tagged

You are not signed in. Login or sign up in order to post.