From 3cbfc40303dcc4e5f668050326beb6ff014bf72a Mon Sep 17 00:00:00 2001 From: David Monjoie Date: Mon, 19 Jun 2017 15:43:59 +0200 Subject: [PATCH] [FIX] web: fix m2o with show_address When the show_address option is enabled, the display_name of a partner becomes a newline concatenated version of his name and his address, so the internal value of the widget is this conglomerate. However, if one uses a keypress that does not change the value of the input in edit mode, say ESC for example, the keyup handler of this widget will compare the value in the input with its internal value. If the internal value is still the conglomerate, which is the case if the user hasn't changed the input content since switching in edit mode, we need to trim it to compare it to the actual input value, which is the "standard" display_name, ignoring the magic show_address feature which is only used in readonly. --- .../static/src/js/fields/relational_fields.js | 17 +++++-- .../tests/fields/relational_fields_tests.js | 51 +++++++++++++++++++ 2 files changed, 65 insertions(+), 3 deletions(-) diff --git a/addons/web/static/src/js/fields/relational_fields.js b/addons/web/static/src/js/fields/relational_fields.js index 35addc4a091..cf3d357c4dc 100644 --- a/addons/web/static/src/js/fields/relational_fields.js +++ b/addons/web/static/src/js/fields/relational_fields.js @@ -205,6 +205,17 @@ var FieldMany2One = AbstractField.extend({ _getSearchBlacklist: function () { return []; }, + /** + * Returns the display_name from a string which contains it but was altered + * as a result of the show_address option using a horrible hack. + * + * @private + * @param {string} value + * @returns {string} display_name without show_address mess + */ + _getDisplayName: function (value) { + return value.split('\n')[0]; + }, /** * @private * @param {string} name @@ -244,7 +255,7 @@ var FieldMany2One = AbstractField.extend({ // and hope for the best that noone tries to uses this mechanism to do // something else. if (this.nodeOptions.always_reload) { - value = value.split('\n')[0]; + value = this._getDisplayName(value); } this.$input.val(value); if (!this.autocomplete_bound) { @@ -302,7 +313,7 @@ var FieldMany2One = AbstractField.extend({ .then(function (result) { // possible selections for the m2o var values = _.map(result, function (x) { - x[1] = x[1].split("\n")[0]; + x[1] = self._getDisplayName(x[1]); return { label: _.str.escapeHTML(x[1].trim()) || data.noDisplayContent, value: x[1], @@ -478,7 +489,7 @@ var FieldMany2One = AbstractField.extend({ _onInputKeyup: function () { if (this.$input.val() === "") { this.reinitialize(false); - } else if (this.m2o_value !== this.$input.val()) { + } else if (this._getDisplayName(this.m2o_value) !== this.$input.val()) { this.floating = true; this._updateExternalButton(); } diff --git a/addons/web/static/tests/fields/relational_fields_tests.js b/addons/web/static/tests/fields/relational_fields_tests.js index b35a1e84000..3bf541b097d 100644 --- a/addons/web/static/tests/fields/relational_fields_tests.js +++ b/addons/web/static/tests/fields/relational_fields_tests.js @@ -199,6 +199,57 @@ QUnit.module('relational_fields', { form.destroy(); }); + QUnit.test('many2ones in form views with show_adress', function (assert) { + assert.expect(4); + var form = createView({ + View: FormView, + model: 'partner', + data: this.data, + arch: '
' + + '' + + '' + + '' + + '' + + '' + + '
', + mockRPC: function (route, args) { + if (args.method === 'name_get') { + return this._super(route, args).then(function (result) { + result[0][1] += '\nStreet\nCity ZIP'; + return result; + }); + } + return this._super(route, args); + }, + res_id: 1, + }); + + assert.strictEqual($('a.o_form_uri').html(), 'aaa
Street
City ZIP', + "input should have a multi-line content in readonly due to show_address"); + form.$buttons.find('.o_form_button_edit').click(); + assert.strictEqual(form.$('button.o_external_button:visible').length, 1, + "should have an open record button"); + + form.$('input.o_input').click(); + form.$('input.o_input').trigger($.Event('keyup', { + which: $.ui.keyCode.ESC, + keyCode: $.ui.keyCode.ESC, + })); + + assert.strictEqual(form.$('button.o_external_button:visible').length, 1, + "should still have an open record button"); + form.$('input.o_input').trigger('focusout'); + assert.strictEqual($('.modal button:contains(Create and edit)').length, 0, + "there should not be a quick create modal"); + + form.destroy(); + }); + QUnit.test('many2ones in form views with search more', function (assert) { assert.expect(3); this.data.partner.records.push({