Retour à la documentation
define(["dojo/_base/declare", "spw/api/SpwMap", "spw/api/ConfigLoader", "dojo/_base/array", "dojo/_base/lang",
"dojo/Evented", "spw/api/Utils", "dojo/Deferred"],
function(declare, SpwMap, ConfigLoader, array, lang, Evented, Utils, Deferred){
var SpwWidgetsManager = null;
SpwWidgetsManager = declare("spw.api.SpwWidgetsManager", [Evented], /** @lends spw.api.SpwWidgetsManager.prototype */{
/**
* Tableau des différents outils chargés
* @private
* @type spw.api.SpwBaseWidget[]
*/
_widgets: null,
_widgetClasses: null,
_widgetsConfig: null,
/**
* Référence vers le viewer.
*/
spwViewer: null,
/**
* Indique si toutes les classes des widgets sont chargées.
* @type Boolean
*/
widgetClassesLoaded: null,
/**
* Indique si tous les widgets sont instanciés.
* @type Boolean
*/
widgetsCreated: null,
events: {},
/**
* @constructs
* @classdesc Cette classe est un singleton et permet d'instancier les widgets déclarés dans le fichier widgets.json. De plus, elle offre des méthode permettant d'accéder aux widgets.
*/
constructor: function(config) {
this._widgets = {};
this.spwViewer = config.spwViewer;
this.widgetClassesLoaded = false;
lang.mixin(this.events, SpwWidgetsManager.events);
},
/**
* Charge dynamiquement les classes (code javascript) des widgets déclarés dans widgets.json.
*/
loadWidgetClasses: function(defaultWidgets) {
if(defaultWidgets) {
this.defaultWidgets = defaultWidgets = [].concat(defaultWidgets);
}
this._widgetClasses = {};
this._widgetsConfig = ConfigLoader.getInstance().get("widgets");
array.forEach(this.defaultWidgets, lang.hitch(this, function(w) {
if (w == null || w.config == null || w.config.widgetId == null) {
return;
}
var found = array.some(this._widgetsConfig, lang.hitch(this, function(cfg) {
return cfg && cfg.config && cfg.config.widgetId === w.config.widgetId;
}));
if (!found) {
//if(!w.config.configSecondScreen || w.config.configSecondScreen.create !== false || !this.spwViewer.isSideWindow()){
this._widgetsConfig.push(w);
//}
}
//remove all widget with create = false
this._widgetsConfig = array.filter(this._widgetsConfig, lang.hitch(this, function(w){
return !w.config || (!w.config.configSecondScreen || w.config.configSecondScreen.create !== false || !this.spwViewer.isSideWindow());
}));
}));
this._widgetsConfig.sort(function(w1, w2) {
if (w1.order == null && w2.order == null) {
return 0;
}
if (w1.order === 'last') { return 1; }
if (w2.order === 'last') { return -1; }
if (w1.order == null && w2.order !== null && typeof(w2.order) !== 'undefined') {
return 1;
}
if (w2.order == null && w1.order !== null && typeof(w1.order) !== 'undefined') {
return -1;
}
// dans le cas où 2 infinis -> une soustraction ne fonctionnera pas
if (w1.order < w2.order) {
return -1;
}
else if (w1.order > w2.order) {
return 1;
}
return 0;
});
if (!this._widgetsConfig || this._widgetsConfig.length == 0) {
this.widgetClassesLoaded = true;
this.emit(SpwWidgetsManager.events.widgetClassesLoaded);
this.widgetsCreated = true;
this.emit(SpwWidgetsManager.events.widgetsCreated);
return;
}
var cpt = 0;
var handler = null;
handler = require.on("error", lang.hitch(this, function(err){
cpt++;
if(cpt == this._widgetsConfig.length){
handler.remove();
this.widgetClassesLoaded = true;
this.emit(SpwWidgetsManager.events.widgetClassesLoaded);
}
if(++this._instanciateCount == this._widgetsConfig.length){
this.widgetsCreated = true;
this._instanciateCount = 0;
this.emit(SpwWidgetsManager.events.widgetsCreated);
}
}));
this.calculateToolbarIndexes();
var loadWidgetFunc = function(cfg, i, def) {
if (typeof cfg === 'string') {
cfg = {className: cfg};
}
require([cfg.className], lang.hitch(this, function(WidgetClass){
if(!cfg.config){
cfg.config = {};
}
cpt++;
lang.mixin(cfg.config, {spwViewer: this.spwViewer});
this._widgetClasses[i] = lang.mixin({}, {widgetClass: WidgetClass, widgetConfig: cfg.config});
this.instanciateWidget(this._widgetClasses[i]);
if(cpt == this._widgetsConfig.length) {
handler.remove();
this.widgetClassesLoaded = true;
this.emit(SpwWidgetsManager.events.widgetClassesLoaded);
}
def && def.resolve();
}));
};
var defs = [new Deferred().resolve()];
var stoppedIdx = this._widgetsConfig.length;
array.every(this._widgetsConfig, lang.hitch(this, function(widgetConfig, idx) {
if (widgetConfig.order == null) {
stoppedIdx = idx;
return false;
}
var def = new Deferred();
defs.push(def);
defs[idx].then(lang.hitch(this, loadWidgetFunc, widgetConfig, idx, def));
return true;
}));
defs[stoppedIdx].then(lang.hitch(this, function() {
for (; stoppedIdx < this._widgetsConfig.length; ++stoppedIdx) {
lang.hitch(this, loadWidgetFunc)(this._widgetsConfig[stoppedIdx], stoppedIdx);
}
}));
},
/**
* Instancie les widgets chargés.
*/
instanciateWidgets: function() {
for(var key in this._widgetClasses){
var w = this._widgetClasses[key];
this.instanciateWidget(w);
};
},
_instanciateCount: 0,
/**
* Instancie un widget
* @param w le widget à créer
*/
instanciateWidget: function(w) {
try {
if(typeof w.widgetClass != 'undefined'){
var widget = null;
if(w.widgetConfig.inToolbar){
widget = new w.widgetClass(w.widgetConfig);
this.spwViewer.addWidgetInToolbar(widget);
} else {
widget = new w.widgetClass(w.widgetConfig);
}
if (widget.widgetId == null) {
widget.widgetId = Utils.guid();
}
this._widgets[widget.widgetId] = widget;
return widget;
}
} catch(err){
console.error("Error while instanciating widget " + ((w && w.widgetClass && w.widgetClass.prototype) ? "["+w.widgetClass.prototype.declaredClass+"]" : "[???]"), err);
} finally {
if (this._widgetsConfig && this._widgetsConfig.length > 0) {
if(++this._instanciateCount == this._widgetsConfig.length){
this.widgetsCreated = true;
this._instanciateCount = 0;
this.emit(SpwWidgetsManager.events.widgetsCreated);
}
}
}
return null;
},
/**
* Détruit tous les widgets du viewer.
*/
destroyWidgets: function() {
var widget = null;
var tab=[];
for (var key in this._widgets) { if (this._widgets.hasOwnProperty(key)) tab.push(this._widgets[key]); }
tab.sort(function(w1, w2) {
if (w1.order === w2.order) { return 0; }
if (w1.order === 'last') { return 1; }
if (w2.order === 'last') { return -1; }
if (w1.order == null && w2.order == null) { return 0; }
if (w1.order == null && w2.order !== null && typeof(w2.order) !== 'undefined') { return 1; }
if (w2.order == null && w1.order !== null && typeof(w1.order) !== 'undefined') { return -1; }
if (w1.order < w2.order) { return -1; }
else if (w1.order > w2.order) { return 1; }
return 0;
});
for (var i=tab.length-1; i >= 0; i--) {
widget = tab[i];
if(widget.get('inToolbar') || widget.get('position') == 'toolbar'){
this.spwViewer.removeWidgetFromToolbar(widget);
}
if(widget.onDeactivate){
widget.onDeactivate();
}
this.spwViewer.hideWidget(widget);
widget.destroy();
}
if(this.spwViewer.toolbar){
this.spwViewer.toolbar = null;
}
this._widgets = {};
},
/**
* Calcul l'index de position dans la toolbar pour les widgets placés dans la toolbar.
*/
calculateToolbarIndexes: function(){
var toolWidgetsArray = [];
array.forEach(this._widgetsConfig, lang.hitch(this, function(wConfig){
if(wConfig.config && (wConfig.config.inToolbar || wConfig.config.position == "toolbar")){
toolWidgetsArray.push(wConfig.config);
}
}));
array.forEach(toolWidgetsArray, function(config, idx){
lang.mixin(config, {toolBarIndex: idx});
});
},
/**
* Récupère le(s) widget(s) sur base d'un objet clé-valeur. Par exemple: récupérer les widgets actifs : getWidgets({activated:true}) ; récupérer un widget par son id : getWidgets({widgetId:'monWidget'}); ...
* Toutes les propriétés d'un widget peuvent être interrogées via ce query object. Un Query object vide ({}) permet de récupérer tous les widgets.
* @param queryObject
* @returns {Array} Tableau contenant les widgets correspondants à la query.
*/
getWidgets: function(queryObject) {
return Utils.findInObject(this._widgets, queryObject);
},
/**
* Accède à un widget sur base de son id
* @param id l'id du widget auquel accéder
*/
getWidget: function(id) {
return this._widgets[id];
},
/**
* Appelé à la destruction du Manager
*/
destroy: function(){
this.inherited(arguments);
}
});
SpwWidgetsManager.events = {
/**
* Les classes des widgets présents dans la configuration (widgets.json) sont chargées (!= instanciées).
* @event spw.api.SpwWidgetsManager#widgetClassesLoaded
*/
"widgetClassesLoaded": "widgetClassesLoaded",
/**
* Les widgets sont créés et placé dans le Viewer.
* @event spw.api.SpwWidgetsManager#widgetsCreated
*/
"widgetsCreated": "widgetsCreated"
};
return SpwWidgetsManager;
});