Skip to content

Instantly share code, notes, and snippets.

@if0rest
Last active April 1, 2024 17:36
Show Gist options
  • Save if0rest/264ba1d6287d099c35f78b15e8ece066 to your computer and use it in GitHub Desktop.
Save if0rest/264ba1d6287d099c35f78b15e8ece066 to your computer and use it in GitHub Desktop.
Совместный вывод разделов и элементов в bitrix:news.list.

ВЫВОД РАЗДЕЛОВ И ЭЛЕМЕНТОВ В bitrix:news.list

Часто возникает необходимость вывести разделы инфоблока с элементами на одной странице. Для этой цели подойдет связка catalog.sections + news.list. Или можно обойтись одним bitrix:news.list, немного кастомизировав шаблон компонента. Пойдем вторым путем.

Итак.

  1. Размещаем компонент bitrix:news.list на целевой странице.
  2. Копируем шаблон компонента в текущий шаблон сайта.
  3. Создаем в нем файл result_modifier.php с таким содержимым.
// Получаем все активные разделы ИБ
$rsSections = CIBlockSection::GetList(
    Array("SORT" => "ASC"),
    Array(
        "=IBLOCK_ID" => $arParams["IBLOCK_ID"],
        "=ACTIVE"    => "Y"
    )
);

// Собираем разделы в массив
while ($arSection = $rsSections->GetNext())
    $arSections[] = $arSection;

// Фильтруем элементы по принадлежности к разделу
// Получаем итоговый массив со структурой: [SECTION] => [ELEMENTS]
foreach ($arSections as $arSection){
    foreach ($arResult["ITEMS"] as $arItem){
        if ($arItem["IBLOCK_SECTION_ID"] == $arSection["ID"])
            $arSection["ELEMENTS"][] = $arItem;
    }
    $arElementGroups[] = $arSection;
}

$arResult["ITEMS"] = $arElementGroups;

В итоге получаем такую структуру:

Array
(
    // Разделы
    [0] => Array
        (
            [ID] => 17
            [NAME] => Юридические вопросы
            [CODE] => yuridicheskie-voprosy
            [SECTION_PAGE_URL] => /faq/yuridicheskie-voprosy/
            [ELEMENTS] => Array
                (
                    // Элементы
                    [0] => Array
                    [1] => Array
                    [2] => Array
                )
        )
    [1] => Array
    [2] => Array
    ...
)

В template.php выводим так:

<?foreach ($arResult["ITEMS"] as $arSection):?>
    <h4><?=$arSection["NAME"]?></h4>
    <?if ($arSection["ELEMENTS"]):?>
        <ul>
            <?foreach ($arSection["ELEMENTS"] as $arItem):?>
                <?
                $this->AddEditAction($arItem['ID'], $arItem['EDIT_LINK'], CIBlock::GetArrayByID($arItem["IBLOCK_ID"], "ELEMENT_EDIT"));
                $this->AddDeleteAction($arItem['ID'], $arItem['DELETE_LINK'], CIBlock::GetArrayByID($arItem["IBLOCK_ID"], "ELEMENT_DELETE"), array("CONFIRM" => GetMessage('CT_BNL_ELEMENT_DELETE_CONFIRM')));
                ?>
                <li id="<?=$this->GetEditAreaId($arItem['ID']);?>">
                    <a href="<?=$arItem["DETAIL_PAGE_URL"]?>"><?=$arItem["NAME"]?></a>
                </li>
            <?endforeach?>
        </ul>
    <?endif?>
<?endforeach?>

Не нравится мне имя ключа $arResult["ITEMS"], напрашивается "SECTIONS", но пока оставлю, как есть.


Однако есть вариант лучше, который избавит нас от вложенного foreach.

$rsSections = CIBlockSection::GetList(
    Array("SORT" => "ASC"),
    Array(
        "=IBLOCK_ID" => $arParams['IBLOCK_ID'],
        "=ACTIVE"    => "Y"
    )
);

// Тут вместо инкрементного индекса, ID раздела
while ($arSection = $rsSections->GetNext())
    $arSections[$arSection['ID']] = $arSection;

// По нему производим неявную фильрацию
foreach($arResult["ITEMS"] as $arItem) {
    $arSections[$arItem['IBLOCK_SECTION_ID']]['ITEMS'][] = $arItem;
}

$arResult["SECTIONS"] = $arSections;

Получаем струтуру вида:

Array
(   
    // Разделы
    [18] => Array
        (
            [ID] => 18
            [NAME] => Вопросы по доставка и оплате
            [CODE] => voprosy-po-dostavka-i-oplate
            [SECTION_PAGE_URL] => /faq/voprosy-po-dostavka-i-oplate/
            [IBLOCK_TYPE_ID] => references
            [ITEMS] => Array
                (
                    // Элементы
                    [0] => Array
                        (
                            [ID] => 331
                            [IBLOCK_SECTION_ID] => 18
                            [NAME] => Как изменить номер телефона в личном кабинете?
                            [DETAIL_PAGE_URL] => /faq/voprosy-po-dostavka-i-oplate/kak-izmenit-nomer-telefona/
                        )
                    [1] => Array
                    [2] => Array

В template.php аналогичная верстка, лишь переименуем ключи $arResult.

<?foreach ($arResult["SECTIONS"] as $arSection):?>
    <h4><?=$arSection["NAME"]?></h4>
    <ul>
        <?foreach ($arSection["ITEMS"] as $arItem):?>
            <li id="<?=$this->GetEditAreaId($arItem['ID']);?>">
                <a href="<?=$arItem["DETAIL_PAGE_URL"]?>"><?=$arItem["NAME"]?></a>
            </li>
        <?endforeach?>
    </ul>
<?endforeach?>

Итог:

image

-- Написано на основе данных постов:

@kuklofon
Copy link

Спасибо, друг! Выручил!

@sukhikh18
Copy link

Скорее всего имелось ввиду catalog.section.list, catalog.sections не нашел

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment