3 * FusionForge navigation
5 * Copyright 2009 - 2010, Olaf Lenz
6 * Copyright 2011, Franck Villaume - TrivialDev
8 * This file is part of FusionForge. FusionForge is free software;
9 * you can redistribute it and/or modify it under the terms of the
10 * GNU General Public License as published by the Free Software
11 * Foundation; either version 2 of the Licence, or (at your option)
14 * FusionForge is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
19 * You should have received a copy of the GNU General Public License along
20 * with FusionForge; if not, write to the Free Software Foundation, Inc.,
21 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
24 require_once $gfwww.'search/include/SearchManager.class.php';
27 * This class provides all the navigational elements to be used by the themes,
28 * like the site menu, the project menus, and the user links.
29 * Some of the methods return HTML code, some return abstract data
30 * structures, and some methods give you the choice. The HTML code
31 * always tries to be as generic as possible so that it can easily be
34 class Navigation extends Error {
36 * Associative array of data for the project menus.
38 * @var array $project_menu_data.
40 var $project_menu_data;
43 function Navigation() {
48 /** Get the HTML code of the title of the page. If the array
49 * $params contains a value for the key 'title', this title
50 * is appended to the title generated here. If $asHTML is
51 * set to false, it will return only the title in plain
54 function getTitle($params, $asHTML = true) {
57 if (!isset($params['title'])) {
58 return forge_get_config('forge_name');
60 return forge_get_config('forge_name') . ': ' . $params['title'];
63 // return HTML code otherwise
64 return '<title>' . $this->getTitle($params, false) . '</title>';
68 /** Get the HTML code for the favicon links of the site (to be
69 * put into the <head>. If $asHTML is false, it will return
70 * the URL of the favicon.
72 * @todo: Make favicon configurable
74 function getFavIcon($asHTML = true) {
76 return util_make_url('/images/icon.png');
78 return '<link rel="icon" type="image/png" href="'
79 . $this->getFavIcon(false) .'" />'
80 . '<link rel="shortcut icon" type="image/png" href="'
81 . $this->getFavIcon(false) .'" />';
85 /** Get the HTML code for the RSS feeds of the site (to be put
86 * into the <head>. If $asHTML is false, it will return an
87 * array with the following structure: $result['titles']:
88 * list of titles of the feeds; $result['urls'] list of urls
91 function getRSS($asHTML = true) {
94 $res['titles'] = array();
95 $res['urls'] = array();
97 $res['titles'][] = forge_get_config ('forge_name').' - Project News Highlights RSS';
98 $res['urls'][] = util_make_url('/export/rss_sfnews.php');
100 $res['titles'][] = forge_get_config ('forge_name').' - Project News Highlights RSS 2.0';
101 $res['urls'][] = util_make_url('/export/rss20_news.php');
103 $res['titles'][] = forge_get_config ('forge_name').' - New Projects RSS';
104 $res['urls'][] = util_make_url('/export/rss_sfprojects.php');
106 if (isset($GLOBALS['group_id'])) {
107 $res['titles'][] = forge_get_config ('forge_name') . ' - New Activity RSS';
108 $res['urls'][] = util_make_url('/export/rss20_activity.php?group_id='.$GLOBALS['group_id']);
112 $feeds = $this->getRSS(false);
113 for ($j = 0; $j < count($feeds['urls']); $j++) {
115 <link rel="alternate" title="' .
116 util_html_secure($feeds['titles'][$j]) .
117 '" href="' . $feeds['urls'][$j] .
118 '" type="application/rss+xml"/>';
124 * Get the searchBox HTML code.
126 function getSearchBox() {
127 global $words, $forum_id, $group_id, $group_project_id, $atid, $exact, $type_of_search;
130 if (get_magic_quotes_gpc()) {
131 $defaultWords = stripslashes($words);
133 $defaultWords = $words;
136 $defaultWords = htmlspecialchars($defaultWords);
138 // if there is no search currently, set the default
139 if (!isset($type_of_search) ) {
143 $res .= '<form id="searchBox" action="'.util_make_uri('/search/').'" method="get">
146 SEARCH__PARAMETER_GROUP_ID => $group_id,
147 SEARCH__PARAMETER_ARTIFACT_ID => $atid,
148 SEARCH__PARAMETER_FORUM_ID => $forum_id,
149 SEARCH__PARAMETER_GROUP_PROJECT_ID => $group_project_id
152 $searchManager =& getSearchManager();
153 $searchManager->setParametersValues($parameters);
154 $searchEngines =& $searchManager->getAvailableSearchEngines();
156 $res .= '<label for="searchBox-words">
157 <select name="type_of_search">';
158 for($i = 0, $max = count($searchEngines); $i < $max; $i++) {
159 $searchEngine =& $searchEngines[$i];
160 $res .= '<option value="' . $searchEngine->getType() . '"'
161 . ( $type_of_search == $searchEngine->getType() ? ' selected="selected"' : '' )
162 . '>' . $searchEngine->getLabel($parameters) . '</option>' . "\n";
164 $res .= '</select></label>';
166 $parameters = $searchManager->getParameters();
167 foreach($parameters AS $name => $value) {
168 $res .= '<input type="hidden" value="'.$value.'" name="'.$name.'" />' . "\n";
170 $res .= '<input type="text" size="12" id="searchBox-words" name="words" value="'
171 . $defaultWords . '" />' . "\n";
172 $res .= '<input type="submit" name="Search" value="'._('Search').'" />' . "\n";
174 if (isset($group_id) && $group_id) {
175 $res .= util_make_link('/search/advanced_search.php?group_id=' .
176 $group_id, _('Advanced search'));
185 * Get an array of the user links (Login/Logout/My Account/Register) with the following structure:
186 * $result['titles']: list of the titles. $result['urls']: list of the urls.
188 function getUserLinks() {
190 if (session_loggedin()) {
191 $u =& user_get_object(user_getid());
192 $res['titles'][] = sprintf("%s (%s)", _('Log Out'), $u->getRealName());
193 $res['urls'][] = util_make_uri('/account/logout.php');
195 $res['titles'][] = _('My Account');
196 $res['urls'][] = util_make_uri('/account/');
198 $url = '/account/login.php';
199 if(getStringFromServer('REQUEST_METHOD') != 'POST') {
200 $url .= '?return_to=';
201 $url .= urlencode(getStringFromServer('REQUEST_URI'));
203 $res['titles'][] = _('Log In');
204 $res['urls'][] = util_make_url($url);
206 if (!forge_get_config ('user_registration_restricted')) {
207 $res['titles'][] = _('New Account');
208 $res['urls'][] = util_make_url('/account/register.php');
215 * Get an array of the menu of the site with the following structure:
216 * $result['titles']: list of titles of the links.
217 * $result['urls']: list of urls.
218 * $result['tooltips']: list of tooltips (html title).
219 * $result['selected']: number of the selected menu entry.
221 function getSiteMenu() {
222 $request_uri = getStringFromServer('REQUEST_URI');
225 $menu['titles'] = array();
226 $menu['urls'] = array();
227 $menu['tooltips'] = array();
231 $menu['titles'][] = _('Home');
232 $menu['urls'][] = util_make_uri('/');
233 $menu['tooltips'][] = _('Main Page');
236 $menu['titles'][] = _('My Page');
237 $menu['urls'][] = util_make_uri('/my/');
238 $menu['tooltips'][] = _('Your Page, widgets selected by you to follow your items.');
239 if (strstr($request_uri, util_make_uri('/my/'))
240 || strstr($request_uri, util_make_uri('/account/'))
241 || strstr($request_uri, util_make_uri('/register/'))
242 || strstr($request_uri, util_make_uri('/themes/'))
245 $selected = count($menu['urls'])-1;
248 if (forge_get_config('use_trove') || forge_get_config('use_project_tags') || forge_get_config('use_project_full_list')) {
249 $menu['titles'][] = _('Projects');
250 $menu['urls'][] = util_make_uri('/softwaremap/');
251 $menu['tooltips'][] = _('Map of projects, by categories or types.');
252 if (strstr($request_uri, util_make_uri('/softwaremap/'))) {
253 $selected = count($menu['urls'])-1;
257 if (forge_get_config('use_snippet')) {
258 $menu['titles'][] = _('Code Snippets');
259 $menu['urls'][] = util_make_uri('/snippet/');
260 $menu['tooltips'][] = _('Tooling library. Small coding tips.');
261 if (strstr($request_uri, util_make_uri('/snippet/'))) {
262 $selected = count($menu['urls'])-1;
266 if (forge_get_config('use_people')) {
267 $menu['titles'][] = _('Project Openings');
268 $menu['urls'][] = util_make_uri('/people/');
269 $menu['tooltips'][] = _('Hiring Market Place.');
270 if (strstr($request_uri, util_make_uri('/people/'))) {
271 $selected=count($menu['urls'])-1;
276 $before = count($menu['urls']);
277 $plugin_urls = array();
278 $hookParams['DIRS'] = &$menu['urls'];
279 $hookParams['TITLES'] = &$menu['titles'];
280 $hookParams['TOOLTIPS'] = &$menu['tooltips'];
281 plugin_hook("outermenu", $hookParams);
283 // try to find selected entry
284 for ($j = $before; $j < count($plugin_urls); $j++) {
285 $url = $menu['urls'][$j];
286 if (strstr($request_uri, parse_url ($url, PHP_URL_PATH))) {
292 // Admin and Reporting
293 if (forge_check_global_perm('forge_admin')) {
294 $user_is_super = true;
295 $menu['titles'][] = _('Site Admin');
296 $menu['urls'][] = util_make_url('/admin/');
297 $menu['tooltips'][] = _('Administration Submenu to handle global configuration, users & projects.');
298 if (strstr($request_uri, util_make_uri('/admin/'))) {
299 $selected = count($menu['urls'])-1;
302 if (forge_check_global_perm ('forge_stats', 'read')) {
303 $menu['titles'][] = _('Reporting');
304 $menu['urls'][] = util_make_uri('/reporting/');
305 $menu['tooltips'][] = _('Statistics about visits, users & projects in time frame.');
306 if (strstr($request_uri, util_make_uri('/reporting/'))) {
307 $selected = count($menu['urls'])-1;
312 if (isset($GLOBALS['group_id'])) {
313 // get group info using the common result set
314 $project =& group_get_object($GLOBALS['group_id']);
315 if ($project && is_object($project)) {
316 if ($project->isError()) {
317 } elseif (!$project->isProject()) {
319 $menu['titles'][] = $project->getPublicName();
320 $menu['tooltips'][] = _('Project home page, widgets selected to follow specific items.');
321 if (isset ($GLOBALS['sys_noforcetype']) && $GLOBALS['sys_noforcetype']) {
322 $menu['urls'][]=util_make_uri('/project/?group_id') .$project->getId();
324 $menu['urls'][]=util_make_uri('/projects/') .$project->getUnixName().'/';
326 $selected=count($menu['urls'])-1;
331 $menu['selected'] = $selected;
337 * Get a reference to an array of the projects menu for the project with the id $group_id with the following structure:
338 * $result['starturl']: URL of the projects starting page;
339 * $result['name']: public name of the project;
340 * $result['titles']: list of titles of the menu entries;
341 * $result['tooltips']: list of tooltips (html title) of the menu entries;
342 * $result['urls']: list of urls of the menu entries;
343 * $result['adminurls']: list of urls to the admin pages of the menu entries.
344 * If the user has no admin permissions, the correpsonding adminurl is false.
345 * $result['selected']: number of the menu entry that is currently selected.
347 function getProjectMenu($group_id, $toptab = "") {
348 // rebuild menu if it has never been built before, or
349 // if the toptab was set differently
350 if (!isset($this->project_menu_data[$group_id])
352 || ($toptab != $this->project_menu_data[$group_id]['last_toptab'])) {
353 // get the group and permission objects
354 $group = group_get_object($group_id);
355 if (!$group || !is_object($group)) {
358 if ($group->isError()) {
359 //wasn't found or some other problem
362 if (!$group->isProject()) {
368 $menu =& $this->project_menu_data[$group_id];
369 $menu['titles'] = array();
370 $menu['tooltips'] = array();
371 $menu['urls'] = array();
372 $menu['adminurls'] = array();
374 $menu['name'] = $group->getPublicName();
377 $menu['titles'][] = _('Summary');
378 $menu['tooltips'][] = _('Project Homepage. Widgets oriented');
379 if (isset($GLOBALS['sys_noforcetype']) && $GLOBALS['sys_noforcetype']) {
380 $url = util_make_uri('/project/?group_id=' . $group_id);
382 $url = util_make_uri('/projects/' . $group->getUnixName() .'/');
384 $menu['urls'][] = $url;
385 $menu['adminurls'][] = false;
386 if ($toptab == "home") {
387 $selected = (count($menu['urls'])-1);
390 // setting these allows to change the initial project page
391 $menu['starturl'] = $url;
394 if (forge_check_perm ('project_admin', $group_id)) {
395 $menu['titles'][] = _('Admin');
396 $menu['tooltips'][] = _('Project Administration.');
397 $menu['urls'][] = util_make_uri('/project/admin/?group_id=' . $group_id);
398 $menu['adminurls'][] = false;
399 if ($toptab == "admin") {
400 $selected = (count($menu['urls'])-1);
405 // check for use_home_tab?
406 $TABS_DIRS[]='http://'. $this->getHomePage();
407 $TABS_TITLES[]=_('Home Page');
410 // Project Activity tab
411 $menu['titles'][] = _('Activity');
412 $menu['tooltips'][] = _('Last activities per category.');
413 $menu['urls'][] = util_make_uri('/activity/?group_id=' . $group_id);
414 $menu['adminurls'][] = false;
415 if ($toptab == "activity") {
416 $selected = (count($menu['urls'])-1);
420 if ($group->usesForum()) {
421 $menu['titles'][] = _('Forums');
422 $menu['tooltips'][] = _('Tech & help forums.');
423 $menu['urls'][] = util_make_uri('/forum/?group_id=' . $group_id);
424 if (forge_check_perm ('forum_admin', $group_id)) {
425 $menu['adminurls'][] = util_make_url('/forum/admin/?group_id='.$group_id);
427 $menu['adminurls'][] = false;
429 if ($toptab == "forums") {
430 $selected = (count($menu['urls'])-1);
435 if ($group->usesTracker()) {
436 $menu['titles'][] = _('Tracker');
437 $menu['tooltips'][] = _('Issues, tickets, bugs.');
438 $menu['urls'][] = util_make_uri('/tracker/?group_id=' . $group_id);
439 if (forge_check_perm ('tracker_admin', $group_id)) {
440 $menu['adminurls'][] = util_make_url('/tracker/admin/?group_id='.$group_id);
442 $menu['adminurls'][] = false;
444 if ($toptab == "tracker" ||
446 $toptab == "support" ||
447 $toptab == "patch") {
448 $selected = (count($menu['urls'])-1);
453 if ($group->usesMail()) {
454 $menu['titles'][] = _('Lists');
455 $menu['tooltips'][] = _('Mailing Lists.');
456 $menu['urls'][] = util_make_uri('/mail/?group_id=' . $group_id);
457 if (forge_check_perm ('project_admin', $group_id)) {
458 $menu['adminurls'][] = util_make_url('/mail/admin/?group_id='.$group_id);
460 $menu['adminurls'][] = false;
462 if ($toptab == "mail") {
463 $selected = (count($menu['urls'])-1);
467 // Project/Task Manager
468 if ($group->usesPm()) {
469 $menu['titles'][] = _('Tasks');
470 $menu['tooltips'][] = _('Project Management.');
471 $menu['urls'][] = util_make_uri('/pm/?group_id=' . $group_id);
472 if (forge_check_perm ('pm_admin', $group_id)) {
473 $menu['adminurls'][] = util_make_uri('/pm/admin/?group_id='.$group_id);
475 $menu['adminurls'][] = false;
477 if ($toptab == "pm") {
478 $selected = (count($menu['urls'])-1);
483 if ($group->usesDocman()) {
484 $menu['titles'][] = _('Docs');
485 $menu['tooltips'][] = _('Document Management.');
486 $menu['urls'][] = util_make_uri('/docman/?group_id=' . $group_id);
487 if (forge_check_perm ('docman', $group_id, 'approve')) {
488 $menu['adminurls'][] = util_make_uri('/docman/?group_id='.$group_id.'&view=admin');
490 $menu['adminurls'][] = false;
492 if ($toptab == "docman") {
493 $selected = (count($menu['urls'])-1);
498 if ($group->usesSurvey()) {
499 $menu['titles'][] = _('Surveys');
500 $menu['tooltips'][] = _('Online surveys, project needs your point of view.');
501 $menu['urls'][] = util_make_uri('/survey/?group_id=' . $group_id);
502 if (forge_check_perm ('project_admin', $group_id)) {
503 $menu['adminurls'][] = util_make_uri('/survey/admin/?group_id='.$group_id);
505 $menu['adminurls'][] = false;
507 if ($toptab == "surveys") {
508 $selected = (count($menu['urls'])-1);
513 if ($group->usesNews()) {
514 $menu['titles'][] = _('News');
515 $menu['tooltips'][] = _('Flash head line from the project.');
516 $menu['urls'][] = util_make_uri('/news/?group_id=' . $group_id);
517 if (forge_check_perm ('project_admin', $group_id)) {
518 $menu['adminurls'][] = util_make_uri('/news/admin/?group_id='.$group_id);
520 $menu['adminurls'][] = false;
522 if ($toptab == "news") {
523 $selected = (count($menu['urls'])-1);
528 if ($group->usesSCM()) {
529 $menu['titles'][] = _('SCM');
530 $menu['tooltips'][] = _('Source Content Management, peer-review and source discovery.');
531 $menu['urls'][] = util_make_uri('/scm/?group_id=' . $group_id);
533 if (forge_check_perm ('project_admin', $group_id)) {
534 $menu['adminurls'][] = util_make_uri('/scm/admin/?group_id='.$group_id);
536 $menu['adminurls'][] = false;
538 if ($toptab == "scm") {
539 $selected = (count($menu['urls'])-1);
543 // groupmenu_after_scm hook
544 $hookParams = array();
545 $hookParams['group_id'] = $group_id ;
546 $hookParams['DIRS'] =& $menu['urls'];
547 $hookParams['TITLES'] =& $menu['titles'];
548 $hookParams['TOOLTIPS'] =& $menu['tooltips'];
549 $hookParams['toptab'] =& $toptab;
550 $hookParams['selected'] =& $selected;
551 plugin_hook ("groupmenu_scm", $hookParams);
554 for ($i = 0; $i < count($menu['urls']) - count($menu['adminurls']); $i++) {
555 $menu['adminurls'][] = false;
559 if ($group->usesFRS()) {
560 $menu['titles'][] = _('Files');
561 $menu['tooltips'][] = _('All published files organized per version.');
562 $menu['urls'][] = util_make_uri('/frs/?group_id=' . $group_id);
563 if (forge_check_perm ('frs', $group_id, 'write')) {
564 $menu['adminurls'][] = util_make_uri('/frs/admin/?group_id='.$group_id);
566 $menu['adminurls'][] = false;
568 if ($toptab == "frs") {
569 $selected = (count($menu['urls'])-1);
574 $hookParams = array();
575 $hookParams['group'] = $group_id;
576 $hookParams['DIRS'] =& $menu['urls'];
577 $hookParams['ADMIN'] =& $menu['adminurls'];
578 $hookParams['TITLES'] =& $menu['titles'];
579 $hookParams['TOOLTIPS'] =& $menu['tooltips'];
580 $hookParams['toptab'] =& $toptab;
581 $hookParams['selected'] =& $selected;
582 plugin_hook("groupmenu", $hookParams);
585 for ($i = 0; $i < count($menu['urls']) - count($menu['adminurls']); $i++) {
586 $menu['adminurls'][] = false;
589 // store selected menu item (if any)
590 $menu['selected'] = $selected;
592 $menu['last_toptab'] = $toptab;
595 return $this->project_menu_data[$group_id];
599 * Create the HTML code for the banner "Powered By
600 * FusionForge". If $asHTML is set to false, it will return an
601 * array with the following structure: $result['url']: URL for
602 * the link on the banner; $result['image']: URL of the banner
603 * image; $result['title']: HTML code that outputs the banner;
604 * $result['html']: HTML code that creates the banner and the link.
606 function getPoweredBy($asHTML=true) {
607 $res['url'] = 'http://fusionforge.org/';
608 $res['image'] = util_make_uri('/images/pow-fusionforge.png');
609 $res['title'] = '<img src="'
611 . '" alt="Powered By FusionForge" border="0" />';
612 $res['html'] = util_make_link($res['url'], $res['title'], array(), true);
620 /** Create the HTML code for the "Show Source" link if
621 * forge_get_config('show_source') is set, otherwise "". If $asHTML is set
622 * to false, it returns NULL when forge_get_config('show_source') is not
623 * set, otherwise an array with the following structure:
624 * $result['url']: URL of the link to the source code viewer;
625 * $result['title']: Title of the link.
627 function getShowSource($asHTML=true) {
628 if (forge_get_config('show_source')) {
629 $res['url'] = util_make_url('/source.php?file='.getStringFromServer('SCRIPT_NAME'));
630 $res['title'] = _('Show source');
632 return ($asHTML ? "" : NULL);
637 return util_make_link($res['url'], $res['title'],
638 array('class' => 'showsource'),
646 // c-file-style: "bsd"