Вы здесь

Как правильно отсортировать элементы в renderable array?

1

Здравствуйте. Никак не могу разобраться с порядком в renderable array. Есть такая функция темы

function mpgrey_page_alter(&$build) {
  if (arg(0) == 'taxonomy' && arg(1) == 'term') {
    unset($build['content']['system_main']['nodes']);
    unset($build['content']['system_main']['pager']);
    $build['content']['system_main']['term_heading']['term']['description']['#weight'] = -1002;
    $build['content']['system_main']['term_heading']['term']['nodes'] = array(
      '#markup' => views_embed_view('tovari', 'block_tovari_spisok'),
      '#weight' => -1001,
      );
    $build['content']['system_main']['term_heading']['term']['field_tekst_2']['#weight'] = -1000;
    //$build['content']['#sorted'] = FALSE;
  }
}

хочется, чтобы сначала на странице был ['description'], потом ['nodes'], потом ['field_tekst_2']. А получается ['nodes'], ['field_tekst_2'], ['description']. Установка $build['content']['#sorted'] = FALSE не меняет ситуацию никак. Подскажите пожалуйста, как правильно сделать?

Версия Drupal: 
7.x
Категория: 
Theming
Вопрос задан 16.06.2015 - 17:06

И еще комментарий: то, что ты делаешь, не очень хорошо. потому что сначала модуль Taxonomy дергает связанные ноды (которые ты unsetишь), а потом и твой вьюс делает аналогичную операцию.
Правильнее переопределять стандартный вывод:
1) Views для taxonomy/term/%, вывод полей термина, например, на этапе препроцесса вывода вьюса (пихать нужный вывод в header/footer вьюсов)
2) Использовать модуль Taxonomy display
3) Переопределять из hook_menu_alter callback для taxonomy/term/%taxoonomy_term на свой и в нем делать, что душе угодно (именно это и делает модуль из 2)

Думаю, вариант 2 в твоем случае оптимальный. Там и порядок назначишь из админики

Комментарий оставлен 18.06.2015 - 09:43

Вот за 2) спасибо, как-то я этот модуль стороной обошёл. Действительно, одни и те же данные дёргаются 2 раза, я думал об этом, но не придумал как избежать.
Пробовал 3) но не понял как сделать чтобы показывать метатеги термина из модуля Metatag.

Комментарий оставлен 27.09.2015 - 17:17

Ответы

1

$build['content']['#sorted'] = FALSE
сработает только для элементов массива уровня 'content'

попробуй
$build['content']['system_main']['term_heading']['term']['#sorted'] = FALSE;

Логика поиска ответа на вопрос (по крайне мере моя :))
1. Смотрим https://api.drupal.org/api/drupal/modules%21system%21system.api.php/func...
Из блока See also ясно, что хук дергается drupal_render_page()
2. Смотрим drupal_render_page(). Ясно, что рендер (как оно и должно быть) идет из drupal_render().
3. Смотрим функцию drupal_render()
Видим кусочек
// Get the children of the element, sorted by weight.
$children = element_children($elements, TRUE);
Сортировка происходит в element_children.
4. Финальный заход - смотрим element_children() и понимаем, что параметр '#sorted' не распространяет свое действие в глубину

P.s. на самом деле это совсем не долго, как может показаться

Ответ дан 16.06.2015 - 18:23

спасибо, но так

$build['content']['system_main']['term_heading']['term']['#sorted'] = FALSE;
$build['content']['#sorted'] = FALSE;

тоже ничего не меняется.

Комментарий оставлен 16.06.2015 - 20:48

кто-то же наверняка знает, как эта штука работает?

Комментарий оставлен 17.06.2015 - 17:36

Проверил у себя
$page['content']['system_main']['term_heading']['term']['view_catalog']['#weight'] = 2;
$page['content']['system_main']['term_heading']['term']['field_additional_description']['#weight'] = 1;

view_catalog - аналог твоего nodes
У меня все сработало, элементы поменялись местами.
Проверь taxonomy-term.tpl.php - может, там что-то выводится в ручную в определенных местах вместо обычного print render($content);

Комментарий оставлен 17.06.2015 - 19:00