Generates hierarchical menus.
Property: | Data type: | Description: | Default: |
|---|---|---|---|
(1 / 2 / 3 /...) | menuObj | Required! Defines which menuObj that should render the menuitems on the various levels. 1 is the first level, 2 is the second level, 3 is the third level, 4 is .... Example: temp.sidemenu = HMENU temp.sidemenu.1 = GMENU | (no menu) |
entryLevel | int | Defines at which level in the rootLine, the menu should start. Default is "0" which gives us a menu of the very first pages on the site. If the value is < 0, entryLevel is chosen from "behind" in the rootLine. Thus "-1" is a menu with items from the outermost level, "-2" is the level before the outermost... | 0 |
special | "directory" / "list" / "updated" / "browse" / "rootline" / "keywords" / “language” | (See separate table below) | |
special.value | list of page-uid's /stdWrap | See above | |
minItems | int | The minimum items in the menu. If the number of pages does not reach this level, a dummy-page with the title "..." and uid=[currentpage_id] is inserted. Notice: Affects all sub menus as well. To set the value for each menu level individually, set the properties in the menu objects (see “Common properties” table). | |
maxItems | int | The maximum items in the menu. More items will be ignored. Notice: Affects all sub menus as well. (See “minItems” for notice) | |
begin | int +calc | The first item in the menu. Example: This results in a menu, where the first two items are skipped starting with item number 3: begin = 3 Notice: Affects all sub menus as well. (See “minItems” for notice) | |
excludeUidList | list of int | This is a list of page uid's to exclude when the select statement is done. Comma-separated. You may add “current” to the list to exclude the current page. Example: The pages with these uid-number will NOT be within the menu!! Additionally the current page is always excluded too. excludeUidList = 34,2,current | |
excludeDoktypes | list of integers | Enter the list of page document types (doktype) to exclude from menus. By default pages that are “not in menu” (5) are excluded and those marked for backend user access only (6). | 5,6 |
includeNotInMenu | boolean | If set, pages with type “Not in menu” will be included in menus. The number “5” will simply be removed from the current dok-type list (which is by default “5,6” but can be changed by “excludeDoktypes”, see above). | |
alwaysActivePIDlist | list of integers | This is a list of page UID numbers that will always be regarded as active menu items and thereby automatically opened regardless of the rootline. | |
protectLvar | boolean / keyword | If set, then for each page in the menu it will be checked if an Alternative Page Language record for the language defined in "config.sys_language_uid" (typically defined via &L) exists for the page. If that is not the case and the pages “Localization settings” have the “Hide page if no translation for current language exists” flag set, then the menu item will link to a non accessible page that will yield an error page to the user. Setting this option will prevent that situation by simply adding “&L=0” for such pages, meaning that they will switch to the default language rather than keeping the current language. The check is only carried out if a translation is requested ("config.sys_language_uid" is not zero). Keyword: “all” When set to “all” the same check is carried out but it will not look if “Hide page if no translation for current language exists” is set - it always reverts to default language if no translation is found. For these options to make sense, they should only be used when “config.sys_language_mode” is not set to “content_fallback”. | |
addQueryString | string | see typolink.addQueryString Notice: This works only for special=language. | |
if | ->if | If "if" returns false, the menu is not generated | |
wrap | wrap | ||
stdWrap | ->stdWrap |
[tsref:(cObject).HMENU]
temp.sidemenu = HMENU
temp.sidemenu.entryLevel = 1
temp.sidemenu.1 = TMENU
temp.sidemenu.1 {target = page
NO.afterImg = media/bullets/dots2.gif |*||*| _
NO.afterImgTagParams = hspace="4"
NO.linkWrap = {$fontTag}NO.ATagBeforeWrap = 1
ACT < .NO
ACT = 1
ACT.linkWrap = <b>{$fontTag}</b>}
This property makes it possible to create menus that are not strictly reflecting the current page-structure, but rather creating menus with links to pages like "next/previous", "last modified", "pages in a certain page" and so on.
NOTE: Don't set .entryLevel for a HMENU when using this option! Also be aware that this selects pages for the first level in the menu. Submenus by menuPbjects 2+ will be created as usual.
.special.value always has stdWrap-properties!
Their properies are put in this tables:
Type: | Description: | Default: |
|---|---|---|
directory | This will generate a menu of all pages with pid = 35 and pid = 56. 20 = HMENU 20.special = directory 20.special.value = 35, 56 If .value is not set, the default pid is the current page. Support for Mount Pages: Yes. | |
list | This will generate a menu with the two pages (uid=35 and uid=36) listed: 20 = HMENU 20.special = list 20.special.value = 35, 56 If .value is not set, the default uid is the .entryLevel uid. Support for Mount Pages: Yes. | |
updated | This will generate a menu of the most recently updated pages from the branches in the tree starting with the uid's (uid=35 and uid=36) listed. Furthermore the field "tstamp" is used (default is SYS_LASTCHANGED) and the treedepth is 2 levels. Also there will be shown a maximum of 8 pages and they must have been updated within the last three days (3600*24*3): 20 = HMENU 20.special = updated 20.special.value = 35, 56 20.special { mode = tstamp depth = 2 maxAge = 3600*24*3 limit = 8 } Ordering is by default done in reverse order (desc) with the field specified by “mode” , but setting “alternativeSortingField” for the menu object (eg GMENU, see later) will override that. Properties "mode", "depth", "maxAge" and "limit" is only used with special="updated". mode: Which field in the pages-table to use. Default is "SYS_LASTCHANGED" (which is updated when a page is generated to the youngest tstamp of the records on the page), "manual" or “lastUpdated” will use the field "lastUpdated" (set manually in the page-record) and "tstamp" will use the "tstamp"-field of the pagerecord, which is set automatically when the record is changed. "crdate" will use "crdate"-field of the pagerecord. “starttime” will use the starttime field. Fields with zero value is not selected anyway. depth: By default (if the value is not an integer) the depth is 20 levels. The range is 1-20. A depth of 1 means only the start id, depth of 2 means start-id + first level. NOTE: depth is relative to beginAtLevel. beginAtLevel: Integer. Determines starting level for the pagetrees generated based on .value and .depth. Zero is default and includes the start id. 1=starts with the first row of subpages, 2=starts with the second row of subpages. Depth is relative to this starting point. maxAge: Seconds+calc. Pages with update-dates older than currenttime minus this number of seconds will not be shown in the menu no matter what. Default is "not used". You may use +-*/ for calculations. limit: Max number of items in the menu. Default is 10, max is 100. excludeNoSearchPages: Boolean. If set, pages marked "No search" is not included into special-menus. Support for Mount Pages: Yes. | |
rootline | Creates a menu with pages from the "rootline" (see earlier in this reference) .range = [begin-level] | [end-level] (same way as you reference the .entryLevel for HMENU) .target_[0-x] targets This... page.2 = HMENU page.2.special = rootline page.2.special.range = 1|-2 page.2.special.targets.3 = page page.2.1 = TMENU page.2.1.target = _top page.2.1.wrap = <HR> | <HR> page.2.1.NO { linkWrap = | > } ... creates a menu like this: Page level 1 > Page level 2 > Page level 3 > Page level 4 > (The menu starts at level 1 and does NOT link to the current page (-2 is the level before). Further all pages on level 3 will have "page" as target and all other "_top") Support for Mount Pages: Yes. | |
browse | This kind of menu is built of items given by a list from the property ".item". Each element in the list (sep. by "|") is either a reserved itemname (see list) with a predefined function or a userdefined name which you can assign a link to any page. Note that the current page cannot be the root-page of a site. Support for Mount Pages: No! .items ( "|" separated list of "itemnames") .[itemnames].target (target) - optional/alternative target of the item .[itemnames].uid (uid of page) - optional/alternative page-uid to link to .[itemnames].fields.[fieldname] (string) - override field "fieldname" in pagerecord. .items.prevnextToSection (boolean) - if set, the "prev" and "next" navigation will jump to the next section when it reaches the end of pages in the current section .value (page-uid) - default is current page id. Seldomly you might want to override this value with another page-uid which will then act as the basepoint for the menu and the predefined items. Ordering is by default done in reverse order (desc) with the field specified by “mode” , but setting “alternativeSortingField” for the menu object (eg GMENU, see later) will override that. Reserved itemnames: next / prev : links to next page / previous page. Next and previous pages are from the same "pid" as the current page id (or "value") - that is the next item in a menu with the current page. Also referred to as current level. If ".prevnextToSection" is set then next/prev will link to the first page of next section / last page of previous section. nextsection / prevsection : links to next section / previous section. A section is defined as the subpages of a page on the same level as the parent (pid) page of the current page. Will not work if parent page of current page is the root page of the site. nextsection_last | prevsection_last: Where nextsection/prevsection links to the first page in a section, these links to the last pages. If there is only one page in the section that will be both first and last. Will not work if parent page of current page is the root page of the site. first / last : First / Last page on current level. If there is only one page on the current level that page will be both first and last. up : Links to the parent (pid) page of the current page. (up 1 level) Will always be available index : Links to the parent of the parent page of the current page (up 2 levels). May not be available if that page is out of the rootline. Examples: If id=20 is current page then: 21= prev and first, 19 = next, 18 = last, 17 = up, 1=index, 10 = nextsection, 11 = nextsection_last prevsection and prevsection_last is not present because id=3 has no subpages! TypoScript (only "browse"-part, needs also TMENU/GMENU): xxx = HMENU xxx.special = browse xxx.special { items = index|up|next|prev items.prevnextToSection = 1 index.target = _blank index.fields.title = INDEX index.uid = 8 } .items ( "|" separated list of "itemnames") .[itemnames].target (target) - optional/alternative target of the item .[itemnames].uid (uid of page) - optional/alternative page-uid to link to .[itemnames].fields.[fieldname] (string) - override field "fieldname" in pagerecord. .items.prevnextToSection (boolean) - if set, the "prev" and "next" navigation will jump to the next section when it reaches the end of pages in the current section .value (page-uid) - default is current page id. Seldomly you might want to override this value with another page-uid which will then act as the basepoint for the menu and the predefined items. Ordering is by default done in reverse order (desc) with the field specified by “mode” , but setting “alternativeSortingField” for the menu object (eg GMENU, see later) will override that. Reserved itemnames: next / prev : links to next page / previous page. Next and previous pages are from the same "pid" as the current page id (or "value") - that is the next item in a menu with the current page. Also referred to as current level. If ".prevnextToSection" is set then next/prev will link to the first page of next section / last page of previous section. nextsection / prevsection : links to next section / previous section. A section is defined as the subpages of a page on the same level as the parent (pid) page of the current page. Will not work if parent page of current page is the root page of the site. nextsection_last | prevsection_last: Where nextsection/prevsection links to the first page in a section, these links to the last pages. If there is only one page in the section that will be both first and last. Will not work if parent page of current page is the root page of the site. first / last : First / Last page on current level. If there is only one page on the current level that page will be both first and last. up : Links to the parent (pid) page of the current page. (up 1 level) Will always be available index : Links to the parent of the parent page of the current page (up 2 levels). May not be available if that page is out of the rootline. Examples: If id=20 is current page then: 21= prev and first, 19 = next, 18 = last, 17 = up, 1=index, 10 = nextsection, 11 = nextsection_last prevsection and prevsection_last is not present because id=3 has no subpages! TypoScript (only "browse"-part, needs also TMENU/GMENU): xxx = HMENU xxx.special = browse xxx.special { items = index|up|next|prev items.prevnextToSection = 1 index.target = _blank index.fields.title = INDEX index.uid = 8 } | |
keywords | Makes a menu of pages with one or more keywords also found on the current page. .value = page for which keywords to find similar pages. .mode: Which field in the pages-table to use for sorting. Default is "SYS_LASTCHANGED" (which is updated when a page is generated to the youngest tstamp of the records on the page), "manual" or “lastUpdated” will use the field "lastUpdated" (set manually in the page-record) and "tstamp" will use the "tstamp"-field of the pagerecord, which is set automatically when the record is changed. "crdate" will use "crdate"-field of the pagerecord. “starttime” will use the starttime field. .entryLevel = where in the rootline the search begins. Standard rootline syntax (-x to x) .depth, .limit, .excludeNoSearchPages, .beginAtLevel (like "updated" menu) .setKeywords (/stdWrap) = lets you define the keywords manually by defining them as a commaseparated list. If this property is defined, it overrides the default, which is the keywords of the current page. .keywordsField = defines the field in the pages-table in which to search for the keywords. Default is the fieldname “keyword”. No check is done to see if the field you enter here exists, so enter an existing field, OK?! .keywordsField.sourceField = defines the field from the current page from which to take the keywords being matched. The default is “keyword”. (Notice that “.keywordsField” is only setting the page-record field to search in !) Support for Mount Pages: Yes. | |
language | Creates a language selector menu. Typically this is made as a menu with flags for each language a page is translated to and when the user clicks any element the same page id is hit but with a change to the “&L” parameter in the URL. The “language” type will create menu items based on the current page record but with the language record for each language overlaid if available. The items all link to the current page id and only “&L” is changed. Item states: When “TSFE->sys_language_uid” matches the sys_language uid for an element the state is set to “ACT”, otherwise “NO”. However, if a page is not available due to the pages “Localization settings” (which can disable translations) or if no Alternative Page Language record was found (can be disabled with “.normalWhenNoLanguage”, see below) the state is set to “USERDEF1” for non-active items and “USERDEF2” for active items. So in total there are four states to create designs for. It is recommended to disable the link on menu items rendered with “USERDEF1” and “USERDEF2” in this case since they are disabled exactly because a page in that language does not exist and might even issue an error if tried accessed (depending on site configuration). .value = comma list of sys_language uids to construct the menu with. The number of elements in this list determines the number of menu items. .normalWhenNoLanguage = boolean, which if set will render the button for a language as a non-disabled button even if no translation is found for the language. Example: Creates a language menu with flags (notice that some lines break):
lib.langMenu = HMENU lib.langMenu.special = language lib.langMenu.special.value = 0,1,2 lib.langMenu.1 = GMENU lib.langMenu.1.NO { XY = [5.w]+4, [5.h]+4 backColor = white 5 = IMAGE 5.file = media/flags/flag_uk.gif || media/flags/flag_fr.gif || media/flags/flag_es.gif 5.offset = 2,2 } lib.langMenu.1.ACT < lib.langMenu.1.NO lib.langMenu.1.ACT=1 lib.langMenu.1.ACT.backColor = black lib.langMenu.1.USERDEF1 < lib.langMenu.1.NO lib.langMenu.1.USERDEF1=1 lib.langMenu.1.USERDEF1.5.file = media/flags/flag_uk_d.gif || media/flags/flag_fr_d.gif || media/flags/flag_es_d.gif lib.langMenu.1.USERDEF1.noLink = 1 | |
userdefined | Lets you write your own little PHP-script that generates the array of menuitems. .file [resource] = filename of the php-file to include. (Just like cObject PHP_SCRIPT) .[any other key] = your own variables to your script. They are all accessible in the array $conf in your script Howto: You must populate an array called $menuItemsArray with page-records of the menuitems you want to be in the menu. It goes like this: $menuItemsArray[] = pageRow1; $menuItemsArray[] = pageRow2; $menuItemsArray[] = pageRow3; ... A “pageRow” is a record from the table “pages” with all fields selected (SELECT * FROM...) If you create fake page rows, make sure to add at least “title” and “uid” field values. Notice: If you work with mount-points you can set the MP param which should be set for the page by setting the internal field “_MP_PARAM” in the page-record (xxx-xxx). Overriding URLs: You can also use the internal field "_OVERRIDE_HREF" to set a custom href-value (eg. "http://www.typo3.org") which will in any case be used rather than a link to the page that the page otherwise might represent. If you use "_OVERRIDE_HREF" then "_OVERRIDE_TARGET" can be used to override the target value as well (See example below). Other reserved keys: “_ADD_GETVARS” can be used to add get parameters to the URL, eg. “&L=xxx”. “_SAFE” can be used to protect the element to make sure it is not filtered out for any reason. Creating submenus: You can create submenus for the next level easily by just adding an array of menu items in the internal field "_SUB_MENU" (See example below). Presetting element state If you would like to preset an element to be recognized as a SPC, IFSUB, ACT, CUR or USR mode item, you can do so by specifying one of these values in the key “ITEM_STATE” of the page record. This setting will override the natural state-evaluation. | |
userfunction | Calls a user function/method in class which should (as with “userdefined” above) return an array with page records for the menu. .userFunc = function-name |
[tsref:(cObject).HMENU.special]
By default the HMENU object is designed to create menus from pages in TYPO3. Such pages are represented by their page-record contents. Usually the "title" field is used for the title and the "uid" field is used to create a link to that page in the menu.
However the HMENU and sub-menu objects are so powerful that it would be very useful to use these objects for creating menus of links which does not relate to pages in TYPO3 by their ids. This could be a menu reflecting a menu structure of a plugin where each link might link to the same page id in TYPO3 but where the difference would be in some parameter value.
This can be easily done with the special-type "userdefined" (see table above) where you can return an array of menu items customly build in a PHP-script you write.
First, this listing creates a menu in three levels where the first two are graphical items:
script_ended = 0;
function jumpToUrl(URL) {
document.location = URL;
}
0: # ************************1: # MENU LEFT
2: # ************************
3: lib.leftmenu.20 = HMENU
4: lib.leftmenu.20.special = userfunction
5: lib.leftmenu.20.special.userFunc = user_3dsplm_pi2->makeMenuArray
6: lib.leftmenu.20.1 = GMENU
7: lib.leftmenu.20.1.NO {8: wrap = <tr><td>|</td></tr><tr><td class="bckgdgrey1" height="1"></td></tr>
9: XY = 163,19
10: backColor = white
11: 10 = TEXT
12: 10.text.field = title
13: 10.text.case = upper
14: 10.fontColor = red
15: 10.fontFile = fileadmin/fonts/ARIALNB.TTF
16: 10.niceText = 1
17: 10.offset = 14,12
18: 10.fontSize = 10
19: }
20: lib.leftmenu.20.2 = GMENU
21: lib.leftmenu.20.2.wrap = | <tr><td class="bckgdwhite" height="4"></td></tr><tr><td class="bckgdgrey1" height="1"></td></tr>
22: lib.leftmenu.20.2.NO {23: wrap = <tr><td class="bckgdwhite" height="4"></td></tr><tr><td>|</td></tr>
24: XY = 163,16
25: backColor = white
26: 10 = TEXT
27: 10.text.field = title
28: 10.text.case = upper
29: 10.fontColor = #666666
30: 10.fontFile = fileadmin/fonts/ARIALNB.TTF
31: 10.niceText = 1
32: 10.offset = 14,12
33: 10.fontSize = 11
34: }
35: lib.leftmenu.20.2.RO < lib.leftmenu.20.2.NO
36: lib.leftmenu.20.2.RO = 1
37: lib.leftmenu.20.2.RO.backColor = #eeeeee
38: lib.leftmenu.20.2.ACT < lib.leftmenu.20.2.NO
39: lib.leftmenu.20.2.ACT = 1
40: lib.leftmenu.20.2.ACT.10.fontColor = red
41: lib.leftmenu.20.3 = TMENU
42: lib.leftmenu.20.3.NO {43: allWrap = <tr><td>|</td></tr>
44: linkWrap (
45: <table border="0" cellpadding="0" cellspacing="0" style="margin: 2px; 0px; 2px; 0px;">
46: <tr>
47: <td><img src="clear.gif" width="15" height="1" /></td>
48: <td><img src="fileadmin/arrow_gray.gif" height="9" width="9" hspace="3" /></td>
49: <td>|</td>
50: </tr>
51: </table>
52: )
53: }
The menu looks like this on a webpage:
The TypoScript code above generates this menu, but the items does not link straight to pages as usual. This is because the whole menu is generated from this array, which was returned from the function "menuMenuArray" called in TypoScript line 4+5
1: function makeMenuArray($content,$conf) {2: return array(
3: array(
4: 'title' => 'Contact',
5: '_OVERRIDE_HREF' => 'index.php?id=10',
6: '_SUB_MENU' => array(
7: array(
8: 'title' => 'Offices',
9: '_OVERRIDE_HREF' => 'index.php?id=11',
10: '_OVERRIDE_TARGET' => '_top',
11: 'ITEM_STATE' => 'ACT',
12: '_SUB_MENU' => array(
13: array(
14: 'title' => 'Copenhagen Office',
15: '_OVERRIDE_HREF' => 'index.php?id=11&officeId=cph',
16: ),
17: array(
18: 'title' => 'Paris Office',
19: '_OVERRIDE_HREF' => 'index.php?id=11&officeId=paris',
20: ),
21: array(
22: 'title' => 'New York Office',
23: '_OVERRIDE_HREF' => 'http://www.newyork-office.com',
24: '_OVERRIDE_TARGET' => '_blank',
25: )
26: )
27: ),
28: array(
29: 'title' => 'Form',
30: '_OVERRIDE_HREF' => 'index.php?id=10&cmd=showform',
31: ),
32: array(
33: 'title' => 'Thank you',
34: '_OVERRIDE_HREF' => 'index.php?id=10&cmd=thankyou',
35: ),
36: ),
37: ),
38: array(
39: 'title' => 'Products',
40: '_OVERRIDE_HREF' => 'index.php?id=14',
41: )
42: );
43: }
Notice how the array contains "fake" page-records which has no uid field, only a "title" and "_OVERRIDE_HREF" as required and some other fields as it fits.
The first level with items "Contact" and "Products" contains "title" and "_OVERRIDE_HREF" fields, but "Contact" extends this by a "_SUB_MENU" array which contains a similar array of items.
The first item on the second level, "Offices", contains a field called "_OVERRIDE_TARGET". Further the item has its state set to "ACT" which means it will render as an "active" item (you will have to calculate such stuff manually when you are not rendering a menu of real pages!). Finally there is even another sub-level of menu items.