Я хочу создать навигационное меню начальной загрузки 4, у меня есть следующий запрос SQL, и у меня есть несколько кодов под ним, но я не могу понять, как это сделать!
Это таблицы
TABLE menu
--------------------------------------
| id | title | url |
| 1 | Home | index.php |
| 2 | Menu | # |
| 3 | Contact | # |
| 2 | Winkelwagen | winkelwagen.php |
--------------------------------------
TABLE categories
-------------------------------------
| id | title_cat | url | cparent_id |
| 1 | Auto's | # | 2 |
| 2 | Drank | # | 2 |
-------------------------------------
TABLE products
-------------------------------------
| id | product | url | pparent_id |
| 1 | Ferrari | # | 1 |
| 2 | Heineken | # | 2 |
-------------------------------------
Вот запрос:
$query = "SELECT
X.level,
X.id,
X.name,
X.url,
X.parent_id
FROM
(
SELECT
1 AS LEVEL,
id AS id,
title AS NAME,
url AS url,
0 AS parent_id,
id AS id_1,
-1 AS id_2,
-1 AS id_3
FROM
menu
WHERE
1
UNION
SELECT
2 AS LEVEL,
id AS id,
title_cat AS NAME,
url AS url,
cparent_id AS parent_id,
cparent_id AS id_1,
id AS id_2,
-1 AS id_3
FROM
categories
WHERE
1
UNION
SELECT
3 AS LEVEL,
products.id AS id,
products.product AS NAME,
products.url AS url,
products.pparent_id AS parent_id,
categories.cparent_id AS id_1,
categories.id AS id_2,
products.id AS id_3
FROM
products
LEFT JOIN categories ON products.pparent_id = categories.id
WHERE
1
) X
WHERE
1
ORDER BY
id_1,
id_2,
id_3";
Что дает следующую таблицу с уровнями (и я тоже добавил parent_id, но с parent_id buildTree($array)
входит в цикл):
level id name url parent_id
1 1 Home index.php 0
1 2 Menu # 0
2 1 Auto's # 2
3 1 Ferrari # 1
2 2 Drank # 2
3 2 Heineken # 2
1 3 Contact contact.php 0
1 4 Winkelwagen winkelwagen.php 0
Я хочу, чтобы навигационное меню выглядело так:
<li class="nav-item">
<a class="nav-link" href="index.php">Home</a>
</li>
<li class="nav-item dropdown">
<a class="nav-link dropdown-toggle" href="#" id="navbarDropdown" role="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">Menu</a>
<div class="dropdown-menu" aria-labelledby="navbarDropdown">
<div class="dropdown-submenu">
<a class="dropdown-item dropdown-toggle" href="#">Auto's</a>
<div class="dropdown-menu" aria-labelledby="navbarDropdown">
<a class="dropdown-item" href="#">Ferrari</a>
</div>
</div>
<div class="dropdown-submenu">
<a class="dropdown-item dropdown-toggle" href="#">Drank</a>
<div class="dropdown-menu" aria-labelledby="navbarDropdown">
<a class="dropdown-item" href="#">Heineken</a>
</div>
</div>
</div>
</li>
<li class="nav-item">
<a class="nav-link" href="#">Contact</a>
</li>
<li class="nav-item">
<a class="nav-link" href="winkelwagen.php">Winkelwagen</a>
</li>
У меня есть следующие коды, сначала мы создаем массив из запроса, который вы уже видели выше:
$sql = $pdo->prepare($query);
function menu_builder($sql) {
if ($sql->execute()) {
while ($row = $sql->fetch(PDO::FETCH_ASSOC)) {
$array[] = $row;
}
buildTree($array); // or menu_builder($sql);
}
}
Следующий код не работает, потому что он входит в бесконечный цикл (и если он работает, мне все еще нужно сделать html правильным:):
function buildTree($array, $parent_id = 0, $parents = array()) {
if($parent_id == 0) {
foreach ($array as $element) {
if (($element['parent_id'] != 0) && !in_array($element['parent_id'], $parents)) {
$parents[] = $element['parent_id'];
}
}
}
$menu_html = '';
foreach($array as $element) {
if($element['parent_id'] == $parent_id) {
if(in_array($element['id'], $parents)) {
$menu_html .= '<li class="dropdown">';
$menu_html .= '<a href="'.$element['url'].'" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-expanded="false">'.$element['name'].' <span class="caret"></span></a>';
}
else {
$menu_html .= '<li>';
$menu_html .= '<a href="' . $element['url'] . '">' . $element['name'] . '</a>';
}
if(in_array($element['id'], $parents)) {
$menu_html .= '<ul class="dropdown-menu" role="menu">';
$menu_html .= buildTree($array, $element['id'], $parents);
$menu_html .= '</ul>';
}
$menu_html .= '</li>';
}
}
return $menu_html;
}
И это делает нормальное <ul>
/ <li>
меню, которое я не знаю, как заставить его работать у меня с начальной загрузкой:
function menu_builder($sql) {
$level = 0;
if ($sql->execute()) {
while ($row = $sql->fetch(PDO::FETCH_ASSOC)) {
while($level < $row['level']) {
echo "<ul>" . PHP_EOL;
$level++;
}
while($level > $row['level']) {
echo "</ul>" . PHP_EOL;
$level--;
}
echo " <li>#" . $row['id'] . "->" . $row['name'] . "</li>" . PHP_EOL;
}
}
while($level-- > 0) {
echo "</ul>" . PHP_EOL;
}
}
Если вам нужна дополнительная информация, пожалуйста, спросите меня, я постарался прояснить вопрос с помощью кодов, которые я пробую, и таблицы, которую я использую.
JQuery:
$('.dropdown-menu a.dropdown-toggle').on('click', function(e) {
if (!$(this).next().hasClass('show')) {
$(this).parents('.dropdown-menu').first().find('.show').removeClass("show");
}
var $subMenu = $(this).next(".dropdown-menu");
$subMenu.toggleClass('show');
$(this).parents('li.nav-item.dropdown.show').on('hidden.bs.dropdown', function(e) {
$('.dropdown-submenu .show').removeClass("show");
});
return false;
});
CSS:
.dropdown-submenu {
position: relative;
}
.dropdown-submenu a::after {
transform: rotate(-90deg);
position: absolute;
right: 6px;
top: .8em;
}
.dropdown-submenu .dropdown-menu {
top: 0;
left: 100%;
margin-left: .1rem;
margin-right: .1rem;
}