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 .= '<select name="type_of_search">';
157 for($i = 0, $max = count($searchEngines); $i < $max; $i++) {
158 $searchEngine =& $searchEngines[$i];
159 $res .= '<option value="' . $searchEngine->getType() . '"'
160 . ( $type_of_search == $searchEngine->getType() ? ' selected="selected"' : '' )
161 . '>' . $searchEngine->getLabel($parameters) . '</option>' . "\n";
165 $parameters = $searchManager->getParameters();
166 foreach($parameters AS $name => $value) {
167 $res .= '<input type="hidden" value="'.$value.'" name="'.$name.'" />' . "\n";
169 $res .= '<input type="text" size="12" id="searchBox-words" name="words" value="'
170 . $defaultWords . '" />' . "\n";
171 $res .= '<input type="submit" name="Search" value="'._('Search').'" />' . "\n";
173 if (isset($group_id) && $group_id) {
174 $res .= util_make_link('/search/advanced_search.php?group_id=' .
175 $group_id, _('Advanced search'));
184 * Get an array of the user links (Login/Logout/My Account/Register) with the following structure:
185 * $result['titles']: list of the titles. $result['urls']: list of the urls.
187 function getUserLinks() {
189 if (session_loggedin()) {
190 $u =& user_get_object(user_getid());
191 $res['titles'][] = sprintf("%s (%s)", _('Log Out'), $u->getRealName());
192 $res['urls'][] = util_make_uri('/account/logout.php');
194 $res['titles'][] = _('My Account');
195 $res['urls'][] = util_make_uri('/account/');
197 $url = '/account/login.php';
198 if(getStringFromServer('REQUEST_METHOD') != 'POST') {
199 $url .= '?return_to=';
200 $url .= urlencode(getStringFromServer('REQUEST_URI'));
202 $res['titles'][] = _('Log In');
203 $res['urls'][] = util_make_uri($url);
205 if (!forge_get_config ('user_registration_restricted')) {
206 $res['titles'][] = _('New Account');
207 $res['urls'][] = util_make_uri('/account/register.php');
214 * Get an array of the menu of the site with the following structure:
215 * $result['titles']: list of titles of the links.
216 * $result['urls']: list of urls.
217 * $result['tooltips']: list of tooltips (html title).
218 * $result['selected']: number of the selected menu entry.
220 function getSiteMenu() {
221 $request_uri = getStringFromServer('REQUEST_URI');
224 $menu['titles'] = array();
225 $menu['urls'] = array();
226 $menu['tooltips'] = array();
230 $menu['titles'][] = _('Home');
231 $menu['urls'][] = util_make_uri('/');
232 $menu['tooltips'][] = _('Main Page');
235 $menu['titles'][] = _('My Page');
236 $menu['urls'][] = util_make_uri('/my/');
237 $menu['tooltips'][] = _('Your Page, widgets selected by you to follow your items.');
238 if (strstr($request_uri, util_make_uri('/my/'))
239 || strstr($request_uri, util_make_uri('/account/'))
240 || strstr($request_uri, util_make_uri('/register/'))
241 || strstr($request_uri, util_make_uri('/themes/'))
244 $selected = count($menu['urls'])-1;
247 if (forge_get_config('use_trove') || forge_get_config('use_project_tags') || forge_get_config('use_project_full_list')) {
248 $menu['titles'][] = _('Projects');
249 $menu['urls'][] = util_make_uri('/softwaremap/');
250 $menu['tooltips'][] = _('Map of projects, by categories or types.');
251 if (strstr($request_uri, util_make_uri('/softwaremap/'))) {
252 $selected = count($menu['urls'])-1;
256 if (forge_get_config('use_snippet')) {
257 $menu['titles'][] = _('Code Snippets');
258 $menu['urls'][] = util_make_uri('/snippet/');
259 $menu['tooltips'][] = _('Tooling library. Small coding tips.');
260 if (strstr($request_uri, util_make_uri('/snippet/'))) {
261 $selected = count($menu['urls'])-1;
265 if (forge_get_config('use_people')) {
266 $menu['titles'][] = _('Project Openings');
267 $menu['urls'][] = util_make_uri('/people/');
268 $menu['tooltips'][] = _('Hiring Market Place.');
269 if (strstr($request_uri, util_make_uri('/people/'))) {
270 $selected=count($menu['urls'])-1;
275 $before = count($menu['urls']);
276 $plugin_urls = array();
277 $hookParams['DIRS'] = &$menu['urls'];
278 $hookParams['ADMIN'] =& $menu['adminurls'];
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_uri('/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 (is_int($project) && $project == 0) {
316 if (preg_match('/root=/',$request_uri)) {
317 $project_name = preg_replace('/.*?root=/', '', $request_uri);
318 $project =& group_get_object_by_name($project_name);
321 if ($project && is_object($project)) {
322 if ($project->isError()) {
323 } elseif (!$project->isProject()) {
325 $menu['titles'][] = $project->getPublicName();
326 $menu['tooltips'][] = _('Project home page, widgets selected to follow specific items.');
327 if (isset ($GLOBALS['sys_noforcetype']) && $GLOBALS['sys_noforcetype']) {
328 $menu['urls'][]=util_make_uri('/project/?group_id') .$project->getId();
330 $menu['urls'][]=util_make_uri('/projects/') .$project->getUnixName().'/';
332 $selected=count($menu['urls'])-1;
337 $menu['selected'] = $selected;
343 * Get a reference to an array of the projects menu for the project with the id $group_id with the following structure:
344 * $result['starturl']: URL of the projects starting page;
345 * $result['name']: public name of the project;
346 * $result['titles']: list of titles of the menu entries;
347 * $result['tooltips']: list of tooltips (html title) of the menu entries;
348 * $result['urls']: list of urls of the menu entries;
349 * $result['adminurls']: list of urls to the admin pages of the menu entries.
350 * If the user has no admin permissions, the correpsonding adminurl is false.
351 * $result['selected']: number of the menu entry that is currently selected.
353 function getProjectMenu($group_id, $toptab = "") {
354 // rebuild menu if it has never been built before, or
355 // if the toptab was set differently
356 if (!isset($this->project_menu_data[$group_id])
358 || ($toptab != $this->project_menu_data[$group_id]['last_toptab'])) {
359 // get the group and permission objects
360 $group = group_get_object($group_id);
361 if (!$group || !is_object($group)) {
364 if ($group->isError()) {
365 //wasn't found or some other problem
368 if (!$group->isProject()) {
374 $menu =& $this->project_menu_data[$group_id];
375 $menu['titles'] = array();
376 $menu['tooltips'] = array();
377 $menu['urls'] = array();
378 $menu['adminurls'] = array();
380 $menu['name'] = $group->getPublicName();
383 $menu['titles'][] = _('Summary');
384 $menu['tooltips'][] = _('Project Homepage. Widgets oriented');
385 if (isset($GLOBALS['sys_noforcetype']) && $GLOBALS['sys_noforcetype']) {
386 $url = util_make_uri('/project/?group_id=' . $group_id);
388 $url = util_make_uri('/projects/' . $group->getUnixName() .'/');
390 $menu['urls'][] = $url;
391 $menu['adminurls'][] = false;
392 if ($toptab == "home") {
393 $selected = (count($menu['urls'])-1);
396 // setting these allows to change the initial project page
397 $menu['starturl'] = $url;
400 if (forge_check_perm ('project_admin', $group_id)) {
401 $menu['titles'][] = _('Admin');
402 $menu['tooltips'][] = _('Project Administration.');
403 $menu['urls'][] = util_make_uri('/project/admin/?group_id=' . $group_id);
404 $menu['adminurls'][] = false;
405 if ($toptab == "admin") {
406 $selected = (count($menu['urls'])-1);
411 // check for use_home_tab?
412 $TABS_DIRS[]='http://'. $this->getHomePage();
413 $TABS_TITLES[]=_('Home Page');
416 // Project Activity tab
417 $menu['titles'][] = _('Activity');
418 $menu['tooltips'][] = _('Last activities per category.');
419 $menu['urls'][] = util_make_uri('/activity/?group_id=' . $group_id);
420 $menu['adminurls'][] = false;
421 if ($toptab == "activity") {
422 $selected = (count($menu['urls'])-1);
426 if ($group->usesForum()) {
427 $menu['titles'][] = _('Forums');
428 $menu['tooltips'][] = _('Tech & help forums.');
429 $menu['urls'][] = util_make_uri('/forum/?group_id=' . $group_id);
430 if (forge_check_perm ('forum_admin', $group_id)) {
431 $menu['adminurls'][] = util_make_uri('/forum/admin/?group_id='.$group_id);
433 $menu['adminurls'][] = false;
435 if ($toptab == "forums") {
436 $selected = (count($menu['urls'])-1);
441 if ($group->usesTracker()) {
442 $menu['titles'][] = _('Tracker');
443 $menu['tooltips'][] = _('Issues, tickets, bugs.');
444 $menu['urls'][] = util_make_uri('/tracker/?group_id=' . $group_id);
445 if (forge_check_perm ('tracker_admin', $group_id)) {
446 $menu['adminurls'][] = util_make_uri('/tracker/admin/?group_id='.$group_id);
448 $menu['adminurls'][] = false;
450 if ($toptab == "tracker" ||
452 $toptab == "support" ||
453 $toptab == "patch") {
454 $selected = (count($menu['urls'])-1);
459 if ($group->usesMail()) {
460 $menu['titles'][] = _('Lists');
461 $menu['tooltips'][] = _('Mailing Lists.');
462 $menu['urls'][] = util_make_uri('/mail/?group_id=' . $group_id);
463 if (forge_check_perm ('project_admin', $group_id)) {
464 $menu['adminurls'][] = util_make_uri('/mail/admin/?group_id='.$group_id);
466 $menu['adminurls'][] = false;
468 if ($toptab == "mail") {
469 $selected = (count($menu['urls'])-1);
473 // Project/Task Manager
474 if ($group->usesPm()) {
475 $menu['titles'][] = _('Tasks');
476 $menu['tooltips'][] = _('Project Management.');
477 $menu['urls'][] = util_make_uri('/pm/?group_id=' . $group_id);
478 if (forge_check_perm ('pm_admin', $group_id)) {
479 $menu['adminurls'][] = util_make_uri('/pm/admin/?group_id='.$group_id);
481 $menu['adminurls'][] = false;
483 if ($toptab == "pm") {
484 $selected = (count($menu['urls'])-1);
489 if ($group->usesDocman()) {
490 $menu['titles'][] = _('Docs');
491 $menu['tooltips'][] = _('Document Management.');
492 $menu['urls'][] = util_make_uri('/docman/?group_id=' . $group_id);
493 if (forge_check_perm ('docman', $group_id, 'approve')) {
494 $menu['adminurls'][] = util_make_uri('/docman/?group_id='.$group_id.'&view=admin');
496 $menu['adminurls'][] = false;
498 if ($toptab == "docman") {
499 $selected = (count($menu['urls'])-1);
504 if ($group->usesSurvey()) {
505 $menu['titles'][] = _('Surveys');
506 $menu['tooltips'][] = _('Online surveys, project needs your point of view.');
507 $menu['urls'][] = util_make_uri('/survey/?group_id=' . $group_id);
508 if (forge_check_perm ('project_admin', $group_id)) {
509 $menu['adminurls'][] = util_make_uri('/survey/admin/?group_id='.$group_id);
511 $menu['adminurls'][] = false;
513 if ($toptab == "surveys") {
514 $selected = (count($menu['urls'])-1);
519 if ($group->usesNews()) {
520 $menu['titles'][] = _('News');
521 $menu['tooltips'][] = _('Flash head line from the project.');
522 $menu['urls'][] = util_make_uri('/news/?group_id=' . $group_id);
523 if (forge_check_perm ('project_admin', $group_id)) {
524 $menu['adminurls'][] = util_make_uri('/news/admin/?group_id='.$group_id);
526 $menu['adminurls'][] = false;
528 if ($toptab == "news") {
529 $selected = (count($menu['urls'])-1);
534 if ($group->usesSCM()) {
535 $menu['titles'][] = _('SCM');
536 $menu['tooltips'][] = _('Source Content Management, peer-review and source discovery.');
537 $menu['urls'][] = util_make_uri('/scm/?group_id=' . $group_id);
539 if (forge_check_perm ('project_admin', $group_id)) {
540 $menu['adminurls'][] = util_make_uri('/scm/admin/?group_id='.$group_id);
542 $menu['adminurls'][] = false;
544 if ($toptab == "scm") {
545 $selected = (count($menu['urls'])-1);
549 // groupmenu_after_scm hook
550 $hookParams = array();
551 $hookParams['group_id'] = $group_id ;
552 $hookParams['DIRS'] =& $menu['urls'];
553 $hookParams['ADMIN'] =& $menu['adminurls'];
554 $hookParams['TITLES'] =& $menu['titles'];
555 $hookParams['TOOLTIPS'] =& $menu['tooltips'];
556 $hookParams['toptab'] =& $toptab;
557 $hookParams['selected'] =& $selected;
558 plugin_hook ("groupmenu_scm", $hookParams);
561 for ($i = 0; $i < count($menu['urls']) - count($menu['adminurls']); $i++) {
562 $menu['adminurls'][] = false;
566 if ($group->usesFRS()) {
567 $menu['titles'][] = _('Files');
568 $menu['tooltips'][] = _('All published files organized per version.');
569 $menu['urls'][] = util_make_uri('/frs/?group_id=' . $group_id);
570 if (forge_check_perm ('frs', $group_id, 'write')) {
571 $menu['adminurls'][] = util_make_uri('/frs/admin/?group_id='.$group_id);
573 $menu['adminurls'][] = false;
575 if ($toptab == "frs") {
576 $selected = (count($menu['urls'])-1);
581 $hookParams = array();
582 $hookParams['group'] = $group_id;
583 $hookParams['DIRS'] =& $menu['urls'];
584 $hookParams['ADMIN'] =& $menu['adminurls'];
585 $hookParams['TITLES'] =& $menu['titles'];
586 $hookParams['TOOLTIPS'] =& $menu['tooltips'];
587 $hookParams['toptab'] =& $toptab;
588 $hookParams['selected'] =& $selected;
589 plugin_hook("groupmenu", $hookParams);
592 for ($i = 0; $i < count($menu['urls']) - count($menu['adminurls']); $i++) {
593 $menu['adminurls'][] = false;
596 // store selected menu item (if any)
597 $menu['selected'] = $selected;
599 $menu['last_toptab'] = $toptab;
602 return $this->project_menu_data[$group_id];
606 * Create the HTML code for the banner "Powered By
607 * FusionForge". If $asHTML is set to false, it will return an
608 * array with the following structure: $result['url']: URL for
609 * the link on the banner; $result['image']: URL of the banner
610 * image; $result['title']: HTML code that outputs the banner;
611 * $result['html']: HTML code that creates the banner and the link.
613 function getPoweredBy($asHTML=true) {
614 $res['url'] = 'http://fusionforge.org/';
615 $res['image'] = util_make_uri('/images/pow-fusionforge.png');
616 $res['title'] = '<img src="'
618 . '" alt="Powered By FusionForge" />';
619 $res['html'] = util_make_link($res['url'], $res['title'], array(), true);
627 /** Create the HTML code for the "Show Source" link if
628 * forge_get_config('show_source') is set, otherwise "". If $asHTML is set
629 * to false, it returns NULL when forge_get_config('show_source') is not
630 * set, otherwise an array with the following structure:
631 * $result['url']: URL of the link to the source code viewer;
632 * $result['title']: Title of the link.
634 function getShowSource($asHTML=true) {
635 if (forge_get_config('show_source')) {
636 $res['url'] = util_make_uri('/source.php?file='.getStringFromServer('SCRIPT_NAME'));
637 $res['title'] = _('Show source');
639 return ($asHTML ? "" : NULL);
644 return util_make_link($res['url'], $res['title'],
645 array('class' => 'showsource'),
653 // c-file-style: "bsd"