Строим дерево средствами HTML+JQuery+MySQL+PHP.

24.01.2020
treeview

Очередная задача, возникшая при разработке небольшой информационной системы, — сделать древовидное отображение структуры объектов с несколькими уровнями вложенности и возможностью навигации.

По сути это аналог дельфового treeview. Структура страницы не отличается от любого html файла.

Первое, что потребуется для реализации — это рассказать браузеру как оно (дерево) должно выглядеть.

Для этого в заголовок страницы необходимо поместить описание стилей CSS или же указать ссылку на файл описания стилей. В данном случае стиль помещен в раздел head.


<style type="text/css" media="all">
 /* общий стиль */<br />
   body {font-family: Arial, Tahoma, sans-serif; margin: 2em; font-size: 62.5%;}<br />
   p {<br />
      font-size: 1.2em;<br />
   }<br />
   a {<br />
      color: #0066cc;<br />
      text-decoration: none;<br />
   }<br />
a:hover {<br />
      text-decoration: underline;<br />
   }<br />
   a:active, a:focus {<br />
      color: #666;<br />
      background-color:  #f4f4f4;<br />
   }<br />
   a.current {<br />
      color: black;<br />
      font-weight: bold;<br />
      background-color:  #f4f4f4;<br />
   }<br />
/* Дерево многоуровневое<br />
   -------------------------------- */<br />
   #multi-derevo {<br />
      width: 220px; /* блок под дерево */<br />
      border: solid; /* границы блока */<br />
      border-color: silver gray gray silver;<br />
      border-width: 2px;<br />
      padding: 0 0 1em 0;  /* нижний отступ */<br />
      font-size: 1.3em;<br />
   }<br />
      span { /* обертка пункта */<br />
         text-decoration: none;<br />
         display: block; /* растянем до правого края блока */<br />
         margin: 0 0 0 1.2em;<br />
         background-color: transparent;<br />
         border: solid silver; /* цвет линий */<br />
         border-width: 0 0 1px 1px; /* границы: низ и лево */</p>
<p>      }<br />
        span a  {/* тест элемента дерева */<br />
            display: block;<br />
            position: relative;<br />
            top: .95em; /* смещаем узел на середину линии */<br />
            background-color: #fff; /* закраска в цвет фона обязательна иначе будет видно линию */<br />
            margin: 0 0 .2em .7em; /* делаем промежуток между узлами, отодвигаем левее   */<br />
            padding: 0 0.3em; /* небольшой отступ от линии */</p>
<p>         }<br />
   	h4 {/* заголовок дерева */<br />
         font-size: 1em;<br />
         font-weight: bold;<br />
         margin: 0;<br />
         padding: 0 .25em;<br />
         border-bottom: 1px solid silver;<br />
   	}<br />
      h4 a {<br />
         display: block;</p>
<p>      }<br />
      ul, li {<br />
         list-style-image:none;<br />
         list-style-position:outside;<br />
         list-style-type:none;<br />
         margin:0;<br />
         padding:0;</p>
<p>      }<br />
         ul li {<br />
            line-height: 1.2em;</p>
<p>         }<br />
            ul li ul {<br />
               display: none; /* узлы свернуты  */</p>
<p>            }<br />
            	ul li ul li {<br />
                  margin: 0 0 0 1.2em;<br />
                  border-left: 1px solid silver; /* цвет вертикальной линии между узлами */</p>
<p>            	}<br />
               li.last {/* последний узел, соединительную линию к след. узлу убираем */<br />
                  border: none;<br />
               }<br />
     .marker { /* маркер раскрытия списка в закрытом состоянии */<br />
	     background-color: #fff;<br />
         border-color:  transparent transparent  transparent #666;<br />
         border-style: solid;<br />
         border-width: .25em 0 .25em .5em;<br />
		 display: block;<br />
		 heigth: 0;<br />
         margin: .35em .25em 0 0;<br />
         float: left;<br />
         width: 0;<br />
         height: 0;<br />
         line-height: 0;</p>
<p>      }<br />
      .marker.open {/* маркер раскрытия списка в открытом состоянии */<br />
         border-color: #999 transparent transparent transparent;<br />
		 border-width: .6em .25em 0 .25em;<br />
      }<br />
   /* IE 6 Fixup */<br />
   * html #multi-derevo * { height: 1%;}<br />
   * html .marker { border-style: dotted dotted dotted solid; }<br />
   * html .marker.open { border-style: solid dotted dotted dotted; }<br />
    /*]]>*/<br />
    </style>

В приведенном коде присутсвуют комментарии, для понимания особенностей некоторых параметров. Ну и конечно же, для точто чтобы дерево работало, поскольку оно использует jquery, укажем ссылки на необходимые для этого скрипты, так же разместив их в разделе head страницы.

<script src="js/jquery-1.4.2.min.js" type="text/javascript"></script>
<script src="js/jquery.cookie.js" type="text/javascript"></script>
<script src="js/jquery.derevo.js" type="text/javascript"></script>

Здесь Вы наверняка обратили внимание на указание использовать jquery.cookie.js и jquery.derevo.js
Если у Вас нет этих файлов, — можете скачать их в конце статьи.
Как уже сказано в названии статьи, — данные для стоительства дерева будут черпаться из БД (в данном случае mysql).
В моем случае отправной точкой отрисовки дерева является код предприятия для которого будут строиться подчиненные узлы. Этот код был заранее получен, — и не важно передадите ли вы его get-параметром или сессионной переменной. Здесь он в переменной $kodpred. По структуре своей дерево простое. Вот так оно выглядит в примитивном виде:

 	<li>
<span><a href="">1. Ветка</a></span>
<ul>
 	<li><span><a href="#">1.1. Ветка</a></span></li>
 	<li><span><a href="#11">1.2. Ветка</a></span></li>
</ul>
</li>

Обозначим размещение дерева и титульную надпись

<div id="multi-derevo">
<h4><a href="left.php">Выберите предприятие</a></h4>
<ul>

Прежде чем отрисовывать все элементы дерева с учетом их подчиненности сделаем запрос к БД, чтобы узнать доступные для отображения объекты, ведь (в даннос случае) они имеют различные подчиненные структуры.
Код PHP:

if($kodpred == "main") {
$query1="select * from r_pred";
}else{
$query1="select * from r_pred where user_pref='$kodpred'";
}
$keystr = 0;
$result1=mysql_query($query1);
while($mass1=mysql_fetch_array($result1)){
$pred=$mass1[pred];
$key_pred=$mass1[pk_pred];

Продолжением данного PHP-кода будет отрисовка объектов дерева по результатам запроса.
Мне заранее известна структура, в данном случае, предприятия и точно известна возможная структура.
Поскольку она однотипна и имеет вид предприятие-цех-склад, поэтому при формировании веток я задаю каждой ветке дерева дополнительный параметр (p-pp-pz соответственно).
Эти параметры дополняют формируемую ссылку в ветви.

$result1=mysql_query($query1);
while($mass1=mysql_fetch_array($result1)){
$pred=$mass1[pred];
$key_pred=$mass1[pk_pred];
echo "
 	<li><span><a href='main.php?p=".$key_pred."' TARGET='mainFrame'>".iconv('utf-8','cp1251' ,$pred)."</a></span>";
echo "
<ul>";
$keystr= $keystr+1;
$query2="select * from r_pd where key_pch='$key_pred'";
$result2=mysql_query($query2);
while($mass2=mysql_fetch_array($result2)){
$pd=$mass2[pd];
$key_pd=$mass2[pk_pd];
echo "
 	<li><span><a href='main.php?p=".$key_pred."&pp=".$key_pd."' TARGET='mainFrame'>".iconv('utf-8','cp1251' ,$pd)."</a></span></li>
";

Приведенным куском кода будет получено 2 объекта дерева для каждого из предприятий: предприятия и цеха. Видно что у предприятия в ссылке формируется параметр «р» , а у цеха параметр «рр». Теперь добавим к каждому цеху склад. Продолжение кода:

echo "
<ul>";
echo "
 	<li><span><a href='main.php?p=".$key_pred."&pp=".$key_pd."&pz=true' 

TARGET='mainFrame'>ПКЗ</a></span></li>
";
echo "</ul>
";
echo "</ul>
";
}

Здесь ПКЗ и есть склад с параметром «pz».

Результатом работы такого php-скрипта будет дерево показанное на рисунке. Конечно в показанном дереве больше подчиненных объектов, но построение дочерних узлов ни чем не от личается от приведенного примера. Если будут вопросы — спрашивате в комментариях.

PS: Не забудьте поделиться статьей кнопкой соцсети справа от записи.

Оставить комментарий