123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713
"use strict";
modulum("VMSessionNavigationManager", ["EventListener"],
function(context, cls) {
const Wevents = context.constants.widgetEvents;
cls.VMSessionNavigationManager = context.oo.Class(cls.EventListener, function($super) {
return {
__name: "VMSessionNavigationManager",
_session: null,
_currentApplication: null,
_sidebarWidget: null,
_chromeBarTitleWidget: null,
_currentChromeBarWidget: null,
_stackCurrentApplication: null,
_applicationItems: null,
_windowItems: null,
_handles: null,
_applicationStackRootWidgets: null,
_applicationStackWidgets: null,
_applicationStacks: null,
_windowStacks: null,
_rootStackLookup: null,
_applicationLookupByProcId: null,
_applicationParentLookup: null,
_applicationProcIds: null,
_currentStackItem: null,
_lastActiveWindow: null,
constructor: function(session) {
$super.constructor.call(this);
this._session = session;
this._sidebarWidget = cls.WidgetFactory.createWidget("SessionSidebar", {
appHash: gbc.systemAppId
});
this._chromeBarTitleWidget = cls.WidgetFactory.createWidget("ChromeBarTitle", {
appHash: gbc.systemAppId
});
this._chromeBarTitleWidget.onDropDownBeforeOpen(() => {
const appId = this._applicationProcIds.get(this._currentApplication),
rootProcId = this._rootStackLookup.get(appId),
dropDownContent = this._applicationStackWidgets.get(rootProcId);
this._chromeBarTitleWidget.setDropDownContent(dropDownContent);
});
this._chromeBarTitleWidget.onDropDownClose(() => {
this._chromeBarTitleWidget.setDropDownContent(null);
});
this._applicationItems = new Map();
this._windowItems = new Map();
this._handles = new WeakMap();
this._stackCurrentApplication = new Map();
this._applicationStackWidgets = new Map();
this._applicationStackRootWidgets = new Map();
this._applicationStacks = new Map();
this._windowStacks = new Map();
this._rootStackLookup = new Map();
this._applicationLookupByProcId = new Map();
this._applicationParentLookup = new Map();
this._applicationProcIds = new WeakMap();
this._lastActiveWindow = new Map();
},
destroy: function() {
this._applicationItems = null;
this._windowItems = null;
this._handles = null;
for (const rootWidget of this._applicationStackRootWidgets.values()) {
this._sidebarWidget.removeChildWidget(rootWidget);
}
this._applicationStackRootWidgets = null;
this._applicationStackWidgets = null;
this._applicationStacks = null;
this._rootStackLookup = null;
this._applicationLookupByProcId = null;
this._applicationParentLookup = null;
this._sidebarWidget.destroy();
this._sidebarWidget = null;
this._chromeBarTitleWidget.destroy();
this._chromeBarTitleWidget = null;
this._session = null;
this._lastActiveWindow.clear();
this._lastActiveWindow = null;
$super.destroy.call(this);
},
getSession: function() {
return this._session;
},
getChromeBarTitleWidget: function() {
return this._chromeBarTitleWidget;
},
getWidget: function() {
return this._sidebarWidget;
},
setCurrentWindow: function(windowNode) {
const app = windowNode.getApplication(),
appId = this._applicationProcIds.get(app);
this._currentApplication = app;
this._currentWindow = windowNode;
const rootProcId = this._rootStackLookup.get(appId);
this._stackCurrentApplication.set(rootProcId, appId);
if (windowNode.getTitle()) {
windowNode.setTitle(windowNode.getTitle());
}
},
getCurrentWindow: function() {
return this._currentWindow;
},
addApplication: function(application) {
if (this._applicationItems.has(application)) {
console.warn("Application already added");
return;
}
const applicationSidebarWidget = cls.WidgetFactory.createWidget("SessionSidebarApplicationItem",
application.getUI().getWidget().getBuildParameters());
this._applicationItems.set(application, applicationSidebarWidget);
this._handles.set(application, {
nameHandle: application.when(Wevents.titleChanged, (evt, src, title) => {
this.syncHost();
applicationSidebarWidget.setApplicationName(title);
const appInfo = application.applicationInfo.connectionInfo,
rootWidget = this._applicationStackRootWidgets.get(appInfo && appInfo.procId);
if (rootWidget) {
rootWidget.setApplicationTitle(title);
}
}),
iconHandle: application.when(Wevents.iconChanged, (evt, src, icon) => {
this.syncHost();
applicationSidebarWidget.setApplicationIcon(icon);
const appInfo = application.applicationInfo.connectionInfo,
rootWidget = this._applicationStackRootWidgets.get(appInfo && appInfo.procId);
if (rootWidget) {
rootWidget.setIcon(icon);
}
}),
clickHandle: applicationSidebarWidget.when(Wevents.click, () => {
const ui = application.getUI();
ui.syncCurrentWindow();
if (gbc.StoredSettingsService.isSideBarVisible()) {
context.HostLeftSidebarService.hideSidebar();
}
})
});
application.dvm.onOrdersManaged(() => {
applicationSidebarWidget.setApplicationName(application.getTitle());
applicationSidebarWidget.setApplicationIcon(application.getImage());
}, true);
gbc.HostService.updateDisplay();
return applicationSidebarWidget;
},
updateApplicationInformation: function(application) {
const appInfo = application.applicationInfo.connectionInfo;
let procId = null,
procIdParent = null,
procIdWaiting = null;
if (appInfo) {
procId = appInfo.procId;
procIdParent = appInfo.procIdParent || null;
procIdWaiting = Boolean(appInfo.procIdWaiting);
this._applicationLookupByProcId.set(procId, application);
this._applicationParentLookup.set(procId, procIdParent);
this._applicationProcIds.set(application, procId);
}
if (procId) {
if (!procIdParent || !procIdWaiting || !this._rootStackLookup.get(procIdParent)) {
if (!this._applicationStackRootWidgets.has(procId)) {
const rootWidget = cls.WidgetFactory.createWidget("SessionSidebarApplicationStackItem", {
...(application.getUI().getWidget().getBuildParameters()),
appHash: gbc.systemAppId
});
rootWidget.setApplicationTitle(application.getTitle());
rootWidget.setIcon(application.getImage());
rootWidget.when(context.constants.widgetEvents.click, () => {
let app = this._applicationLookupByProcId.get(this._stackCurrentApplication.get(procId));
if (!app) {
const stack = this._applicationStacks.get(procId);
app = this._applicationLookupByProcId.get(stack[stack.length - 1]);
}
const ui = app.getUI();
ui.syncCurrentWindow();
context.HostLeftSidebarService.showTopMenu(false, true);
context.TopmenuService.syncTopMenus(app.applicationHash);
if (gbc.StoredSettingsService.isSideBarVisible()) {
context.HostLeftSidebarService.hideSidebar();
}
});
const listWidget = cls.WidgetFactory.createWidget("SessionSidebarApplicationStackList", {
...(application.getUI().getWidget().getBuildParameters()),
appHash: gbc.systemAppId
});
this._applicationStackRootWidgets.set(procId, rootWidget);
this._applicationStackWidgets.set(procId, listWidget);
this._applicationStacks.set(procId, [procId]);
this._windowStacks.set(procId, []);
this._rootStackLookup.set(procId, procId);
listWidget.addChildWidget(this._applicationItems.get(application));
this._sidebarWidget.addChildWidget(rootWidget);
this.emit(context.constants.VMSessionNavigationManagerEvents.addSessionSidebarApplicationStackItem,
application, rootWidget);
}
} else {
const rootProcId = this._rootStackLookup.get(procIdParent),
stack = this._applicationStacks.get(rootProcId),
listWidget = this._applicationStackWidgets.get(rootProcId);
stack.push(procId);
listWidget.addChildWidget(this._applicationItems.get(application));
this._rootStackLookup.set(procId, rootProcId);
}
context.HostLeftSidebarService.updateApplicationCount(1);
}
},
removeApplication: function(application) {
context.HostLeftSidebarService.updateApplicationCount(-1);
const {
nameHandle,
iconHandle,
clickHandle
} = this._handles.get(application);
nameHandle();
iconHandle();
clickHandle();
this._handles.delete(application);
const applicationSidebarWidget = this._applicationItems.get(application),
parentWidget = applicationSidebarWidget.getParentWidget();
if (parentWidget) {
parentWidget.removeChildWidget(applicationSidebarWidget);
}
applicationSidebarWidget.destroy();
this._applicationItems.delete(application);
if (this._applicationProcIds.has(application)) {
const procId = this._applicationProcIds.get(application);
this._applicationProcIds.delete(application);
this._applicationLookupByProcId.delete(procId);
}
const appInfo = application.applicationInfo.connectionInfo,
procId = appInfo.procId,
rootProcId = this._rootStackLookup.get(procId),
stack = this._applicationStacks.get(rootProcId);
stack.remove(procId);
if (!stack.length) {
this._applicationStacks.delete(rootProcId);
this._sidebarWidget.removeChildWidget(this._applicationStackRootWidgets.get(rootProcId));
if (this._currentStackItem === this._applicationStackRootWidgets.get(rootProcId)) {
this._currentStackItem = null;
}
this.emit(context.constants.VMSessionNavigationManagerEvents.removeSessionSidebarApplicationStackItem,
application, this._applicationStackRootWidgets.get(rootProcId));
this._applicationStackRootWidgets.get(rootProcId).destroy();
this._applicationStackRootWidgets.delete(rootProcId);
[...this._rootStackLookup.keys()].filter(k => this._rootStackLookup[k] === rootProcId)
.forEach(k => {
this._rootStackLookup.delete(k);
this._applicationParentLookup.delete(k);
});
this._sidebarWidget.removeChildWidget(this._applicationStackWidgets.get(rootProcId));
}
},
setApplicationProcessing: function(application, processing) {
this._applicationItems.get(application).setProcessing(processing);
},
freezeApplication: function(application) {
const item = this._applicationItems.get(application);
if (item) {
item.freeze();
}
},
unfreezeApplication: function(application) {
const item = this._applicationItems.get(application);
if (item) {
item.unfreeze();
}
},
addWindow: function(windowNode) {
if (this._windowItems.has(windowNode)) {
console.warn("Window already added");
return;
}
const application = windowNode.getApplication();
windowNode.whenControllerCreated(() => {
const windowSidebarWidget = cls.WidgetFactory.createWidget("SessionSidebarWindowItem",
windowNode.getWidget().getBuildParameters());
this._applicationItems.get(application).addChildWidget(windowSidebarWidget);
this._windowItems.set(windowNode, windowSidebarWidget);
const windowList = this._windowStacks.get(this._getRootProcId(application));
windowList.add(windowNode);
windowSidebarWidget.setWindowName(windowNode.attribute("text") || windowNode.attribute("name"));
windowSidebarWidget.setWindowIcon(windowNode.getWidget().getImage());
this._handles.set(windowNode, {
nameHandle: windowNode.when(Wevents.titleChanged, (evt, src, title) => {
this.syncHost();
windowSidebarWidget.setWindowName(title);
}),
iconHandle: windowNode.when(Wevents.iconChanged, (evt, src, icon) => {
this.syncHost();
windowSidebarWidget.setWindowIcon(icon);
}),
clickHandle: windowSidebarWidget.when(Wevents.click, () => {
const ui = application.getUI();
const uiWidget = ui.getWidget();
ui.syncCurrentWindow();
ui.setCurrentWindow(windowNode.getId());
var infoLastWindow = this._lastActiveWindow.get(this.getRootWaitingApplication(application).getProcId());
if (ui !== infoLastWindow.ui || windowNode.getId() !== infoLastWindow.windowId) {
uiWidget.domAttributesMutator(() => uiWidget.addClass("inactiveWindow"));
} else {
uiWidget.domAttributesMutator(() => uiWidget.removeClass("inactiveWindow"));
}
if (gbc.StoredSettingsService.isSideBarVisible()) {
context.HostLeftSidebarService.hideSidebar();
}
})
});
this.emit(context.constants.VMSessionNavigationManagerEvents.addSessionSidebarWindowItem,
application, windowSidebarWidget);
return windowSidebarWidget;
}, true);
},
removeWindow: function(windowNode) {
const {
nameHandle,
iconHandle,
clickHandle
} = this._handles.get(windowNode);
nameHandle();
iconHandle();
clickHandle();
this._handles.delete(windowNode);
const windowSidebarWidget = this._windowItems.get(windowNode);
const application = windowNode.getApplication();
this.emit(context.constants.VMSessionNavigationManagerEvents.removeSessionSidebarWindowItem,
application, windowSidebarWidget);
this._applicationItems.get(windowNode.getApplication()).removeChildWidget(windowSidebarWidget);
windowSidebarWidget.destroy();
this._windowItems.delete(windowNode);
const windowList = this._windowStacks.get(this._getRootProcId(application));
windowList.remove(windowNode);
},
freezeWindow: function(windowNode, isNextModal) {
const windowWidget = windowNode && windowNode.getWidget();
if (windowWidget) {
windowWidget.freeze(isNextModal);
}
if (windowNode) {
this._windowItems.get(windowNode).setFrozen(true);
}
},
unfreezeWindow: function(windowNode) {
const windowWidget = windowNode && windowNode.getWidget();
if (windowWidget) {
windowWidget.unfreeze();
}
if (windowNode) {
this._windowItems.get(windowNode).setFrozen(false);
}
context.TopmenuService.syncTopMenus(windowWidget.getApplicationIdentifier());
},
updateItemsStatuses: function(currentWindowNode) {
if (currentWindowNode && !currentWindowNode.isModal()) {
const currentApp = currentWindowNode && currentWindowNode.getApplication(),
currentSession = currentApp && currentApp.getSession(),
rootProcId = this._rootStackLookup.get(this._applicationProcIds.get(currentApp)),
applicationStackItemWidget = this._applicationStackRootWidgets.get(rootProcId);
if (this._session) {
if (currentWindowNode) {
if (currentSession && (!currentSession.isInTabbedContainerMode() || currentSession.getHostApplication() === currentApp)) {
const chromeBarWidget = currentApp && currentApp.getChromeBar();
const windowList = this._windowStacks.get(this._getRootProcId(currentApp));
const stackItem = this._applicationStackRootWidgets.get(this._getRootProcId(currentApp));
this._chromeBarTitleWidget.setListingVisible(windowList.length > 1);
this._chromeBarTitleWidget.setWindowTitle(currentWindowNode.getTitle(), currentApp);
this._chromeBarTitleWidget.setIcon(currentWindowNode.getIcon());
if (this._currentChromeBarWidget !== chromeBarWidget) {
if (this._currentChromeBarWidget) {
this._currentChromeBarWidget.setTitle();
this._currentChromeBarWidget = null;
}
if (chromeBarWidget) {
chromeBarWidget.setTitle(this._chromeBarTitleWidget, currentApp);
this._currentChromeBarWidget = chromeBarWidget;
}
}
}
if (this._currentStackItem) {
this._currentStackItem.setVisible(false);
this._currentStackItem = null;
}
if (applicationStackItemWidget) {
this._currentStackItem = applicationStackItemWidget;
applicationStackItemWidget.setVisible(true);
}
}
this._session.getApplications().forEach(app => {
const appItem = this._applicationItems.get(app);
if (appItem) {
appItem.toggleClass("activeWindow", app === currentApp);
app.model.getNodesByTag("Window").forEach(win => {
const winItem = this._windowItems.get(win);
if (winItem) {
winItem.toggleClass("activeWindow", app.getVMWindow() === win);
winItem.toggleClass("visibleWindow", win === currentWindowNode);
}
});
}
});
}
}
},
_getRootProcId: function(application) {
return this._rootStackLookup.get(this._applicationProcIds.get(application));
},
syncHost: function() {
this.updateItemsStatuses(context.HostService._currentWindowNode);
},
getApplicationWidgetList: function() {
return this._applicationStackRootWidgets;
},
getApplicationByProcId: function(procId) {
return this._applicationLookupByProcId.get(procId);
},
getWindowWidgetList: function() {
return this._windowItems;
},
getRootWaitingApplication: function(application) {
let app = application;
let appInfo = application.applicationInfo.connectionInfo;
let procId = appInfo.procId;
do {
if (!appInfo.procIdWaiting || !appInfo.procIdParent) {
return app;
}
procId = appInfo.procIdParent;
app = this._applicationLookupByProcId.get(procId);
appInfo = app && app.applicationInfo.connectionInfo;
} while (app && appInfo);
return null;
},
getParentApplication: function(application) {
let parentProcId = application.applicationInfo.connectionInfo.procIdParent;
if (parentProcId) {
return this._applicationLookupByProcId.get(parentProcId);
}
return null;
},
getChildApplication: function(application) {
let appProcId = application.getProcId();
for (let [procId, app] of this._applicationLookupByProcId.entries()) {
if (app.applicationInfo.connectionInfo.procIdParent === appProcId) {
return app;
}
}
return null;
},
setLastActiveWindow: function(application, lastActiveWindowId) {
let rootApp = this.getRootWaitingApplication(application);
if (!rootApp) {
return;
}
this._lastActiveWindow.set(rootApp.getProcId(), {
ui: application.getUI(),
windowId: lastActiveWindowId
});
let windowNode = application.model.getNode(lastActiveWindowId);
let windowText = windowNode.attribute("text");
if (!windowText) {
windowText = windowNode.attribute("name");
}
},
goBackToLastActiveWindow: function(application) {
var procId = this.getRootWaitingApplication(application || this.getSession().getCurrentApplication()).getProcId();
var info = this._lastActiveWindow.get(procId);
info.ui.syncCurrentWindow();
info.ui.setCurrentWindow(info.windowId);
const uiWidget = info.ui.getWidget();
uiWidget.domAttributesMutator(() => uiWidget.removeClass("inactiveWindow"));
if (gbc.StoredSettingsService.isSideBarVisible()) {
context.HostLeftSidebarService.hideSidebar();
}
},
getApplications: function() {
var res = [];
this._applicationLookupByProcId.forEach((value) => {
res.push(value);
});
return res;
}
};
});
});