Loading core/modules/navigation/layouts/navigation.html.twig +1 −0 Original line number Diff line number Diff line Loading @@ -70,6 +70,7 @@ } only %} </div> {{ content.content_top }} {{ content.content }} </nav> Loading core/modules/navigation/navigation.api.php 0 → 100644 +57 −0 Original line number Diff line number Diff line <?php /** * @file * Hooks related to the Navigation module. */ /** * @addtogroup hooks * @{ */ /** * Provide content for Navigation content_top section. * * @return array * An associative array of renderable elements. * * @see hook_navigation_content_top_alter() */ function hook_navigation_content_top(): array { return [ 'navigation_foo' => [ '#markup' => \Drupal::config('system.site')->get('name'), '#cache' => [ 'tags' => ['config:system.site'], ], ], 'navigation_bar' => [ '#markup' => 'bar', ], 'navigation_baz' => [ '#markup' => 'baz', ], ]; } /** * Alter replacement values for placeholder tokens. * * @param $content_top * An associative array of content returned by hook_navigation_content_top(). * * @see hook_navigation_content_top() */ function hook_navigation_content_top_alter(array &$content_top): void { // Remove a specific element. unset($content_top['navigation_foo']); // Modify an element. $content_top['navigation_bar']['#markup'] = 'new bar'; // Change weight. $content_top['navigation_baz']['#weight'] = '-100'; } /** * @} End of "addtogroup hooks". */ core/modules/navigation/src/Hook/NavigationHooks.php +5 −0 Original line number Diff line number Diff line Loading @@ -99,6 +99,11 @@ public function theme($existing, $type, $theme, $path) : array { ], ]; $items['menu_region__footer'] = ['variables' => ['items' => [], 'title' => NULL, 'menu_name' => NULL]]; $items['navigation_content_top'] = [ 'variables' => [ 'items' => [], ], ]; return $items; } Loading core/modules/navigation/src/NavigationRenderer.php +32 −1 Original line number Diff line number Diff line Loading @@ -3,6 +3,7 @@ namespace Drupal\navigation; use Drupal\Component\Utility\NestedArray; use Drupal\Component\Utility\SortArray; use Drupal\Core\Block\BlockPluginInterface; use Drupal\Core\Cache\CacheBackendInterface; use Drupal\Core\Cache\CacheableMetadata; Loading @@ -18,6 +19,7 @@ use Drupal\Core\Menu\LocalTaskManagerInterface; use Drupal\Core\Plugin\Context\Context; use Drupal\Core\Plugin\Context\ContextDefinition; use Drupal\Core\Render\Element; use Drupal\Core\Routing\RouteMatchInterface; use Drupal\Core\Security\Attribute\TrustedCallback; use Drupal\Core\Session\AccountInterface; Loading Loading @@ -128,6 +130,7 @@ public function doBuildNavigation($build): array { if ($storage) { foreach ($storage->getSections() as $delta => $section) { $build[$delta] = $section->toRenderArray([]); $build[$delta]['#cache']['contexts'] = ['user.permissions', 'theme', 'languages:language_interface']; } } // The render array is built based on decisions made by SectionStorage Loading Loading @@ -157,6 +160,8 @@ public function doBuildNavigation($build): array { ]; $build[0] = NestedArray::mergeDeepArray([$build[0], $defaults]); $build[0]['content_top'] = $this->getContentTop(); if ($logo_provider === self::LOGO_PROVIDER_CUSTOM) { $logo_path = $logo_settings->get('logo.path'); if (!empty($logo_path) && is_file($logo_path)) { Loading @@ -169,10 +174,36 @@ public function doBuildNavigation($build): array { } } } $build[0]['#cache']['contexts'] = ['user.permissions', 'theme', 'languages:language_interface']; return $build; } /** * Gets the content for content_top section. * * @return array * The content_top section content. */ protected function getContentTop(): array { $content_top = [ '#theme' => 'navigation_content_top', ]; $content_top_items = $this->moduleHandler->invokeAll('navigation_content_top'); $this->moduleHandler->alter('navigation_content_top', $content_top_items); uasort($content_top_items, [SortArray::class, 'sortByWeightElement']); // Filter out empty items, taking care to merge any cacheability metadata. $cacheability = new CacheableMetadata(); $content_top_items = array_filter($content_top_items, function ($item) use (&$cacheability) { if (Element::isEmpty($item)) { $cacheability = $cacheability->merge(CacheableMetadata::createFromRenderArray($item)); return FALSE; } return TRUE; }); $cacheability->applyTo($content_top); $content_top['#items'] = $content_top_items; return $content_top; } /** * Build the top bar for content entity pages. * Loading core/modules/navigation/templates/navigation-content-top.html.twig 0 → 100644 +17 −0 Original line number Diff line number Diff line {# /** * @file * Default theme implementation to display the navigation content_top section. * * Available variables: * - items: An associative array of renderable elements to display in the * content_top section. * * @ingroup themeable */ #} {% if items is not empty %} <div class="admin-toolbar__content-top"> {{ items }} </div> {% endif %} Loading
core/modules/navigation/layouts/navigation.html.twig +1 −0 Original line number Diff line number Diff line Loading @@ -70,6 +70,7 @@ } only %} </div> {{ content.content_top }} {{ content.content }} </nav> Loading
core/modules/navigation/navigation.api.php 0 → 100644 +57 −0 Original line number Diff line number Diff line <?php /** * @file * Hooks related to the Navigation module. */ /** * @addtogroup hooks * @{ */ /** * Provide content for Navigation content_top section. * * @return array * An associative array of renderable elements. * * @see hook_navigation_content_top_alter() */ function hook_navigation_content_top(): array { return [ 'navigation_foo' => [ '#markup' => \Drupal::config('system.site')->get('name'), '#cache' => [ 'tags' => ['config:system.site'], ], ], 'navigation_bar' => [ '#markup' => 'bar', ], 'navigation_baz' => [ '#markup' => 'baz', ], ]; } /** * Alter replacement values for placeholder tokens. * * @param $content_top * An associative array of content returned by hook_navigation_content_top(). * * @see hook_navigation_content_top() */ function hook_navigation_content_top_alter(array &$content_top): void { // Remove a specific element. unset($content_top['navigation_foo']); // Modify an element. $content_top['navigation_bar']['#markup'] = 'new bar'; // Change weight. $content_top['navigation_baz']['#weight'] = '-100'; } /** * @} End of "addtogroup hooks". */
core/modules/navigation/src/Hook/NavigationHooks.php +5 −0 Original line number Diff line number Diff line Loading @@ -99,6 +99,11 @@ public function theme($existing, $type, $theme, $path) : array { ], ]; $items['menu_region__footer'] = ['variables' => ['items' => [], 'title' => NULL, 'menu_name' => NULL]]; $items['navigation_content_top'] = [ 'variables' => [ 'items' => [], ], ]; return $items; } Loading
core/modules/navigation/src/NavigationRenderer.php +32 −1 Original line number Diff line number Diff line Loading @@ -3,6 +3,7 @@ namespace Drupal\navigation; use Drupal\Component\Utility\NestedArray; use Drupal\Component\Utility\SortArray; use Drupal\Core\Block\BlockPluginInterface; use Drupal\Core\Cache\CacheBackendInterface; use Drupal\Core\Cache\CacheableMetadata; Loading @@ -18,6 +19,7 @@ use Drupal\Core\Menu\LocalTaskManagerInterface; use Drupal\Core\Plugin\Context\Context; use Drupal\Core\Plugin\Context\ContextDefinition; use Drupal\Core\Render\Element; use Drupal\Core\Routing\RouteMatchInterface; use Drupal\Core\Security\Attribute\TrustedCallback; use Drupal\Core\Session\AccountInterface; Loading Loading @@ -128,6 +130,7 @@ public function doBuildNavigation($build): array { if ($storage) { foreach ($storage->getSections() as $delta => $section) { $build[$delta] = $section->toRenderArray([]); $build[$delta]['#cache']['contexts'] = ['user.permissions', 'theme', 'languages:language_interface']; } } // The render array is built based on decisions made by SectionStorage Loading Loading @@ -157,6 +160,8 @@ public function doBuildNavigation($build): array { ]; $build[0] = NestedArray::mergeDeepArray([$build[0], $defaults]); $build[0]['content_top'] = $this->getContentTop(); if ($logo_provider === self::LOGO_PROVIDER_CUSTOM) { $logo_path = $logo_settings->get('logo.path'); if (!empty($logo_path) && is_file($logo_path)) { Loading @@ -169,10 +174,36 @@ public function doBuildNavigation($build): array { } } } $build[0]['#cache']['contexts'] = ['user.permissions', 'theme', 'languages:language_interface']; return $build; } /** * Gets the content for content_top section. * * @return array * The content_top section content. */ protected function getContentTop(): array { $content_top = [ '#theme' => 'navigation_content_top', ]; $content_top_items = $this->moduleHandler->invokeAll('navigation_content_top'); $this->moduleHandler->alter('navigation_content_top', $content_top_items); uasort($content_top_items, [SortArray::class, 'sortByWeightElement']); // Filter out empty items, taking care to merge any cacheability metadata. $cacheability = new CacheableMetadata(); $content_top_items = array_filter($content_top_items, function ($item) use (&$cacheability) { if (Element::isEmpty($item)) { $cacheability = $cacheability->merge(CacheableMetadata::createFromRenderArray($item)); return FALSE; } return TRUE; }); $cacheability->applyTo($content_top); $content_top['#items'] = $content_top_items; return $content_top; } /** * Build the top bar for content entity pages. * Loading
core/modules/navigation/templates/navigation-content-top.html.twig 0 → 100644 +17 −0 Original line number Diff line number Diff line {# /** * @file * Default theme implementation to display the navigation content_top section. * * Available variables: * - items: An associative array of renderable elements to display in the * content_top section. * * @ingroup themeable */ #} {% if items is not empty %} <div class="admin-toolbar__content-top"> {{ items }} </div> {% endif %}