Publish Vulpes Preview 15 sources for desktop, Android and Tundra
Share Gaia assets and adapters, keep private profiles and development documents local, and update both public READMEs.
This commit is contained in:
parent
93e3a48004
commit
b38dea0597
25901 changed files with 9982925 additions and 369 deletions
377
gaia/tv_apps/smart-system/js/stack_manager.js
Executable file
377
gaia/tv_apps/smart-system/js/stack_manager.js
Executable file
|
|
@ -0,0 +1,377 @@
|
|||
'use strict';
|
||||
|
||||
/* global AppWindowManager */
|
||||
|
||||
var StackManager = {
|
||||
init: function sm_init() {
|
||||
window.addEventListener('appcreated', this);
|
||||
window.addEventListener('launchapp', this);
|
||||
window.addEventListener('appopening', this);
|
||||
window.addEventListener('appterminated', this);
|
||||
window.addEventListener('home', this);
|
||||
window.addEventListener('cardviewclosed', this);
|
||||
},
|
||||
|
||||
getCurrent: function sm_getCurrent() {
|
||||
if (this.position < 0) {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
var app = this._currentFromStack();
|
||||
|
||||
// XXX: This code will be removed when bug 967405 lands.
|
||||
// Until then we can get into edge cases where the app currently
|
||||
// displayed is not part of the stack and we don't want to break.
|
||||
if (!app) {
|
||||
app = AppWindowManager.getActiveApp();
|
||||
}
|
||||
|
||||
return app;
|
||||
},
|
||||
|
||||
_currentFromStack: function sm_currentInStack() {
|
||||
return this._stack[this.position].getActiveWindow();
|
||||
},
|
||||
outOfStack: function sm_outOfStack() {
|
||||
return (this._currentFromStack() !== this.getCurrent());
|
||||
},
|
||||
|
||||
getPrev: function sm_getPrev() {
|
||||
if (this.outOfStack()) {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
var inGroupPrev = this._currentFromStack().getPrev();
|
||||
if (inGroupPrev) {
|
||||
return inGroupPrev;
|
||||
}
|
||||
var previousGroup = this._stack[this.position - 1];
|
||||
if (previousGroup) {
|
||||
return previousGroup.getLeafWindow();
|
||||
}
|
||||
|
||||
return undefined;
|
||||
},
|
||||
|
||||
getNext: function sm_getNext() {
|
||||
if (this.outOfStack()) {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
var inGroupNext = this._currentFromStack().getNext();
|
||||
if (inGroupNext) {
|
||||
return inGroupNext;
|
||||
}
|
||||
var nextGroup = this._stack[this.position + 1];
|
||||
if (nextGroup) {
|
||||
return nextGroup.getRootWindow();
|
||||
}
|
||||
|
||||
return undefined;
|
||||
},
|
||||
|
||||
goPrev: function sm_goPrev() {
|
||||
var oldApp = this.getCurrent();
|
||||
var newApp = this.getPrev();
|
||||
if (!oldApp || !newApp) {
|
||||
return;
|
||||
}
|
||||
|
||||
this._queueBroadcast(newApp, oldApp);
|
||||
|
||||
if (newApp.groupID !== oldApp.groupID) {
|
||||
this.position--;
|
||||
}
|
||||
},
|
||||
|
||||
goNext: function sm_goNext() {
|
||||
var oldApp = this.getCurrent();
|
||||
var newApp = this.getNext();
|
||||
if (!oldApp || !newApp) {
|
||||
return;
|
||||
}
|
||||
|
||||
this._queueBroadcast(newApp, oldApp);
|
||||
|
||||
if (newApp.groupID !== oldApp.groupID) {
|
||||
this.position++;
|
||||
}
|
||||
},
|
||||
|
||||
commit: function sm_commit() {
|
||||
// We're back to the same place, let's close up the gesture without
|
||||
// queueing.
|
||||
if (this._didntMove) {
|
||||
window.dispatchEvent(new CustomEvent('sheets-gesture-end'));
|
||||
}
|
||||
if (!this._broadcastTimeout) {
|
||||
this._broadcast();
|
||||
}
|
||||
},
|
||||
|
||||
commitClose: function sm_commitClose() {
|
||||
// TODO: make this transition pretty but at least we're
|
||||
// fixing the race condition
|
||||
clearTimeout(this._broadcastTimeout);
|
||||
this._broadcastTimeout = null;
|
||||
|
||||
if (this._appIn) {
|
||||
this._appIn.broadcast('closed');
|
||||
}
|
||||
|
||||
if (this._appOut) {
|
||||
this._appOut.transitionController.clearTransitionClasses();
|
||||
}
|
||||
|
||||
this._cleanUp();
|
||||
},
|
||||
|
||||
snapshot: function sm_snapshot() {
|
||||
return this._stack.slice(0);
|
||||
},
|
||||
|
||||
get length() {
|
||||
return this._stack.length;
|
||||
},
|
||||
|
||||
get position() {
|
||||
return this._current;
|
||||
},
|
||||
|
||||
get _didntMove() {
|
||||
return !!this._appIn && this._appIn === this._appOut;
|
||||
},
|
||||
|
||||
set position(position) {
|
||||
var _position = parseInt(position);
|
||||
if (_position < -1 || _position >= this._stack.length) {
|
||||
console.warn('bad stack position. requested position = ',
|
||||
_position, '; stack length = ', this._stack.length);
|
||||
return;
|
||||
}
|
||||
|
||||
this._current = _position;
|
||||
},
|
||||
|
||||
_stack: [],
|
||||
_current: -1,
|
||||
|
||||
handleEvent: function sm_handleEvent(e) {
|
||||
switch (e.type) {
|
||||
case 'appcreated':
|
||||
var app = e.detail;
|
||||
// Multiple apps use role=system to opt out of being part of
|
||||
// the the card view.
|
||||
// XXX: This code will be removed when bug 967405 lands.
|
||||
if (app.manifest && app.manifest.role == 'system') {
|
||||
return;
|
||||
}
|
||||
|
||||
// The FTU application should never show up in the stack.
|
||||
// XXX: This code will be removed when bug 967405 lands.
|
||||
if (app.name == 'FTU') {
|
||||
return;
|
||||
}
|
||||
|
||||
// If the app is a child window of other window, do not insert it.
|
||||
if (app.previousWindow) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (app.stayBackground) {
|
||||
this._insertBelow(app);
|
||||
} else {
|
||||
this._moveToTop(this.position);
|
||||
this._insertOnTop(app);
|
||||
}
|
||||
break;
|
||||
case 'launchapp':
|
||||
var config = e.detail;
|
||||
if (!config.stayBackground) {
|
||||
this._moveToTop(this.position);
|
||||
|
||||
var idx = this._indexOfURL(config.url);
|
||||
if (idx !== undefined) {
|
||||
this._moveToTop(idx);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 'appopening':
|
||||
var app = e.detail; // jshint ignore: line
|
||||
var root = app.getRootWindow();
|
||||
|
||||
var id = this._indexOfInstanceID(root.instanceID);
|
||||
if (id !== undefined && id !== this._current) {
|
||||
this._current = id;
|
||||
}
|
||||
break;
|
||||
case 'home':
|
||||
this._moveToTop(this.position);
|
||||
this.position = -1;
|
||||
this.commitClose();
|
||||
break;
|
||||
case 'appterminated':
|
||||
var instanceID = e.detail.instanceID;
|
||||
this._remove(instanceID);
|
||||
break;
|
||||
case 'cardviewclosed':
|
||||
if (e.detail && e.detail.newStackPosition) {
|
||||
this.position = e.detail.newStackPosition;
|
||||
}
|
||||
break;
|
||||
}
|
||||
this._stackChanged();
|
||||
},
|
||||
|
||||
_insertBelow: function sm_insertBelow(app) {
|
||||
this._stack.splice(0, 0, app);
|
||||
if (this._stack.length > 1) {
|
||||
this.position++;
|
||||
} else {
|
||||
this.position = 0;
|
||||
}
|
||||
},
|
||||
|
||||
_insertOnTop: function sm_insertOnTop(app) {
|
||||
this.position = this._stack.push(app) - 1;
|
||||
},
|
||||
|
||||
_moveToTop: function sm_moveToTop(index) {
|
||||
if (index === -1 || index >= this._stack.length) {
|
||||
return;
|
||||
}
|
||||
|
||||
var sheet = this._stack.splice(index, 1)[0];
|
||||
this.position = this._stack.push(sheet) - 1;
|
||||
},
|
||||
|
||||
_indexOfURL: function sm_indexOfURL(url) {
|
||||
var result;
|
||||
this._stack.some(function(app, idx) {
|
||||
if (app.url == url) {
|
||||
result = idx;
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
});
|
||||
|
||||
return result;
|
||||
},
|
||||
|
||||
_indexOfInstanceID: function sm_indexOfIntanceID(instanceID) {
|
||||
var result;
|
||||
this._stack.some(function(app, idx) {
|
||||
if (app.instanceID == instanceID) {
|
||||
result = idx;
|
||||
return true;
|
||||
} false;
|
||||
});
|
||||
|
||||
return result;
|
||||
},
|
||||
|
||||
_remove: function sm_remove(instanceID) {
|
||||
for (var i = (this._stack.length - 1); i >= 0; i--) {
|
||||
var sConfig = this._stack[i];
|
||||
|
||||
if (sConfig.instanceID == instanceID) {
|
||||
this._stack.splice(i, 1);
|
||||
|
||||
if (i <= this.position && this.position >= 0) {
|
||||
this.position--;
|
||||
}
|
||||
return;
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
_stackChanged: function sm_stackChanged() {
|
||||
var details = {
|
||||
position: this.position,
|
||||
sheets: this._stack
|
||||
};
|
||||
|
||||
var evt = new CustomEvent('stackchanged', { detail: details });
|
||||
|
||||
window.dispatchEvent(evt);
|
||||
},
|
||||
|
||||
_broadcastTimeout: null,
|
||||
_appIn: null,
|
||||
_appOut: null,
|
||||
_queueBroadcast: function sm_queueBroadcast(appIn, appOut) {
|
||||
if (this._appIn) {
|
||||
this._appIn.cancelQueuedShow();
|
||||
}
|
||||
this._appIn = appIn;
|
||||
appIn.queueShow();
|
||||
|
||||
if (!this._appOut) {
|
||||
this._appOut = appOut;
|
||||
appOut.queueHide();
|
||||
}
|
||||
|
||||
if (this._broadcastTimeout === null) {
|
||||
AppWindowManager.sendStopRecordingRequest();
|
||||
}
|
||||
|
||||
clearTimeout(this._broadcastTimeout);
|
||||
this._broadcastTimeout = setTimeout(this._broadcast.bind(this), 800);
|
||||
},
|
||||
|
||||
_broadcast: function sm_broadcast(close) {
|
||||
clearTimeout(this._broadcastTimeout);
|
||||
this._broadcastTimeout = null;
|
||||
|
||||
// We're back to the same place
|
||||
if (this._didntMove) {
|
||||
this._appIn.transitionController.clearTransitionClasses();
|
||||
this._cleanUp();
|
||||
return;
|
||||
}
|
||||
|
||||
// We're done swiping around, let's close up the gesture. Note that
|
||||
// sheets-gesture-start is detected and sent in SheetsTransition!!!
|
||||
window.dispatchEvent(new CustomEvent('sheets-gesture-end'));
|
||||
|
||||
if (this._appIn) {
|
||||
this._appIn.broadcast('swipein');
|
||||
}
|
||||
if (this._appOut) {
|
||||
this._appOut.broadcast('swipeout');
|
||||
}
|
||||
|
||||
this._cleanUp();
|
||||
|
||||
this._stackChanged();
|
||||
},
|
||||
|
||||
|
||||
_cleanUp: function sm_cleanUp() {
|
||||
this._appIn = null;
|
||||
this._appOut = null;
|
||||
},
|
||||
|
||||
/* Debug */
|
||||
_dump: function sm_dump() {
|
||||
var prefix = 'StackManager';
|
||||
for (var i = 0; i < this._stack.length; i++) {
|
||||
var separator = (i == this.position) ? ' * ' : ' - ';
|
||||
console.log(prefix + separator + i + ' -> ' + this._stack[i].name +
|
||||
'/' + this._stack[i].instanceID);
|
||||
var child = this._stack[i].nextWindow;
|
||||
while (child) {
|
||||
var separator2 = (child.isActive()) ? ' @ ' : ' = ';
|
||||
console.log(prefix + separator2 + i + ' ---> ' + this._stack[i].name +
|
||||
'/' + this._stack[i].instanceID);
|
||||
child = child.nextWindow;
|
||||
}
|
||||
}
|
||||
},
|
||||
__clearAll: function sm_clearAll() {
|
||||
this._stack = [];
|
||||
this.position = 0;
|
||||
}
|
||||
};
|
||||
|
||||
StackManager.init();
|
||||
Loading…
Reference in a new issue