mirror of
https://github.com/EGroupware/egroupware.git
synced 2024-11-25 09:23:28 +01:00
* Stylite template got an application header again
and other bugfixes for the tab restore: commits r1436-44
This commit is contained in:
parent
4a17a747f0
commit
095567423d
@ -489,3 +489,18 @@ body {
|
||||
|
||||
.egw_fw_content_browser_iframe {
|
||||
}
|
||||
|
||||
.egw_fw_ui_app_header_container {
|
||||
border-width: 0px 1px 0px 1px;
|
||||
border-style: solid;
|
||||
border-color: #D5DDE6;
|
||||
}
|
||||
|
||||
.egw_fw_ui_app_header {
|
||||
border-width: 0px 0px 1px 0px;
|
||||
border-style: solid;
|
||||
border-color: #D5DDE6;
|
||||
padding: 5px 2px 4px 15px;
|
||||
font-size: 9pt;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
@ -142,6 +142,11 @@ class jdots_framework extends egw_framework
|
||||
{
|
||||
return $matches[1];
|
||||
}
|
||||
if (strlen($GLOBALS['egw_info']['server']['webserver_url']) > 1)
|
||||
{
|
||||
list(,$url) = explode(parse_url($GLOBALS['egw_info']['server']['webserver_url'],PHP_URL_PATH),
|
||||
parse_url($url,PHP_URL_PATH),2);
|
||||
}
|
||||
if (preg_match('/\/([^\/]+)\/([^\/]+\.php)?(\?|\/|$)/',$url,$matches))
|
||||
{
|
||||
return $matches[1];
|
||||
@ -273,7 +278,7 @@ class jdots_framework extends egw_framework
|
||||
if (typeof window.parent.framework != "undefined")
|
||||
{
|
||||
var app = window.parent.framework.getApplicationByName("'.$app.'");
|
||||
window.parent.framework.setWebsiteTitle(app,"'.htmlspecialchars($vars['website_title']).'");
|
||||
window.parent.framework.setWebsiteTitle(app,"'.htmlspecialchars($vars['website_title']).'","'.$app_header.'");
|
||||
}';
|
||||
|
||||
//Register the global key press handler
|
||||
@ -723,8 +728,10 @@ class jdots_framework extends egw_framework
|
||||
|
||||
/**
|
||||
* Stores the user defined sorting of the applications inside the preferences
|
||||
*
|
||||
* @param array $apps
|
||||
*/
|
||||
public function ajax_appsort($apps)
|
||||
public function ajax_appsort(array $apps)
|
||||
{
|
||||
$order = array();
|
||||
$i = 0;
|
||||
@ -749,6 +756,10 @@ class jdots_framework extends egw_framework
|
||||
/**
|
||||
* Prepare an array with apps used to render the navbar
|
||||
*
|
||||
* @param string $url contains the current url on the client side. It is used to
|
||||
* determine whether the default app/home should be opened on the client
|
||||
* or whether a specific application-url has been given.
|
||||
*
|
||||
* @return array of array(
|
||||
* 'name' => app / directory name
|
||||
* 'title' => translated application title
|
||||
@ -757,9 +768,12 @@ class jdots_framework extends egw_framework
|
||||
* 'icon_app' => application of icon
|
||||
* 'icon_hover' => hover-icon, if used by template
|
||||
* 'target'=> ' target="..."' attribute fragment to open url in target, popup or ''
|
||||
* 'opened' => unset or false if the tab should not be opened, otherwise the numeric position in the tab list
|
||||
* 'active' => true if this tab should be the active one when it is restored, otherwise unset or false
|
||||
* 'openOnce' => unset or the url which will be opened when the tab is restored
|
||||
* )
|
||||
*/
|
||||
public function ajax_navbar_apps()
|
||||
public function ajax_navbar_apps($url)
|
||||
{
|
||||
$apps = parent::_get_navbar_apps();
|
||||
|
||||
@ -781,13 +795,43 @@ class jdots_framework extends egw_framework
|
||||
unset($apps['sitemgr-link']);
|
||||
}
|
||||
|
||||
// check if user called a specific url --> open it as active tab
|
||||
$last_direct_url =& egw_cache::getSession(__CLASS__, 'last_direct_url');
|
||||
if ($url !== $last_direct_url)
|
||||
{
|
||||
$active_tab = $url_tab = self::app_from_url($url);
|
||||
$last_direct_url = $url;
|
||||
}
|
||||
if ($active_tab)
|
||||
{
|
||||
$apps[$active_tab]['openOnce'] = str_replace('&cd=yes','',$url);
|
||||
$store_prefs = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
$active_tab = $GLOBALS['egw_info']['user']['preferences']['common']['active_tab'];
|
||||
}
|
||||
$open_tabs = explode(',',$GLOBALS['egw_info']['user']['preferences']['common']['open_tabs']);
|
||||
if (!in_array($active_tab,$open_tabs))
|
||||
{
|
||||
$open_tabs[] = $active_tab;
|
||||
$store_prefs = true;
|
||||
}
|
||||
if ($store_prefs)
|
||||
{
|
||||
$GLOBALS['egw']->preferences->read_repository();
|
||||
$GLOBALS['egw']->preferences->change('common', 'open_tabs', implode(',',$open_tabs));
|
||||
$GLOBALS['egw']->preferences->change('common', 'active_tab', $active_tab);
|
||||
$GLOBALS['egw']->preferences->save_repository(true);
|
||||
}
|
||||
//error_log(__METHOD__."('$url') url_tab='$url_tab', active_tab=$active_tab, open_tabs=".array2string($open_tabs));
|
||||
// Restore Tabs
|
||||
foreach(explode(',',$GLOBALS['egw_info']['user']['preferences']['common']['open_tabs']) as $n => $app)
|
||||
foreach($open_tabs as $n => $app)
|
||||
{
|
||||
if (isset($apps[$app])) // user might no longer have app rights
|
||||
{
|
||||
$apps[$app]['opened'] = $n;
|
||||
if ($GLOBALS['egw_info']['user']['preferences']['common']['active_tab'] == $app)
|
||||
if ($app == $active_tab)
|
||||
{
|
||||
$apps[$app]['active'] = true;
|
||||
}
|
||||
|
@ -203,10 +203,7 @@ egw_fw.prototype.setActiveApp = function(_app)
|
||||
}
|
||||
|
||||
//Set the website title
|
||||
if (_app.website_title)
|
||||
{
|
||||
document.title = _app.website_title;
|
||||
}
|
||||
this.refreshAppTitle();
|
||||
|
||||
//Show the application tab
|
||||
if (_app.tab)
|
||||
@ -390,13 +387,17 @@ egw_fw.prototype.notifyTabChange = function()
|
||||
/**
|
||||
* Checks whether the application already owns a tab and creates one if it doesn't exist
|
||||
*/
|
||||
egw_fw.prototype.createApplicationTab = function(_app)
|
||||
egw_fw.prototype.createApplicationTab = function(_app, _pos)
|
||||
{
|
||||
//Default the pos parameter to -1
|
||||
if (typeof _pos == 'undefined')
|
||||
_pos = -1;
|
||||
|
||||
if (_app.tab == null)
|
||||
{
|
||||
//Create the tab
|
||||
_app.tab = this.tabsUi.addTab(_app.icon, this.tabClickCallback, this.tabCloseClickCallback,
|
||||
_app);
|
||||
_app, _pos);
|
||||
_app.tab.setTitle(_app.displayName);
|
||||
|
||||
//Set the tab closeable if there's more than one tab
|
||||
@ -412,10 +413,14 @@ egw_fw.prototype.createApplicationTab = function(_app)
|
||||
* @param bool _hidden specifies, whether the application should be set active
|
||||
* after opening the tab
|
||||
*/
|
||||
egw_fw.prototype.applicationTabNavigate = function(_app, _url, _useIframe, _hidden)
|
||||
egw_fw.prototype.applicationTabNavigate = function(_app, _url, _useIframe, _hidden, _pos)
|
||||
{
|
||||
//Default the post parameter to -1
|
||||
if (typeof _pos == 'undefined')
|
||||
_pos = -1;
|
||||
|
||||
//Create the tab for that application
|
||||
this.createApplicationTab(_app);
|
||||
this.createApplicationTab(_app, _pos);
|
||||
|
||||
if (typeof _url == 'undefined' || _url == null)
|
||||
_url = _app.indexUrl;
|
||||
@ -442,7 +447,6 @@ egw_fw.prototype.applicationTabNavigate = function(_app, _url, _useIframe, _hidd
|
||||
|
||||
_app.browser.browse(_url, true);//_useIframe);
|
||||
|
||||
//
|
||||
if (typeof _hidden == 'undefined' || !_hidden)
|
||||
{
|
||||
this.setActiveApp(_app);
|
||||
@ -497,8 +501,17 @@ egw_fw.prototype.parseAppFromUrl = function(_url)
|
||||
egw_fw.prototype.loadApplicationsCallback = function(apps)
|
||||
{
|
||||
var defaultApp = null;
|
||||
var restore = [];
|
||||
var activeTabIdx = 0;
|
||||
var restore = new Object;
|
||||
var restore_count = 0;
|
||||
|
||||
var mkRestoreEntry = function(_app, _pos, _url, _active) {
|
||||
return {
|
||||
'app': _app,
|
||||
'position': _pos,
|
||||
'url': _url,
|
||||
'active': _active
|
||||
}
|
||||
}
|
||||
|
||||
//Iterate through the application array returned
|
||||
for (var i = 0; i < apps.length; i++)
|
||||
@ -531,34 +544,62 @@ egw_fw.prototype.loadApplicationsCallback = function(apps)
|
||||
if ((typeof app.opened != 'undefined') && (app.opened !== false))
|
||||
{
|
||||
defaultApp = null;
|
||||
restore[app.opened] = appData;
|
||||
if (app.active)
|
||||
activeTabIdx = app.opened;
|
||||
|
||||
var url = null;
|
||||
if (typeof app.openOnce != 'undefined' && app.openOnce)
|
||||
url = app.openOnce;
|
||||
|
||||
restore[appData.appName] = mkRestoreEntry(appData, app.opened,
|
||||
url, app.active ? 1 : 0);
|
||||
restore_count += 1;
|
||||
}
|
||||
|
||||
this.applications[appData.appName] = appData;
|
||||
}
|
||||
|
||||
// check if a menuaction or app is specified in the url --> display that
|
||||
//Processing of the url or the defaultApp is now deactivated.
|
||||
|
||||
/* // check if a menuaction or app is specified in the url --> display that
|
||||
var _app = this.parseAppFromUrl(window.location.href);
|
||||
if (_app)
|
||||
{
|
||||
_url = window.location.href.replace(/&?cd=yes/,'');
|
||||
this.applicationTabNavigate(_app, _url);
|
||||
}
|
||||
//If this app is already opened, don't change its position. Otherwise
|
||||
//add it to the end of the tab list
|
||||
var appPos = restore_count;
|
||||
if (typeof restore[_app.appName] != 'undefined')
|
||||
appPos = restore[_app.appName].position;
|
||||
|
||||
restore[_app.appName] = mkRestoreEntry(_app, appPos,
|
||||
window.location.href.replace(/&?cd=yes/,''), 2);
|
||||
}*/
|
||||
|
||||
// else display the default application
|
||||
else if (defaultApp)
|
||||
if (defaultApp && restore_count == 0)
|
||||
{
|
||||
this.applicationTabNavigate(defaultApp);
|
||||
restore[defaultApp.appName] = mkRestoreEntry(defaultApp, 0, null, 1);
|
||||
}
|
||||
|
||||
// restore the already opened tabs
|
||||
if (restore.length > 0)
|
||||
{
|
||||
for (var i = 0; i < restore.length; i++)
|
||||
//The last parameter is the so called "hidden" parameter
|
||||
this.applicationTabNavigate(restore[i], null, null, i != activeTabIdx);
|
||||
}
|
||||
//Generate an array with all tabs which shall be restored sorted in by
|
||||
//their active state
|
||||
|
||||
//Fill in the sorted_restore array...
|
||||
var sorted_restore = [];
|
||||
for (appName in restore)
|
||||
sorted_restore[sorted_restore.length] = restore[appName];
|
||||
|
||||
//...and sort it
|
||||
sorted_restore.sort(function (a, b) {
|
||||
return ((a.active < b.active) ? 1 : ((a.active == b.active) ? 0 : -1));
|
||||
});
|
||||
|
||||
//Now actually restore the tabs by passing the application, the url, whether
|
||||
//this is an legacyApp (null triggers the application default), whether the
|
||||
//application is hidden (only the active tab is shown) and its position
|
||||
//in the tab list.
|
||||
for (var i = 0; i < sorted_restore.length; i++)
|
||||
this.applicationTabNavigate(
|
||||
sorted_restore[i].app, sorted_restore[i].url, null, i != 0,
|
||||
sorted_restore[i].position);
|
||||
|
||||
this.scrollAreaUi.update();
|
||||
|
||||
@ -581,7 +622,7 @@ egw_fw.prototype.loadApplications = function(_menuaction)
|
||||
this.tabsUi.clean();
|
||||
|
||||
//Perform an AJAX request loading all available applications
|
||||
var req = new egw_json_request(_menuaction)
|
||||
var req = new egw_json_request(_menuaction, [window.location.href])
|
||||
req.sendRequest(true, this.loadApplicationsCallback, this);
|
||||
}
|
||||
|
||||
@ -714,22 +755,40 @@ egw_fw.prototype.setSidebox = function(_app, _data, _md5)
|
||||
}
|
||||
|
||||
_app.hasSideboxMenuContent = true;
|
||||
_app.sidemenuEntry.parent.open(_app.sidemenuEntry);
|
||||
|
||||
//Only view the sidemenu content if this is really the active application
|
||||
if (_app == _app.parentFw.activeApp)
|
||||
{
|
||||
_app.sidemenuEntry.parent.open(_app.sidemenuEntry);
|
||||
_app.parentFw.scrollAreaUi.update();
|
||||
_app.parentFw.scrollAreaUi.setScrollPos(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the website title of an application
|
||||
* @param object _app the application whose title should be set.
|
||||
* @param string _title title to set
|
||||
*/
|
||||
egw_fw.prototype.setWebsiteTitle = function(_app,_title)
|
||||
egw_fw.prototype.setWebsiteTitle = function(_app, _title, _header)
|
||||
{
|
||||
document.title = _title;
|
||||
if (_app) _app.website_title = _title;
|
||||
if (_app) {
|
||||
_app.website_title = _title;
|
||||
_app.app_header = _header;
|
||||
|
||||
if (_app == this.activeApp)
|
||||
this.refreshAppTitle();
|
||||
}
|
||||
}
|
||||
|
||||
egw_fw.prototype.refreshAppTitle = function()
|
||||
{
|
||||
if (this.activeApp)
|
||||
{
|
||||
this.tabsUi.setAppHeader(this.activeApp.app_header);
|
||||
document.title = this.activeApp.website_title;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -22,6 +22,9 @@ function egw_fw_class_application(_parentFw, _appName, _displayName, _icon,
|
||||
this.legacyApp = _legacyApp;
|
||||
this.hasPrerequisites;
|
||||
|
||||
this.website_title = '';
|
||||
this.app_header = '';
|
||||
|
||||
this.sideboxWidth = _sideboxWidth;
|
||||
|
||||
//Setup a link to the parent framework class
|
||||
|
@ -359,9 +359,10 @@ egw_fw_ui_sidemenu.prototype.clean = function()
|
||||
* @param function(_sender) _callback specifies the function which should be called when the tab title is clicked. The _sender parameter passed is a reference to this egw_fw_ui_tab element.
|
||||
* @param function(_sender) _closeCallback specifies the function which should be called when the tab close button is clicked. The _sender parameter passed is a reference to this egw_fw_ui_tab element.
|
||||
* @param object _tag can be used to attach any user data to the object. Inside egw_fw _tag is used to attach an egw_fw_class_application to each sidemenu entry.
|
||||
* @param int _pos is the position where the tab will be inserted
|
||||
*/
|
||||
function egw_fw_ui_tab(_parent, _contHeaderDiv, _contDiv, _icon, _callback,
|
||||
_closeCallback, _tag)
|
||||
_closeCallback, _tag, _pos)
|
||||
{
|
||||
this.parent = _parent;
|
||||
this.contHeaderDiv = _contHeaderDiv;
|
||||
@ -371,9 +372,11 @@ function egw_fw_ui_tab(_parent, _contHeaderDiv, _contDiv, _icon, _callback,
|
||||
this.closeable = true;
|
||||
this.callback = _callback;
|
||||
this.closeCallback = _closeCallback;
|
||||
this.position = _pos;
|
||||
|
||||
//Create the header div and set its "click" function and "hover" event
|
||||
this.headerDiv = document.createElement("span");
|
||||
this.headerDiv._position = _pos;
|
||||
$(this.headerDiv).addClass("egw_fw_ui_tab_header");
|
||||
|
||||
//Create a new callback object and attach it to the header div
|
||||
@ -440,7 +443,31 @@ function egw_fw_ui_tab(_parent, _contHeaderDiv, _contDiv, _icon, _callback,
|
||||
$(this.contentDiv).addClass("egw_fw_ui_tab_content");
|
||||
$(this.contentDiv).hide();
|
||||
|
||||
//Sort the element in at the given position
|
||||
var _this = this;
|
||||
var $_children = $(this.contHeaderDiv).children();
|
||||
var _cnt = $_children.size();
|
||||
|
||||
if (_cnt > 0 && _pos > -1)
|
||||
{
|
||||
$_children.each(function(i) {
|
||||
if (_pos <= this._position)
|
||||
{
|
||||
$(this).before(_this.headerDiv);
|
||||
return false;
|
||||
}
|
||||
else if (i == (_cnt - 1))
|
||||
{
|
||||
$(this).after(_this.headerDiv);
|
||||
return false;
|
||||
}
|
||||
});
|
||||
}
|
||||
else
|
||||
{
|
||||
$(this.contHeaderDiv).append(this.headerDiv);
|
||||
}
|
||||
|
||||
$(this.contDiv).append(this.contentDiv);
|
||||
}
|
||||
|
||||
@ -531,12 +558,40 @@ function egw_fw_ui_tabs(_contDiv)
|
||||
$(this.contHeaderDiv).addClass("egw_fw_ui_tabs_header");
|
||||
$(this.contDiv).append(this.contHeaderDiv);
|
||||
|
||||
this.appHeaderContainer = document.createElement("div");
|
||||
$(this.appHeaderContainer).addClass("egw_fw_ui_app_header_container");
|
||||
$(this.contDiv).append(this.appHeaderContainer);
|
||||
|
||||
this.appHeader = document.createElement("div");
|
||||
$(this.appHeader).addClass("egw_fw_ui_app_header");
|
||||
$(this.appHeader).hide();
|
||||
$(this.appHeaderContainer).append(this.appHeader);
|
||||
|
||||
this.tabs = Array();
|
||||
|
||||
this.activeTab = null;
|
||||
this.tabHistory = Array();
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the "appHeader" text below the tabs list.
|
||||
*
|
||||
* @param string _text is the text which will be seen in the appHeader.
|
||||
*/
|
||||
egw_fw_ui_tabs.prototype.setAppHeader = function(_text)
|
||||
{
|
||||
if (_text != "")
|
||||
{
|
||||
$(this.appHeader).empty();
|
||||
$(this.appHeader).append("<span style=\"color:gray \">»</span> " + _text);
|
||||
$(this.appHeader).show();
|
||||
}
|
||||
else
|
||||
{
|
||||
$(this.appHeader).hide();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Function internally used to remove double entries from the tab history. The tab
|
||||
* history is used to store the order in which the tabs have been opened, to be able
|
||||
@ -558,12 +613,36 @@ egw_fw_ui_tabs.prototype.cleanHistory = function()
|
||||
* @param function _callback(_sender) function which should be called whenever the tab header is clicked. The _sender parameter passed is a reference to this egw_fw_ui_tab element.
|
||||
* @param function _closeCallback(_sender) function which should be called whenever the close button of the tab is clicked. The _sender parameter passed is a reference to this egw_fw_ui_tab element.
|
||||
* @param object _tag can be used to attach any user data to the object. Inside egw_fw _tag is used to attach an egw_fw_class_application to each sidemenu entry.
|
||||
* @param int _pos specifies the position in the tab list. If _pos is -1, the tab will be added to the end of the tab list
|
||||
*/
|
||||
egw_fw_ui_tabs.prototype.addTab = function(_icon, _callback, _closeCallback, _tag)
|
||||
egw_fw_ui_tabs.prototype.addTab = function(_icon, _callback, _closeCallback, _tag, _pos)
|
||||
{
|
||||
var pos = -1;
|
||||
if (typeof _pos != 'undefined')
|
||||
pos = _pos;
|
||||
|
||||
var tab = new egw_fw_ui_tab(this, this.contHeaderDiv, this.contDiv, _icon, _callback,
|
||||
_closeCallback, _tag);
|
||||
_closeCallback, _tag, pos);
|
||||
|
||||
//Insert the tab into the tab list.
|
||||
var inserted = false;
|
||||
if (pos > -1)
|
||||
{
|
||||
for (var i in this.tabs)
|
||||
{
|
||||
if (this.tabs[i].position > pos)
|
||||
{
|
||||
this.tabs.splice(i, 0, tab)
|
||||
inserted = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (pos == -1 || !inserted)
|
||||
{
|
||||
this.tabs[this.tabs.length] = tab;
|
||||
}
|
||||
|
||||
if (this.activeTab == null)
|
||||
this.showTab(tab);
|
||||
|
Loading…
Reference in New Issue
Block a user