/**
* Project AMDA-NG
* Name CatalogUI.js
* @class amdaUI.catalogUI
* @extends Ext.container.Container
* @brief Catalog Module UI definition (View)
* @author elena
*/
Ext.define('amdaUI.CatalogUI', {
extend: 'Ext.container.Container',
alias: 'widget.panelCatalog',
requires: [
'Ext.ux.grid.menu.RangeMenu',
'Ext.ux.grid.FiltersFeature',
'Ext.ux.grid.filter.DateFilter',
'Ext.ux.grid.filter.NumericFilter',
'Ext.ux.grid.filter.StringFilter',
'Ext.grid.plugin.BufferedRenderer',
'amdaUI.StatisticalPlug'
],
isCatalog: true,
activeField : null,
statics: {
COL_TO_HIDE_DURATION: 'colToHideDuration'
},
constructor: function (config) {
this.init(config);
this.callParent(arguments);
this.toReconfigure = true;
if (this.object) {
this.loadObject();
}
},
setObject: function (object, toReconfigure) {
if (toReconfigure)
this.toReconfigure = true;
// set object
this.object = object;
// load object into view
this.loadObject();
// show the default duration column
this.TTGrid.headerCt.getGridColumns();
Ext.Array.each(this.TTGrid.headerCt.getGridColumns(), function (item, index, all) {
// if item is the default duration column
if (item.id == amdaUI.CatalogUI.COL_TO_HIDE_DURATION + '2') {
// show this column
item.show();
}
});
// fire the refresh event (to statistical plugin)
this.fireEvent("refresh");
// global event
myDesktopApp.EventManager.fireEvent("refresh");
},
/**
* set params description into this.object
*/
setParamInfo: function (parameters) {
var params = [];
Ext.Array.each(parameters, function (item, index) {
params[index] = item;
}, this);
this.object.set('parameters', params);
this.object.set('nbParameters', params.length);
},
/**
* update this.object from form
*/
updateObject: function () {
// get the basic form
var basicForm = this.formPanel.getForm();
var updateStatus = true;
var fieldsWithoutName = basicForm.getFields().items;
Ext.Array.each(fieldsWithoutName, function (item, index, allItems) {
if (item !== this.fieldName) {
if (!item.isValid()) {
// set update isn't allowed
updateStatus = false;
}
}
}, this);
// if the update is allowed
if (updateStatus) {
/// real object update
// update TimeTable object with the content of form
basicForm.updateRecord(this.object);
}
// return the update status
return updateStatus;
},
addInterval: function (start, stop) {
var row = this.TTGrid.getStore().getTotalCount();
var me = this;
this.TTGrid.getSelectionModel().deselectAll();
AmdaAction.addCacheInterval({'start': start, 'stop': stop, 'index': row, 'isCatalog': true}, function (result, e) {
this.status = result.status;
if (!this.TTGrid.getStore().loading) {
this.TTGrid.getStore().reload({
callback: function (records, options, success) {
me.TTGrid.getView().bufferedRenderer.scrollTo(row, false, function () {
me.TTGrid.getView().select(row);
}, me);
}
});
}
}, this);
},
updateCount: function () {
this.object.set('nbIntervals', this.TTGrid.getStore().getTotalCount());
this.formPanel.getForm().findField('nbIntervals').setValue(this.object.get('nbIntervals'));
},
generateTT: function () {
if (this.fclose()) {
Ext.Msg.confirm('Generate TT', 'Current Catalog has been modified.\nDo you want to save it to include these changes in the generated Time Table ?',
function (btn, text) {
if (btn == 'yes') {
var me = this;
// mark this.closed as true before the call to close() as that will fire the beforeclose event again
if (this.object.get('id') == "") {
// case of creation of catalog
this.saveCatalog(function () {
me.createTT(me.object.get('id'));
}, true);
} else {
// casse existing catalog
this.saveProcess(false, function () {
me.createTT(me.object.get('id'));
}, true);
}
return;
}
}, this);
} else {
this.createTT(this.object.get('id'));
return;
}
},
updateSurveyDates : function(ttObj){
var starts = [];
var stops= [];
if (this.TTGrid.getStore().getTotalCount() <= 0)
return;
reqObj = {
'typeTT': 'catalog',
}
AmdaAction.readCacheIntervals(reqObj, function(result, e)
{
if (!result) {
myDesktopApp.errorMsg(e.message);
Ext.defer(function () {
Ext.Msg.toFront()
}, 10);
return;
} else if (!result.success)
{
if (result.message)
myDesktopApp.errorMsg(result.message);
else
myDesktopApp.errorMsg('Unknown error during catalog survey dates update');
Ext.defer(function () {
Ext.Msg.toFront()
}, 10);
return;
}
Ext.Array.each(result.intervals, function (item, index) {
starts[index] = new Date(item.start);
stops[index] = new Date(item.start);
});
if(starts.length !== 0 || stops.length !== 0) {
starts.sort();
stops.sort();
s = new Date(starts[0]);
e = new Date(stops[stops.length - 1]);
s = Ext.Date.format(s, 'Y-m-d\\TH:i:s.u');
e = Ext.Date.format(e, 'Y-m-d\\TH:i:s.u');
if(! ttObj.get('surveyStart') ){
ttObj.set('surveyStart', s);
this.status.isModified = true;
}
if(! ttObj.get('surveyStop') ){
ttObj.set('surveyStop', e);
this.status.isModified = true;
}
}
});
},
createTT: function (catId) {
var ttObj = Ext.create('amdaModel.TimeTable');
var timeTabNode = Ext.create('amdaModel.TimeTableNode', {leaf: true});
ttObj.set('relatedCatalogId', catId)
creatDate = new Date(this.object.get('created'));
date = Ext.Date.format(creatDate, 'Y-m-d\\TH:i:s.u');
descr = 'Generated by CDPP/Amda Catalog Module \n' + 'From Catalog: ' + this.object.get('name') + '\nOn: ' + date + '\n';
ttObj.set('description', descr + this.object.get('description'));
ttObj.set('contact', this.object.get('contact'));
//this.updateSurveyDates(ttObj);
timeTabNode.set('object', ttObj);
var explorerTree = Ext.getCmp(amdaUI.ExplorerUI.RESRC_TAB.TREE_ID);
var ttRootNode = explorerTree.getRootNode().findChild('id', 'timeTable-treeRootNode', true);
amdaModel.InteractiveNode.preloadNodes(ttRootNode.getRootNode(),
function ()
{
// edit newNode into Parameter Module with node as contextNode
timeTabNode.editInModule();
});
},
// Convert UTC date to client local date
convertUTCDateToLocalDate: function (date) {
if (date == null) {
return date;
}
;
var newDate = new Date(date.getTime() + date.getTimezoneOffset() * 60 * 1000);
var offset = date.getTimezoneOffset() / 60;
var hours = date.getHours();
newDate.setHours(hours - offset);
return newDate;
},
onAfterInit: function (result, e)
{
var me = this;
if (!result) {
myDesktopApp.errorMsg(e.message);
Ext.defer(function () {
Ext.Msg.toFront()
}, 10);
return;
} else if (!result.success)
{
if (result.message)
myDesktopApp.errorMsg(result.message);
else
myDesktopApp.errorMsg('Unknown error during catalog cache initialisation');
Ext.defer(function () {
Ext.Msg.toFront()
}, 10);
return;
}
if (me.toReconfigure)
{
// clear filters
if (me.TTGrid.filters) {
me.TTGrid.getStore().clearFilter(true);
me.TTGrid.filters.clearFilters();
me.TTGrid.filters.destroy();
}
var fieldsConfig = [
{
name: 'start',
type: 'date',
dateFormat: 'Y-m-d\\TH:i:s.u',
convert: function (value, rec) {
if (!Ext.isDate(value)) {
return new Date(value);
}
return value;
}
},
{
name: 'stop',
type: 'date',
dateFormat: 'Y-m-d\\TH:i:s.u',
convert: function (value, rec) {
if (!Ext.isDate(value)) {
return new Date(value);
}
return value;
}
},
{
name: 'durationDay',
type: 'float',
convert: function (value, rec) {
if (rec.get('stop') && rec.get('start') && (rec.get('stop') - rec.get('start')) >= 0) {
return (rec.get('stop') - rec.get('start')) / 3600000.0/24.0;
}
},
persist: false
},
{
name: 'durationHour',
type: 'float',
convert: function (value, rec) {
if (rec.get('stop') && rec.get('start') && (rec.get('stop') - rec.get('start')) >= 0) {
return (rec.get('stop') - rec.get('start')) / 3600000.0;
}
},
persist: false
},
{
name: 'durationMin',
type: 'float',
convert: function (value, rec) {
if (rec.get('stop') && rec.get('start') && (rec.get('stop') - rec.get('start')) >= 0) {
return (rec.get('stop') - rec.get('start')) / 60000.0;
}
},
persist: false
},
{
name: 'durationSec',
type: 'float',
convert: function (value, rec) {
if (rec.get('stop') && rec.get('start') && (rec.get('stop') - rec.get('start')) >= 0) {
return (rec.get('stop') - rec.get('start')) / 1000.0;
}
},
persist: false
},
{name: 'cacheId', type: 'int'},
{name: 'isNew', type: 'boolean', defaultValue: false},
{name: 'isModified', type: 'boolean', defaultValue: false}
];
var updateDurationColumnsVisibility = function (columns, visibleId) {
Ext.Array.each(columns, function (item, index) {
// if item is a column to hide automatically
if (Ext.util.Format.substr(item.id, 0, amdaUI.CatalogUI.COL_TO_HIDE_DURATION.length) == amdaUI.CatalogUI.COL_TO_HIDE_DURATION) {
// if item isn't the column which is being declared and is not hidden
if (item.id != visibleId && !item.isHidden()) {
// hide this column
item.hide();
}
}
});
};
var columnsConfig = [
{
xtype: 'rownumberer',
width: 50,
minWidth: 50,
renderer: function (value, metaData, record) {
var msg = record.index + 1;
if (record.get('isNew') || record.get('isModified')) {
msg += ' *';
metaData.style = 'font-weight: bold'
}
return msg;
}
},
{
header: 'Start Time', dataIndex: 'start', width: 145,
editor: {xtype: 'datefield', allowBlank: false, hideTrigger: true, format: 'Y-m-d\\TH:i:s.u'},
renderer: function (value) {
if (value != null) {
if (Ext.isDate(value)) {
return Ext.Date.format(value, 'Y-m-d\\TH:i:s.u');
} else {
return Ext.Date.format(new Date(value), 'Y-m-d\\TH:i:s.u');
}
} else {
return value;
}
}
},
{
header: 'Stop Time', dataIndex: 'stop', width: 145,
editor: {xtype: 'datefield', allowBlank: false, hideTrigger: true, format: 'Y-m-d\\TH:i:s.u'},
renderer: function (value) {
if (value != null) {
if (Ext.isDate(value)) {
return Ext.Date.format(value, 'Y-m-d\\TH:i:s.u');
} else {
return Ext.Date.format(new Date(value), 'Y-m-d\\TH:i:s.u');
}
} else {
return value;
}
}
},
{
xtype: 'gridcolumn',
text: 'Duration (day)',
sortable: true,
dataIndex: 'durationDay',
width: 120,
minWidth: 50,
menuDisabled: false,
hidden: true,
id: amdaUI.CatalogUI.COL_TO_HIDE_DURATION + '1',
renderer: function (value) {
return this.dateToString(value);
},
listeners: {
beforeshow: function () {
updateDurationColumnsVisibility(this.ownerCt.getGridColumns(), amdaUI.CatalogUI.COL_TO_HIDE_DURATION + '1');
}
},
filter: {type: 'numeric'}
},
{
xtype: 'gridcolumn',
text: 'Duration (hour)',
sortable: true,
dataIndex: 'durationHour',
width: 120,
minWidth: 50,
menuDisabled: false,
hidden: true,
id: amdaUI.CatalogUI.COL_TO_HIDE_DURATION + '2',
renderer: function (value) {
return this.dateToString(value);
},
listeners: {
beforeshow: function () {
updateDurationColumnsVisibility(this.ownerCt.getGridColumns(), amdaUI.CatalogUI.COL_TO_HIDE_DURATION + '2');
}
},
filter: {type: 'numeric'}
},
{
xtype: 'gridcolumn',
text: 'Duration (Min)',
sortable: true,
dataIndex: 'durationMin',
width: 120,
minWidth: 50,
menuDisabled: false,
hidden: false,
id: amdaUI.CatalogUI.COL_TO_HIDE_DURATION + '3',
renderer: function (value) {
return this.dateToString(value);
},
listeners: {
beforeshow: function () {
updateDurationColumnsVisibility(this.ownerCt.getGridColumns(), amdaUI.CatalogUI.COL_TO_HIDE_DURATION + '3');
}
},
filter: {type: 'numeric'}
},
{
xtype: 'gridcolumn',
text: 'Duration (Sec)',
sortable: true,
dataIndex: 'durationSec',
width: 120,
minWidth: 50,
menuDisabled: false,
hidden: true,
id: amdaUI.CatalogUI.COL_TO_HIDE_DURATION + '4',
renderer: function (value) {
return Ext.util.Format.number(value, '0.000');
},
listeners: {
beforeshow: function () {
updateDurationColumnsVisibility(this.ownerCt.getGridColumns(), amdaUI.CatalogUI.COL_TO_HIDE_DURATION + '4');
}
},
filter: {type: 'numeric'}
}
];
var pramColumnWidth = 120 * (1 - 0.7 * (1 - 1 / result.parameters.length));
Ext.Array.each(result.parameters, function (obj, index) {
var field = {
name: obj.id
};
var column = {
text: obj.name,
sortable: true,
dataIndex: obj.id,
menuDisabled: false,
minWidth: 50,
paramColumn: true
};
switch (obj.type) {
case 0: //double
field = Ext.apply({}, field, {
type: 'string'
});
column = Ext.apply({}, column, {
xtype: 'gridcolumn',
width: pramColumnWidth * parseInt(obj.size),
editor: 'textfield',
filter: {type: 'numeric', menuItemCfgs: {decimalPrecision: 10}}
});
break;
case 1: //dateTime
field = Ext.apply({}, field, {
type: 'date',
dateFormat: 'Y-m-d\\TH:i:s.u',
convert: function (value, rec) {
if (!Ext.isDate(value)) {
return new Date(value);
}
return value;
}
});
column = Ext.apply({}, column, {
xtype: 'datecolumn',
width: 120,
editor: {
xtype: 'datefield',
allowBlank: false,
hideTrigger: true,
format: 'Y-m-d\\TH:i:s.u'
},
filter: {type: 'date', dateFormat: 'Y-m-d'},
renderer: function (value) {
if (value != null) {
if (Ext.isDate(value)) {
return Ext.Date.format(value, 'Y-m-d\\TH:i:s.u');
} else {
return Ext.Date.format(new Date(value), 'Y-m-d\\TH:i:s.u');
}
} else {
return value;
}
}
});
break;
case 2: //string
field = Ext.apply({}, field, {
type: 'string'
});
column = Ext.apply({}, column, {
xtype: 'gridcolumn',
width: pramColumnWidth * parseInt(obj.size),
editor: 'textfield',
renderer :function(value){
var renderedVal = value;
if(value.toLowerCase().startsWith("http://") ||value.toLowerCase().startsWith("https://")) {
renderedVal = '' + value +'';
}
return renderedVal;
},
filter: {type: 'string'}
});
break;
case 3: //int
field = Ext.apply({}, field, {
type: 'string'
});
column = Ext.apply({}, column, {
xtype: 'gridcolumn',
width: pramColumnWidth * parseInt(obj.size),
editor: 'textfield',
filter: {type: 'numeric'}
});
break;
default:
field = Ext.apply({}, field, {
type: 'string'
});
column = Ext.apply({}, column, {
xtype: 'gridcolumn',
width: pramColumnWidth * parseInt(obj.size),
editor: 'textfield',
filter: {type: 'string'}
});
}
fieldsConfig.push(field);
columnsConfig.push(column);
});
var store = Ext.create('Ext.data.Store', {
fields: fieldsConfig,
autoDestroy: false,
pageSize: 200,
buffered: true,
purgePageCount: 0,
remoteSort: true,
proxy: {
type: 'direct',
api: {read: AmdaAction.readCacheIntervals},
// remplir automatiquement tt, sharedtt , catalog, shared catalog
extraParams: {'typeTT': 'catalog'},
reader:
{
type: 'json',
root: 'intervals',
totalProperty: 'totalCount'
}
},
listeners: {
scope: me,
load: function (store, records) {
// myDesktopApp.EventManager.fireEvent('refresh');
me.TTGrid.getView().refresh();
me.TTGrid.getSelectionModel().refresh();
me.updateCount();
//Statistical plugin
this.fireEvent("refresh");
},
prefetch: function (store, records, successful, operation, eOpts) {
if (operation && (operation.action == 'read'))
{
if (operation.response && operation.response.result && operation.response.result.success)
me.status = operation.response.result.status;
}
}
}
});
me.TTGrid.reconfigure(store, columnsConfig);
if (me.TTGrid.filters) {
me.TTGrid.filters.bindStore(store);
}
}
me.TTGrid.getSelectionModel().deselectAll();
//
// // clear filters
if (me.TTGrid.filters) {
me.TTGrid.getStore().clearFilter(true);
me.TTGrid.filters.clearFilters();
}
//
// clear sort
me.TTGrid.getStore().sorters.clear();
//me.TTGrid.getStore().sorters = new Ext.util.MixedCollection();
//set cache token to the Catalog object
me.object.set('cacheToken', result.token);
me.setParamInfo(result.parameters);
me.TTGrid.getStore().load();
me.status = result.status;
//Statistical plugin
me.fireEvent("refresh");
},
/**
* load object catalog into this view
*/
loadObject: function () {
// load object into form
this.object.set('created', this.convertUTCDateToLocalDate(this.object.get('created')));
this.formPanel.getForm().loadRecord(this.object);
this.status = null;
if (this.object.get('fromPlugin') && (this.object.get('objName') != '')) {
if (this.object.get('objFormat') && this.object.get('objFormat') != '') {
//From uploaded file
AmdaAction.initObjectCacheFromUploadedFile(this.object.get('objName'), this.object.get('objFormat'), this.isCatalog, this.onAfterInit, this);
} else {
//From tmp object (ie Statistics result)
AmdaAction.initObjectCacheFromTmpObject(this.object.get('folderId'), this.object.get('objName'), this.isCatalog, this.onAfterInit, this);
}
} else {
var typeTT = myDesktopApp.getLoadedModule(myDesktopApp.dynamicModules.catalog.id).linkedNode.data.nodeType;
if (this.object.get('id') == '' && this.object.get('relatedTimeTableId') == '') {
// creating new catalog
AmdaAction.initObjectCache(this.isCatalog, this.object.get('nbParameters'), this.onAfterInit, this);
} else if (this.object.get('relatedTimeTableId') != '') {
// Generate Catalog from Time Table
var pathern = this.object.get('relatedTimeTableId').split('_')[0];
if (pathern == 'sharedtimeTable')
typeTT='sharedtimeTable';
AmdaAction.initObjectCacheFromTimeTable(this.object.get('relatedTimeTableId'), typeTT, this.object.get('nbParameters'), this.onAfterInit, this);
} else {
//From existing TT file
AmdaAction.initObjectCacheFromObject(this.object.get('id'), typeTT, this.onAfterInit, this);
}
}
//Statistical plugin
this.fireEvent("refresh");
},
checkIntervalsStatusForSave: function (onStatusOk) {
onStatusOk();
},
/*
* save method called by Save button
*/
saveProcess: function (toRename, onAfterSave, notDisplayMsg)
{
var module = myDesktopApp.getLoadedModule(myDesktopApp.dynamicModules.catalog.id);
// store / columns are the same - not needed to reconfigure grid
this.toReconfigure = false;
this.updateSurveyDates(this.object);
// if save shared catalog
if (module.contextNode && (module.contextNode.get('id') == 'sharedcatalog-treeRootNode'))
{
module.linkedNode = null;
module.createLinkedNode();
module.createObject(this.object.getJsonValues());
var obj = module.linkedNode.get('object');
// synchronisation of objects
this.object = obj;
module.linkedNode.create({notDisplayMsg: notDisplayMsg, callback: function () {
if (onAfterSave)
onAfterSave();
}, scope: this});
}
// if the name has been modified this is a creation
else if (this.fclose() || this.status && (this.status.nbFiltered > 0)) {
if (this.object.isModified('name') || this.object.get('fromPlugin')) {
// if object already has an id : it's a 'rename' of an existing
if (this.object.get('id')) {
// the context Node is the parent node of current edited one
var contextNode = module.linkedNode.parentNode;
// link a new node to the TimeTableModule
module.createLinkedNode();
// set the contextNode
module.linkedNode.set('contextNode', contextNode);
// create a new object linked
module.createObject(this.object.getJsonValues());
var obj = module.linkedNode.get('object');
// synchronisation of objects
this.object = obj;
if (toRename)
module.linkedNode.toRename = true;
}
module.linkedNode.create({callback: function () {
module.linkedNode.update({notDisplayMsg: notDisplayMsg, callback: function () {
if (onAfterSave)
onAfterSave();
}, scope: this}, "", notDisplayMsg);
}, scope: this});
} else {
//update
module.linkedNode.update({notDisplayMsg: notDisplayMsg, callback: function () {
if (onAfterSave)
onAfterSave();
}, scope: this});
}
}
},
saveCatalog: function (onAfterSave, notDisplayMsg) {
if (this.updateObject())
{
var basicForm = this.formPanel.getForm();
// if there's at least one record in the store of TTGrid
if (this.TTGrid.getStore().getTotalCount() > 0)
{
// update TimeTable object which the content of form
basicForm.updateRecord(this.object);
var me = this;
this.checkIntervalsStatusForSave(function () {
//Name validation
var module = myDesktopApp.getLoadedModule(myDesktopApp.dynamicModules.catalog.id);
if (!module)
return;
module.linkedNode.isValidName(me.fieldName.getValue(), function (res)
{
if (!res) {
me.fieldName.validFlag = 'Error during object validation';
myDesktopApp.errorMsg(me.fieldName.validFlag);
me.fieldName.validate();
return;
}
if (!res.valid) {
if (res.error) {
if (res.error.search('subtree') != -1) {
Ext.MessageBox.show({title: 'Warning',
msg: res.error + '
Do you want to overwrite it?',
width: 300,
buttons: Ext.MessageBox.OKCANCEL,
fn: me.overwriteProcess,
icon: Ext.MessageBox.WARNING,
scope: me
});
me.fieldName.validFlag = true;
} else
me.fieldName.validFlag = res.error;
} else {
me.fieldName.validFlag = 'Invalid object name';
myDesktopApp.errorMsg(me.fieldName.validFlag);
}
me.fieldName.validate();
return;
}
me.fieldName.validFlag = true;
me.fieldName.validate();
me.saveProcess(false, onAfterSave, notDisplayMsg);
});
});
} else {
Ext.Msg.alert('No intervals', 'Your catalog is invalid,
you must have at least one interval');
}
}
},
/**
* overwrite metod called by Save button
*/
overwriteProcess: function (btn) {
if (btn == 'cancel')
return;
this.fieldName.clearInvalid();
this.saveProcess(true);
},
/**
* Check if changes were made before closing window
* @return true if changes
*/
fclose: function () {
if (this.status == null)
return false;
var isDirty = this.formPanel.getForm().isDirty() || (this.status.isModified) || (this.status.nbModified > 0) || (this.status.nbNew > 0);
return isDirty;
},
onChangeStartField: function(field, newValue, oldValue){
if (field.isValid()) {
if (field.isValid() && this.activeField == 'surveyStart') {
// launch the update of duration fields
var form = this.findParentByType('form').getForm();
var stop = form.findField('surveyStop').setMinValue(newValue);
var start = form.findField('surveyStart').getValue();
var stop = form.findField('surveyStop').getValue();
if (stop <= start) {
form.findField('surveyStart').markInvalid('Start Time must be before Stop Time');
}
}
}
},
onChangeStopField: function(field, newValue, oldValue)
{
if (field.isValid() && this.activeField =='surveyStop' ) {
// launch the update of duration fields
var form = this.findParentByType('form').getForm();
var start = form.findField('surveyStart').getValue();
var stop =form.findField('surveyStop').getValue();
if ( stop <= start ) {
field.markInvalid('Stop Time must be after Start Time');
}
}
},
columnForm: function(isNew, self, me , columnInfo = null){
// Different avaible types
var types = Ext.create('Ext.data.Store', {
fields: ['type', 'name'],
data : [
{"type":2, "name":"String"},
{"type":3, "name":"Integer"},
{"type":0, "name":"Float"},
{"type":1,"name":"TIme"}
]
});
// Window for the creation of the new Column
var window = Ext.create('Ext.window.Window', {
title: (isNew) ? 'New Column' : 'Edit Column',
width: 275,
height: 210,
closable:false,
modal:true,
resizable: false,
items: [
{
xtype: 'form',
layout: 'form',
id: 'simpleForm',
frame: true,
bodyPadding: '5 5 0',
fieldDefaults: {
msgTarget: 'side',
labelWidth: 85
},
items: [{
// Name
xtype:'textfield',
fieldLabel: 'Column Name',
name: 'nameColumn',
value: (isNew) ? null : columnInfo.name,
allowBlank: false,
tooltip: 'Enter the name of the column you want to create'
},{
// Type
xtype: 'combobox',
fieldLabel: 'Data Type',
name:'typeColumn',
store:types,
allowBlank: false,
value : (isNew) ? null : columnInfo.type,
queryMode: 'local',
displayField: 'name',
valueField: 'type',
editable: false,
tooltip: 'Enter the type of data you want to put in this column'
},
{
// Size
xtype:'numberfield',
fieldLabel: 'Size',
name: 'sizeColumn',
value: (isNew) ? 1 : columnInfo.size,
maxValue: 3,
minValue: 1,
allowBlank: false,
tooltip: 'For exemple: 1 for scalar type or 3 for a vector'
},
{
// Name
xtype:'textarea',
fieldLabel: 'Description',
name: 'descriptionColumn',
height:50,
value: (isNew) ? null : columnInfo.description,
allowBlank: true,
}
],
buttons: [{
text: 'Save',
handler: function() {
// If the form is correctly filled, we continue
if(this.up('form').getForm().isValid()){
if(isNew){
var newColumnPrefix='added_param_id_';
var nbAddedColumn= 0;
Ext.each(self.TTGrid.headerCt.getGridColumns(), function(column){
if(column.dataIndex.substr(0, 15) == newColumnPrefix){
nbAddedColumn++;
}
});
AmdaAction.addColumn(newColumnPrefix+nbAddedColumn,
this.up('form').getForm().findField('nameColumn').getValue(),
this.up('form').getForm().findField('typeColumn').getValue(),
this.up('form').getForm().findField('sizeColumn').getValue(),
this.up('form').getForm().findField('descriptionColumn').getValue(),
function(result, e){
if(result){
me.toReconfigure = true;
me.onAfterInit(result);
window.close();
}
});
}
else{
var newName = null;
var newType = null;
var newSize = null;
var newDescription = null;
// Check if there is modifications
if(this.up('form').getForm().findField('nameColumn').getValue() != columnInfo.name){
newName = this.up('form').getForm().findField('nameColumn').getValue();
}
if(this.up('form').getForm().findField('typeColumn').getValue() != columnInfo.type){
newType = this.up('form').getForm().findField('typeColumn').getValue();
}
if(this.up('form').getForm().findField('sizeColumn').getValue() != columnInfo.size){
newSize = this.up('form').getForm().findField('sizeColumn').getValue();
}
if(this.up('form').getForm().findField('descriptionColumn').getValue() != columnInfo.description){
newDescription = this.up('form').getForm().findField('descriptionColumn').getValue();
}
if(newName != null || newType != null || newSize != null || newDescription != null)
{
AmdaAction.editColumn(columnInfo.id, newName, newType, newSize, newDescription, function(result, e){
if(result){
me.toReconfigure = true;
me.onAfterInit(result);
window.close();
}
});
}
else{
window.close();
}
}
}
},
},
{
// to reset the form
text: 'Reset',
handler: function() {
this.up('form').getForm().reset();
}
},
{
// To quit the window
text: 'Cancel',
handler: function() {
window.close();
}
}]
}
]
}).show();
},
init: function (config)
{
var me = this;
this.object = config.object;
this.fieldName = new Ext.form.field.Text({
fieldLabel: 'Name',
allowBlank: false,
stripCharsRe: /(^\s+|\s+$)/g,
emptyText: 'Please no spaces!',
name: 'name',
validateOnChange: false,
validateOnBlur: false,
validFlag: false,
validator: function () {
return this.validFlag;
}
});
var cellEditing = Ext.create('Ext.grid.plugin.CellEditing', {
// clicksToEdit: 2,
onEditComplete: function (ed, value, startValue) {
var me = this,
activeColumn = me.getActiveColumn(),
context = me.context,
record;
if (activeColumn) {
record = context.record;
me.setActiveEditor(null);
me.setActiveColumn(null);
me.setActiveRecord(null);
context.value = value;
if (!me.validateEdit()) {
me.editing = false;
return;
}
// Only update the record if the new value is different than the
// startValue. When the view refreshes its el will gain focus
if (!record.isEqual(value, startValue)) {
var obj = {
'cacheId': record.get('cacheId'),
'isCatalog': true,
'data': {}
};
if(activeColumn.dataIndex == "start" || activeColumn.dataIndex == "stop")
obj['data'][activeColumn.dataIndex] = Ext.Date.format(value, 'Y-m-d\\TH:i:s.u');
else
obj['data'][activeColumn.dataIndex] = value;
//Interval is modified on the server side
me.editing = true;
AmdaAction.modifyCacheInterval(obj, function (result, e) {
var module = myDesktopApp.getLoadedModule(myDesktopApp.dynamicModules.catalog.id);
if (module)
module.getUiContent().status = result.status;
if (!context.store.loading) {
context.grid.getSelectionModel().deselectAll();
context.store.reload({
callback: function (records, options, success) {
context.view.bufferedRenderer.scrollTo(context.rowIdx, true, function () {
me.fireEvent('edit', me, context);
me.editing = false;
}, me);
}
});
} else {
me.editing = false;
}
}, this);
} else
me.editing = false;
}
}
});
var filters = {
ftype: 'filters',
encode: true, // json encode the filter query
local: false,
filters: [
]
};
const self = this;
this.TTGrid = Ext.create('Ext.grid.Panel', {
height: 530,
features: [filters],
columns: [],
frame: true,
columnLines: true,
selModel: {pruneRemoved: false},
countDecimals: function (value) {
if (Math.floor(value) === value)
return 0;
return value.toString().split(".")[1].length || 0;
},
dateToString: function (value) {
ndegits = this.countDecimals(value);
if (ndegits <= 3) {
return Ext.util.Format.number(value, '0.000');
} else if (value < 0.1) {
return value.toExponential(3);
} else {
return Ext.util.Format.number(value, '0.000000');
}
},
// selType: 'cellmodel',
plugins: [cellEditing, {ptype: 'bufferedrenderer'}],
listeners: {
afterrender: function ( ) {
this.TTGrid.headerCt.resizer.tracker.gridBugFix = true;
// Adding "Delete Column" in the menu
var menu = this.TTGrid.headerCt.getMenu();
menu.on('beforeshow',function(){
var deleteName='delete_column';
var editName= 'edit_column';
var isDeleteinMenu = false;
var isEditInMenu = false;
// Is there already the delete or edit item in the menu
Ext.each(menu.items.items, function(items){
if(items.name == deleteName){
isDeleteinMenu = true;
}
if(items.name == editName){
isEditInMenu = true;
}
});
// Computing the number of parameters in the catalog
var nbParamColumns=0;
Ext.each(this.TTGrid.headerCt.getGridColumns(), function(column){
if(column.paramColumn){
nbParamColumns++
}
});
// Adding the "Edit Column" if conditions satisfied
if(!isEditInMenu){
menu.add({
text: 'Edit Column',
iconCls: 'icon-parameters',
name: editName,
handler: function(item,e) {
AmdaAction.getCatColumnInfo(menu.activeHeader.dataIndex,function(result, e){
if(result){
me.columnForm(false, self,me, result);
}
});
}
});
}
// Adding the "Delete Column" if conditions satisfied
if(!isDeleteinMenu){
menu.add({
text: 'Delete Column',
iconCls: 'icon-delete',
disabled:false,
name: deleteName,
handler: function(item,e) {
AmdaAction.deleteColumn(menu.activeHeader.dataIndex,function(result, e){
me.toReconfigure = true;
me.onAfterInit(result);
});
}
});
}
Ext.each(menu.items.items, function(item){
if(item.name == deleteName){
item.setDisabled(!menu.activeHeader.paramColumn || nbParamColumns <= 1);
}
if(item.name == editName){
item.setDisabled(!menu.activeHeader.paramColumn);
}
});
}, this);
},
scope: this
},
dockedItems: [{
xtype: 'toolbar',
items: [{
iconCls: 'icon-add',
text:'New line',
scope: this,
handler: function () {
cellEditing.cancelEdit();
var store = this.TTGrid.getStore();
var selection = this.TTGrid.getView().getSelectionModel().getSelection()[0];
var row = 0;
if (selection)
row = store.indexOf(selection) + 1;
this.TTGrid.getSelectionModel().deselectAll();
var me = this;
AmdaAction.addCacheInterval({'index': row, 'isCatalog': true}, function (result, e) {
this.status = result.status;
if (!this.TTGrid.getStore().loading) {
this.TTGrid.getStore().reload({
callback: function (records, options, success) {
me.TTGrid.getView().bufferedRenderer.scrollTo(row, false, function () {
me.TTGrid.getView().select(row);
cellEditing.startEditByPosition({row: row, column: 1});
}, me);
}
});
}
}, this);
}
},
{
iconCls: 'icon-delete',
disabled: true,
text:'Delete Line',
itemId: 'delete',
scope: this,
handler: function () {
var selection = this.TTGrid.getView().getSelectionModel().getSelection()[0];
if (selection)
{
var rowId = selection.get('cacheId');
this.TTGrid.getSelectionModel().deselectAll();
AmdaAction.removeTTCacheIntervalFromId(rowId, this.isCatalog, function (result, e) {
this.status = result.status;
if (!this.TTGrid.getStore().loading) {
this.TTGrid.getStore().reload();
}
}, this);
}
}
},
'-',{
iconCls: 'icon-add',
text:'New Column(s)',
itemId: 'column_add',
scope: this,
handler: function () {
me.columnForm(true, self,me);
}
}, '->',
{
text: 'Clear Filters',
scope: this,
handler: function () {
this.TTGrid.getStore().clearFilter(true);
this.TTGrid.filters.clearFilters();
}
}]
}]
});
this.formPanel = Ext.create('Ext.form.Panel', {
region: 'center',
layout: 'hbox',
model: 'amdaModel.Catalog',
trackResetOnLoad: true, // reset to the last loaded record
bodyStyle: {background: '#dfe8f6'},
defaults: {border: false, align: 'stretch', bodyStyle: {background: '#dfe8f6'}, padding: '3'},
fieldDefaults: {labelWidth: 80, labelAlign: 'top'},
items: [{
xtype: 'form',
flex: 1,
buttonAlign: 'left',
// title : 'Information',
layout: {type: 'vbox', pack: 'start', align: 'stretch'},
items: [
this.fieldName,
{
xtype: 'fieldcontainer',
layout: 'hbox',
items: [{
xtype: 'datefield', fieldLabel: 'Creation date',
name: 'created', disabled: true,
hideTrigger: true, format: 'Y/m/d H:i:s'
},
{xtype: 'splitter'},
{xtype: 'textfield', fieldLabel: 'Intervals', name: 'nbIntervals', disabled: true}
]
},
{
xtype:'fieldset',
columnWidth: 0.5,
title: 'Survey Period',
collapsible: true,
defaultType: 'datefield',
defaults: {anchor: '100%'},
layout: 'anchor',
items :[{
fieldLabel: 'Start Time',
name: 'surveyStart',
emptyText: 'YYYY/MM/DDThh:mm:ss.fff',
format: 'Y-m-d\\TH:i:s.u',
enforceMaxLength: true,
maxLength: 25,
labelWidth: 60,
labelAlign: 'left',
renderer: function (value) {
if (value != null) {
if (Ext.isDate(value)) {
return Ext.Date.format(value, 'Y-m-d\\TH:i:s.u');
} else {
return Ext.Date.format(new Date(value), 'Y-m-d\\TH:i:s.u');
}
} else {
return value;
}
},
listeners: {
change: this.onChangeStartField,
focus: function(field) {
this.activeField = 'surveyStart';
},
}
}, {
fieldLabel: 'Stop Time',
name: 'surveyStop',
emptyText: 'YYYY/MM/DDThh:mm:ss.fff',
format: 'Y-m-d\\TH:i:s.u',
labelAlign: 'left',
enforceMaxLength: true,
maxLength: 25,
labelWidth: 60,
align: 'left',
listeners: {
change: this.onChangeStopField,
focus: function(field) {
this.activeField = 'surveyStop';
},
}
}]
},
{
xtype: 'textarea',
name: 'contact',
fieldLabel: 'Contact',
height:50
},
{
xtype: 'textarea',
name: 'description',
fieldLabel: 'Description',
height: 150
},
{
xtype: 'component',
height: 20
}],
dockedItems: [
{
xtype: 'toolbar',
dock: 'bottom',
ui: 'footer',
height: 120,
items: [
{
type: 'button',
text: 'Save',
width: 50,
scope: this,
handler: function ()
{
this.saveCatalog();
}
}, {
type: 'button',
text: 'Reset',
width: 50,
scope: this,
handler: function () {
var module = myDesktopApp.getLoadedModule(myDesktopApp.dynamicModules.catalog.id);
// module.createLinkedNode();
// module.createObject();
this.setObject(module.getLinkedNode().get('object'), true);
}
},
{
type: 'button',
text: 'Create New Catalog',
width: 120,
scope: this,
handler: function ()
{
var module = myDesktopApp.getLoadedModule(myDesktopApp.dynamicModules.catalog.id);
if (!module)
return;
module.createLinkedNode();
module.createObject();
var obj = module.linkedNode.get('object');
var me = this;
Ext.Msg.prompt('Create catalog', 'Enter the number of columns:', function (btn, text) {
if (btn == 'ok') {
module.createLinkedNode();
module.createObject();
var obj = module.linkedNode.get('object');
var nbParam = parseInt(text);
if ((nbParam <= 0) || (nbParam > 100)) {
nbParam = 1;
}
obj.set('nbParameters', nbParam);
me.setObject(obj, true);
}
}, this);
}
}]
},
//statistical info
{
xtype: 'toolbar',
dock: 'bottom',
ui: 'footer',
items: [{
xtype: 'button',
text: 'Statistical info',
scope: this,
//dock: 'bottom',
//ui: 'footer',
handler: function () {
this.fireEvent('info', 'catalogUI');
}
},
{
type: 'button',
text: 'Visualize',
scope: this,
handler: function () {
var me = this;
myDesktopApp.getLoadedModule(myDesktopApp.dynamicModules.visu.id, true, function (module) {
module.visualize(me.object);
});
}
}
]
},
{
xtype: 'toolbar',
dock: 'bottom',
ui: 'footer',
items: [{
xtype: 'button',
text: 'Generate Time Table',
scope: this,
//dock: 'bottom',
//ui: 'footer',
handler: function () {
this.generateTT(this.object.get('id'));
}
}]},
],
},
{
xtype: 'form',
bodyStyle: {background: '#dfe8f6'},
//padding: '3',
flex: 2,
items: [this.TTGrid]
}]
});
this.TTGrid.getSelectionModel().on('selectionchange', function (selModel, selections) {
this.TTGrid.down('#delete').setDisabled(selections.length === 0);
}, this);
var myConf = {
layout: 'border',
items: [
this.formPanel,
{
xtype: 'panel',
region: 'south',
title: 'Information',
collapsible: true,
collapseMode: 'header',
height: 100,
autoHide: false,
bodyStyle: 'padding:5px',
iconCls: 'icon-information',
loader:
{
autoLoad: true,
url: helpDir + 'catalogHOWTO'
}
}
],
plugins: [{ptype: 'statisticalPlugin'}]
};
Ext.apply(this, Ext.apply(arguments, myConf));
}
});