[BUGFIX] Correctly handle non-existing level in menu.directory VH
[Packages/TYPO3.CMS.git] / typo3 / sysext / fluid_styled_content / Classes / ViewHelpers / Menu / ListViewHelper.php
1 <?php
2 namespace TYPO3\CMS\FluidStyledContent\ViewHelpers\Menu;
3
4 /*
5 * This file is part of the TYPO3 CMS project.
6 *
7 * It is free software; you can redistribute it and/or modify it under
8 * the terms of the GNU General Public License, either version 2
9 * of the License, or any later version.
10 *
11 * For the full copyright and license information, please read the
12 * LICENSE.txt file that was distributed with this source code.
13 *
14 * The TYPO3 project - inspiring people to share!
15 */
16 use TYPO3\CMS\Fluid\Core\ViewHelper\AbstractViewHelper;
17
18 /**
19 * A view helper which returns a list of pages
20 *
21 * = Example =
22 *
23 * <code title="List of pages with uid = 1 and uid = 2">
24 * <ce:menu.list pageUids="{0: 1, 1: 2}" as="pages">
25 * <f:for each="{pages}" as="page">
26 * {page.title}
27 * </f:for>
28 * </ce:menu.list>
29 * </code>
30 *
31 * <output>
32 * Page with uid = 1
33 * Page with uid = 2
34 * </output>
35 */
36 class ListViewHelper extends AbstractViewHelper
37 {
38 use MenuViewHelperTrait;
39
40 /**
41 * Initialize ViewHelper arguments
42 */
43 public function initializeArguments()
44 {
45 $this->registerArgument('as', 'string', 'Name of template variable which will contain selected pages', true);
46 $this->registerArgument('levelAs', 'string', 'Name of template variable which will contain current level', false, null);
47 $this->registerArgument('pageUids', 'array', 'Page UIDs of parent pages', false, []);
48 $this->registerArgument('entryLevel', 'integer', 'The entry level', false, null);
49 $this->registerArgument('maximumLevel', 'integer', 'Maximum level for rendering of nested menus', false, 10);
50 $this->registerArgument('includeNotInMenu', 'boolean', 'Include pages that are marked "hide in menu"?', false, false);
51 $this->registerArgument('includeMenuSeparator', 'boolean', 'Include pages of the type "Menu separator"?', false, false);
52 }
53
54 /**
55 * Render the view helper
56 *
57 * @return string
58 * @throws \TYPO3\CMS\Fluid\Core\ViewHelper\Exception
59 */
60 public function render()
61 {
62 $typoScriptFrontendController = $this->getTypoScriptFrontendController();
63 $as = $this->arguments['as'];
64 $pageUids = (array)$this->arguments['pageUids'];
65 $entryLevel = $this->arguments['entryLevel'];
66 $levelAs = $this->arguments['levelAs'];
67 $maximumLevel = $this->arguments['maximumLevel'];
68 $includeNotInMenu = (bool)$this->arguments['includeNotInMenu'];
69 $includeMenuSeparator = (bool)$this->arguments['includeMenuSeparator'];
70
71 $pageUids = $this->getPageUids($pageUids, $entryLevel);
72 if (empty($pageUids)) {
73 return '';
74 }
75
76 $pages = $typoScriptFrontendController->sys_page->getMenuForPages(
77 $pageUids,
78 '*',
79 '',
80 $this->getPageConstraints($includeNotInMenu, $includeMenuSeparator)
81 );
82
83 $tempPagesForSort = [];
84 foreach ($pageUids as $pageUid) {
85 if ($pages[$pageUid]) {
86 $tempPagesForSort[$pageUid] = $pages[$pageUid];
87 }
88 }
89 $pages = $tempPagesForSort;
90
91 $output = '';
92
93 if (!empty($pages)) {
94 if (!$typoScriptFrontendController->register['ceMenuLevel_list']) {
95 $typoScriptFrontendController->register['ceMenuLevel_list'] = 1;
96 $typoScriptFrontendController->register['ceMenuMaximumLevel_list'] = $maximumLevel;
97 } else {
98 $typoScriptFrontendController->register['ceMenuLevel_list']++;
99 }
100
101 if ($typoScriptFrontendController->register['ceMenuLevel_list'] > $typoScriptFrontendController->register['ceMenuMaximumLevel_list']) {
102 return '';
103 }
104
105 $variables = [
106 $as => $pages
107 ];
108 if (!empty($levelAs)) {
109 $variables[$levelAs] = $typoScriptFrontendController->register['ceMenuLevel_list'];
110 }
111 $output = $this->renderChildrenWithVariables($variables);
112
113 $typoScriptFrontendController->register['ceMenuLevel_list']--;
114
115 if ($typoScriptFrontendController->register['ceMenuLevel_list'] === 0) {
116 unset($typoScriptFrontendController->register['ceMenuLevel_list']);
117 unset($typoScriptFrontendController->register['ceMenuMaximumLevel_list']);
118 }
119 }
120
121 return $output;
122 }
123 }