summaryrefslogtreecommitdiff
path: root/addons/web/static/src/js
diff options
context:
space:
mode:
Diffstat (limited to 'addons/web/static/src/js')
-rw-r--r--addons/web/static/src/js/fields/relational_fields.js13
-rw-r--r--addons/web/static/src/js/views/list/list_editable_renderer.js53
2 files changed, 59 insertions, 7 deletions
diff --git a/addons/web/static/src/js/fields/relational_fields.js b/addons/web/static/src/js/fields/relational_fields.js
index 7df5b390a2c..90c2b08e1e5 100644
--- a/addons/web/static/src/js/fields/relational_fields.js
+++ b/addons/web/static/src/js/fields/relational_fields.js
@@ -681,17 +681,16 @@ var FieldX2Many = AbstractField.extend({
var command = ev.data.changes[this.name];
// Here, we only consider 'UPDATE' commands with data, which occur
// with editable list view. In order to keep the current line in
- // edition, we call confirmChange which will reset the widgets
- // instead of re-rendering the list. 'UPDATE' commands with no data
- // can be ignored: they occur in one2manys when the record is
- // updated from a dialog and in this case, we can re-render the
- // whole subview.
+ // edition, we call confirmUpdate which will try to reset the widgets
+ // of the line being edited, and rerender the rest of the list.
+ // 'UPDATE' commands with no data can be ignored: they occur in
+ // one2manys when the record is updated from a dialog and in this
+ // case, we can re-render the whole subview.
if (command.operation === 'UPDATE' && command.data) {
var state = record.data[this.name];
var fieldNames = state.getFieldNames();
this._reset(record, ev);
- this.renderer.confirmChange(state, command.id, fieldNames, ev.initialEvent);
- return $.when();
+ return this.renderer.confirmUpdate(state, command.id, fieldNames, ev.initialEvent);
}
}
return this._super.apply(this, arguments);
diff --git a/addons/web/static/src/js/views/list/list_editable_renderer.js b/addons/web/static/src/js/views/list/list_editable_renderer.js
index 7984ebf21e1..8379ab3a891 100644
--- a/addons/web/static/src/js/views/list/list_editable_renderer.js
+++ b/addons/web/static/src/js/views/list/list_editable_renderer.js
@@ -105,6 +105,59 @@ ListRenderer.include({
});
},
/**
+ * This is a specialized version of confirmChange, meant to be called when
+ * the change may have affected more than one line (so, for example, an
+ * onchange which add/remove a few lines in a x2many. This does not occur
+ * in a normal list view)
+ *
+ * The update is more difficult when other rows could have been changed. We
+ * need to potentially remove some lines, add some other lines, update some
+ * other lines and maybe reorder a few of them. This problem would neatly
+ * be solved by using a virtual dom, but we do not have this luxury yet.
+ * So, in the meantime, what we do is basically remove every current row
+ * except the 'main' one (the row which caused the update), then rerender
+ * every new row and add them before/after the main one.
+ *
+ * @param {Object} state
+ * @param {string} id
+ * @param {string[]} fields
+ * @param {OdooEvent} ev
+ * @returns {Deferred<AbstractField[]>} resolved with the list of widgets
+ * that have been reset
+ */
+ confirmUpdate: function (state, id, fields, ev) {
+ var self = this;
+ var oldRowIndex = _.findIndex(this.state.data, {id: id});
+ this.state = state;
+ return this.confirmChange(state, id, fields, ev).then(function () {
+ // If no record with 'id' can be found in the state, the
+ // confirmChange method will have rerendered the whole view already,
+ // so no further work is necessary.
+ var record = _.findWhere(state.data, {id: id});
+ if (!record) {
+ return;
+ }
+ var $row = self.$('.o_data_row:nth(' + oldRowIndex + ')');
+ $row.nextAll('.o_data_row').remove();
+ $row.prevAll().remove();
+ var newRowIndex = _.findIndex(state.data, {id: id});
+ _.each(state.data, function (record, index) {
+ if (index === newRowIndex) {
+ return;
+ }
+ var $newRow = self._renderRow(record);
+ if (index < newRowIndex) {
+ $newRow.insertBefore($row);
+ } else {
+ $newRow.insertAfter($row);
+ }
+ });
+ if (self.currentRow !== null) {
+ self.currentRow = newRowIndex;
+ }
+ });
+ },
+ /**
* Edit a given record in the list
*
* @param {string} recordID