Bitrix: компонент с древовидным списком разделов и элементами инфоблока

от автора

в
Время чтения: 3 мин.

Создание компонента с древовидным списком разделов и элементами инфоблока в 1С-Битрикс требует нескольких шагов. Мы создадим кастомный компонент, который будет выводить разделы инфоблока в виде дерева, а также элементы, принадлежащие этим разделам.


1. Структура компонента

Компонент будет состоять из:

  1. Класса компонента — для обработки логики.
  2. Шаблона — для отображения данных.
  3. Описания параметров — для настройки компонента.

2. Создание структуры папок

Создайте папку для компонента в директории /local/components/. Например:

/local/components/custom/section.tree/

Внутри создайте следующие файлы:

  • .description.php — описание компонента.
  • class.php — основной код компонента.
  • template/.default/template.php — шаблон для отображения.

3. Описание компонента (.description.php)

Этот файл описывает параметры компонента.

<?php
if (!defined('B_PROLOG_INCLUDED') || B_PROLOG_INCLUDED !== true) die();

$arComponentDescription = [
    'NAME' => 'Древовидный список разделов с элементами',
    'DESCRIPTION' => 'Выводит разделы инфоблока в виде дерева с элементами',
    'PATH' => [
        'ID' => 'custom',
        'NAME' => 'Кастомные компоненты',
    ],
];

4. Основной код компонента (class.php)

Этот файл содержит логику компонента.

<?php
if (!defined('B_PROLOG_INCLUDED') || B_PROLOG_INCLUDED !== true) die();

class SectionTreeComponent extends CBitrixComponent
{
    // Инициализация компонента
    public function executeComponent()
    {
        $this->arResult = $this->getSectionTree();
        $this->includeComponentTemplate();
    }

    // Получение дерева разделов с элементами
    protected function getSectionTree()
    {
        CModule::IncludeModule('iblock');

        $iblockId = $this->arParams['IBLOCK_ID']; // ID инфоблока
        $sections = [];
        $elements = [];

        // Получаем разделы
        $rsSections = CIBlockSection::GetList(
            ['LEFT_MARGIN' => 'ASC'],
            ['IBLOCK_ID' => $iblockId, 'ACTIVE' => 'Y'],
            false,
            ['ID', 'NAME', 'DEPTH_LEVEL', 'IBLOCK_SECTION_ID']
        );

        while ($section = $rsSections->Fetch()) {
            $sections[$section['ID']] = $section;
        }

        // Получаем элементы
        $rsElements = CIBlockElement::GetList(
            [],
            ['IBLOCK_ID' => $iblockId, 'ACTIVE' => 'Y'],
            false,
            false,
            ['ID', 'NAME', 'IBLOCK_SECTION_ID']
        );

        while ($element = $rsElements->Fetch()) {
            $elements[$element['IBLOCK_SECTION_ID']][] = $element;
        }

        // Формируем дерево
        $tree = $this->buildTree($sections, $elements);

        return $tree;
    }

    // Построение дерева разделов с элементами
    protected function buildTree($sections, $elements)
    {
        $tree = [];

        foreach ($sections as $id => $section) {
            if ($section['IBLOCK_SECTION_ID']) {
                $sections[$section['IBLOCK_SECTION_ID']]['CHILDREN'][$id] = &$sections[$id];
            } else {
                $tree[$id] = &$sections[$id];
            }

            // Добавляем элементы в раздел
            if (isset($elements[$id])) {
                $sections[$id]['ELEMENTS'] = $elements[$id];
            }
        }

        return $tree;
    }
}

5. Шаблон компонента (template/.default/template.php)

Этот файл отвечает за отображение данных.

<?php
if (!defined('B_PROLOG_INCLUDED') || B_PROLOG_INCLUDED !== true) die();

/**
 * @var array $arResult
 */
?>

<div class="section-tree">
    <?php renderTree($arResult); ?>
</div>

<?php
// Рекурсивная функция для отображения дерева
function renderTree($tree)
{
    echo '<ul>';
    foreach ($tree as $section) {
        echo '<li>';
        echo htmlspecialcharsbx($section['NAME']);

        // Выводим элементы раздела
        if (!empty($section['ELEMENTS'])) {
            echo '<ul>';
            foreach ($section['ELEMENTS'] as $element) {
                echo '<li>' . htmlspecialcharsbx($element['NAME']) . '</li>';
            }
            echo '</ul>';
        }

        // Рекурсивно выводим дочерние разделы
        if (!empty($section['CHILDREN'])) {
            renderTree($section['CHILDREN']);
        }

        echo '</li>';
    }
    echo '</ul>';
}
?>

6. Подключение компонента на странице

Чтобы подключить компонент на странице, используйте вызов:

<?php
$APPLICATION->IncludeComponent(
    'custom:section.tree',
    '',
    [
        'IBLOCK_ID' => 5, // ID инфоблока
    ]
);
?>

7. Дополнительные улучшения

  • Кеширование: Добавьте кеширование для повышения производительности.
  • AJAX-подгрузка: Реализуйте подгрузку элементов при раскрытии раздела.
  • Настройка параметров: Добавьте параметры для настройки глубины дерева, сортировки и фильтрации.

Итог

Теперь у вас есть кастомный компонент, который выводит древовидный список разделов с элементами инфоблока. Если нужно доработать или добавить функционал, дайте знать! 😊


Комментарии

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *

Сколько будет 1 + 6?