From caee0fbd542912eb26cdfbdb62aa6ab5bd62e65c Mon Sep 17 00:00:00 2001 From: Renaud Le Gac <legac@cppm.in2p3.fr> Date: Wed, 10 Oct 2012 16:27:27 +0200 Subject: [PATCH] Redesign the FilterBox as LinkedComboBox. --- models/widgets_fields.py | 11 +- static/plugin_dbui/CHANGELOG | 1 + static/plugin_dbui/src/appfilterbox.js | 32 ----- static/plugin_dbui/src/applinkedcombobox.js | 123 ++++++++++++++++++++ 4 files changed, 129 insertions(+), 38 deletions(-) delete mode 100644 static/plugin_dbui/src/appfilterbox.js create mode 100644 static/plugin_dbui/src/applinkedcombobox.js diff --git a/models/widgets_fields.py b/models/widgets_fields.py index 87c03bb3..af93efa9 100755 --- a/models/widgets_fields.py +++ b/models/widgets_fields.py @@ -28,15 +28,14 @@ fieldsModifier.merge_fields('conference_start', # fieldsModifier = dbui.FieldsModifier('foo1') fieldsModifier.configure_field('my_axis', - displayField='axis', - mode='local', - store='axesStore', - valueField='axis', - xtype='xfilterbox') + master=True, + masterField='axis', + masterStore='axesStore', + xtype='xlinkedcombobox') fieldsModifier.configure_field('my_granularity', displayField='granularity', mode='local', store='axesStore', valueField='granularity', - xtype='xfilterbox') + xtype='xlinkedcombobox') diff --git a/static/plugin_dbui/CHANGELOG b/static/plugin_dbui/CHANGELOG index 49d22d41..6a876243 100644 --- a/static/plugin_dbui/CHANGELOG +++ b/static/plugin_dbui/CHANGELOG @@ -5,6 +5,7 @@ HEAD - Improve the files organization defining the model. - Enable tab scrolling in viewport. - Add the possibility to define static store (Ext.data.ArrayStore) in the model. + - Add a new widget LinkedComboBox. 0.4.8.2 (Jul 2012) - Consolidation version diff --git a/static/plugin_dbui/src/appfilterbox.js b/static/plugin_dbui/src/appfilterbox.js deleted file mode 100644 index b484d07b..00000000 --- a/static/plugin_dbui/src/appfilterbox.js +++ /dev/null @@ -1,32 +0,0 @@ -/** - * combobox setup to filter the content of its local store - * - * @extends Ext.form.ComboBox - * - */ -Ext.namespace('App.form'); - -App.form.FilterBox = Ext.extend(App.form.ComboBox, { - - /** - * private method require by the ExtJS component model - */ - initComponent: function () { - - // construct the underlying class. DON'T MOVE - App.form.FilterBox.superclass.initComponent.call(this); - - //logic to filter the content of the store to the combobox value - this.on('select', this.onChange, this); - - }, - - /** - * Handler to catch a change in field value anf to filter the store - */ - onChange: function (combo, record, index) { - this.store.filter(this.displayField, combo.getValue()); - } -}); - -Ext.reg('xfilterbox', App.form.FilterBox); diff --git a/static/plugin_dbui/src/applinkedcombobox.js b/static/plugin_dbui/src/applinkedcombobox.js new file mode 100644 index 00000000..a56d6c5c --- /dev/null +++ b/static/plugin_dbui/src/applinkedcombobox.js @@ -0,0 +1,123 @@ +/** + * Linked combobox has been designed to solve the case with two comboboxes + * where the values of the second one depend on the select value of the + * first one. + * + * The design is based on a master and a slave combobox which are + * linked to a common store. + * + * The master shows the values which are used to filter the common store. + * Values are unique and sorted in alphabetic order. It is enough to define + * the properties master, masterField and masterStore to setup a master. + * + * A slave is a standard combobox. The store identifier should be the same + * than the masterStore. + * + * Several masters and slaves can be attached to a single store. + * + * @extends Ext.form.ComboBox + * + */ +Ext.namespace('App.form'); + +App.form.LinkedComboBox = Ext.extend(Ext.form.ComboBox, { + + /** + * @cfg {Boolean] master true for a master combobox. default is false. + */ + master: false, + + /** + * @cfg {String] masterField field of the common store display in the combobox + */ + masterField: null, + + /** + * @cfg {String] masterStore identifier of the store used by masters and slave + */ + masterStore: null, + + /** + * private method require by the ExtJS component model + */ + initComponent: function () { + + + // configure a master combobox. + // create a local store containing the values which can be used + // to filter the master store + if (this.master) { + + this.mode = 'local'; + this.store = []; + this.masterStore = App.getStore(this.masterStore); + this.masterStore.each(this.fillData, this); + this.store.sort(); + this.triggerAction = 'all'; + + // configure a slave combobox + } else { + + this.store = App.getStore(this.store); + this.triggerAction = 'all'; + } + + // construct the underlying class. DON'T MOVE + App.form.LinkedComboBox.superclass.initComponent.call(this); + + // logic to filter the content of the master store + if (this.master) { + this.on('select', this.filterMasterStore, this); + + // logic to update the content of a slave + } else { + this.store.on('datachanged', this.onDataChanged, this); + } + }, + + /** + * Helper method to extract the master values to filter the common store. + * + * @param {Ext.data.Record} record + */ + fillData: function (record) { + var i, + value = record.get(this.masterField); + + // initialise the list + if (this.store.length === 0) { + this.store.push(value); + return; + } + + // avoid duplicate entries + for (i = 0; i < this.store.length; i += 1) { + if (value === this.store[i]) { + return; + } + } + this.store.push(value); + }, + + /** + * Helper method to filter the master store + * + * @param {Ext.form.combobox} combo + * @param {Ext.data.Record} record + * @param {Integer} index + */ + filterMasterStore: function (combo, record, index) { + this.masterStore.filter(this.masterField, combo.getValue()); + }, + + /** + * Helper method to update the combo box content and to select + * the first value of the filtered store + */ + onDataChanged: function () { + var value = this.store.getAt(0).get(this.displayField); + this.setValue(value); + } +}); + +Ext.reg('xlinkedcombobox', App.form.LinkedComboBox); -- GitLab