Merge lp:~openerp-dev/openobject-client-web/6.0-opw-50873-xal into lp:openobject-client-web

Proposed by Xavier ALT
Status: Merged
Approved by: Xavier ALT
Approved revision: 4867
Merged at revision: 4880
Proposed branch: lp:~openerp-dev/openobject-client-web/6.0-opw-50873-xal
Merge into: lp:openobject-client-web
Diff against target: 322 lines (+86/-30)
9 files modified
addons/openerp/controllers/listgrid.py (+3/-1)
addons/openerp/controllers/openo2m.py (+12/-1)
addons/openerp/static/javascript/form.js (+15/-4)
addons/openerp/static/javascript/listgrid.js (+13/-1)
addons/openerp/static/javascript/m2m.js (+0/-1)
addons/openerp/static/javascript/m2o.js (+2/-2)
addons/openerp/static/javascript/o2m.js (+30/-15)
addons/openerp/static/javascript/openerp/openerp.ui.textarea.js (+1/-1)
openobject/static/javascript/openobject/openobject.dom.js (+10/-4)
To merge this branch: bzr merge lp:~openerp-dev/openobject-client-web/6.0-opw-50873-xal
Reviewer Review Type Date Requested Status
OpenERP Core Team Pending
Review via email: mp+115508@code.launchpad.net

Description of the change

Hi,

This fix Popup window stacking. Currently, all popups are stacked on the root window. If we open a many2one field, then open sub-records (many2many, one2many), those child popup should be stacked on the "many2one" popup window, otherwise we're getting wrong context and view simply crash.

Regards,
Xavier

To post a comment you must log in.
4852. By Xavier ALT

[MERGE] web: correctly get if view is editable when _terp_editable is prefixed by o2m widget name

4853. By Xavier ALT

[FIX] web: one2many field: correctly get widget by prefix for multiple one2many popup stack

4854. By Xavier ALT

[FIX] web: openerp.ui.TextArea, correctly escape textarea id otherwise jQuery won't be able to find it

4855. By Xavier ALT

[FIX] web: one2many popup, force usage of global window.top frame counter as stacking fix might use a different jQuery instance

4856. By Xavier ALT

[FIX] web: also stop the ascent on many2many form - this is a root controller containing reals _terp_model/_terp_id

4857. By Xavier ALT

[FIX] web: fix many2many size when opening from a one2many list

4858. By Xavier ALT

[FIX] web: popup width/height size calculation have to use current root window for correct stacking behaviour

4859. By Xavier ALT

[MERGE] sync with upstream

4860. By Xavier ALT

[FIX] web: fix o2m not getting all data on 3rd level

4861. By Xavier ALT

[FIX] web: fix form not submitting all data when _terp_editable is set to '1' - cause eval_domain_and_context failures

4862. By Xavier ALT

[FIX] web: one2many: remove the temporary form from DOM after submitting

  - when opening a one2many record, we append the from data within the DOM
    (as some browser might not work properly otherwise), but we HAVE TO remove
    afterward otherwise.
       Currently thoses ghost form are not remove, polluting the DOM and
   leading to problem for code getting the context from the DOM (like building
   POST args from ListView.makeArgs())

4863. By Xavier ALT

[FIX] web: one2many: uppon refresh, close popup before reload source list

  - we have to close one2many popup before refresh the source list, otherwise
    ListView.makeArgs() will include content from the popup, which is wrong as
    original list are generate without that information.

4864. By Xavier ALT

[FIX] web: listgrid: use OpenO2M controller for getting the right listgrid widget (start on 2nd level of o2m popup stack)

4865. By Xavier ALT

[FIX] web: one2many make sure we use original context and domain as view params

4866. By Xavier ALT

[FIX] web: listgrid: reload() should take value from parent not root window

4867. By Xavier ALT

[FIX] web: one2many: force building final view using *real* information

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'addons/openerp/controllers/listgrid.py'
2--- addons/openerp/controllers/listgrid.py 2012-07-18 09:35:52 +0000
3+++ addons/openerp/controllers/listgrid.py 2012-09-13 15:27:22 +0000
4@@ -22,7 +22,7 @@
5 import simplejson
6
7 import cherrypy
8-from openerp.controllers import SecuredController
9+from openerp.controllers import SecuredController, openo2m
10 from openerp.utils import rpc, TinyDict, TinyForm, TinyFormError, context_with_concurrency_info, cache
11 from openerp.widgets import listgrid, listgroup
12
13@@ -298,6 +298,8 @@
14 if params.wiz_id:
15 res = wizard.Wizard().execute(params)
16 frm = res['form']
17+ elif params.o2m and len(params.o2m.split('/')) > 1:
18+ frm = openo2m.OpenO2M().create_form(params)
19 else:
20 frm = form.Form().create_form(params)
21
22
23=== modified file 'addons/openerp/controllers/openo2m.py'
24--- addons/openerp/controllers/openo2m.py 2011-11-17 05:56:40 +0000
25+++ addons/openerp/controllers/openo2m.py 2012-09-13 15:27:22 +0000
26@@ -46,10 +46,21 @@
27 # to get proper view, first generate form using the view_params
28 vp = params.view_params
29
30+ widget_prefix, _sep, widget_name = (params.o2m or '').rpartition('/')
31+ if widget_prefix:
32+ prefix_vp = vp.chain_get(widget_prefix)
33+ if prefix_vp:
34+ vp = prefix_vp
35+
36 form = tw.form_view.ViewForm(vp, name="view_form", action="/openerp/openo2m/save")
37 cherrypy.request.terp_validators = {}
38
39- wid = form.screen.widget.get_widgets_by_name(params.o2m)[0]
40+ wid = form.screen.widget.get_widgets_by_name(widget_name)[0]
41+
42+ if widget_prefix and params.o2m:
43+ prefix_params = params.chain_get(params.o2m)
44+ if prefix_params:
45+ params.update(prefix_params)
46
47 # save view_params for later phazes
48 vp = vp.make_plain('_terp_view_params/')
49
50=== modified file 'addons/openerp/static/javascript/form.js'
51--- addons/openerp/static/javascript/form.js 2012-07-30 12:23:28 +0000
52+++ addons/openerp/static/javascript/form.js 2012-09-13 15:27:22 +0000
53@@ -69,7 +69,13 @@
54
55 if (kind == 'many2many') {
56 args['source'] = src;
57- jQuery.frame_dialog({src:openobject.http.getURL(get_form_action('/openerp/openm2m/edit', args))});
58+ jQuery.frame_dialog({
59+ src: openobject.http.getURL(get_form_action('/openerp/openm2m/edit', args))
60+ }, {}, {
61+ width: '70%',
62+ height: '90%',
63+ max_height: 700
64+ });
65 return;
66 }
67
68@@ -301,13 +307,18 @@
69 * readonly fields (default: excludes disabled fields and fields with
70 * readonly="True"
71 */
72-function getFormData(extended, include_readonly) {
73+function getFormData(extended, include_readonly, source) {
74
75 var parentNode = openobject.dom.get('_terp_list') || document.forms['view_form'];
76
77 var frm = {};
78+ var prefix = '';
79+ if (source) {
80+ prefix = source + '/';
81+ }
82
83- var is_editable = jQuery('#_terp_editable').val() == 'True';
84+ var editable = jQuery(idSelector(prefix+'_terp_editable')).val();
85+ var is_editable = (editable == 'True' || editable == '1') ? true : false;
86
87 var $fields = jQuery(parentNode).find('img[kind=picture]');
88 if (is_editable) {
89@@ -745,7 +756,7 @@
90 if (prefix[0] == '_terp_listfields') {
91 prefix.shift();
92 }
93- var params = jQuery.extend(getFormData(1, true), {
94+ var params = jQuery.extend(getFormData(1, true, options.source), {
95 '_terp_domain': options.domain,
96 '_terp_context': options.context,
97 '_terp_prefix': prefix.join('/'),
98
99=== modified file 'addons/openerp/static/javascript/listgrid.js'
100--- addons/openerp/static/javascript/listgrid.js 2012-07-30 11:08:14 +0000
101+++ addons/openerp/static/javascript/listgrid.js 2012-09-13 15:27:22 +0000
102@@ -752,6 +752,8 @@
103
104 var current_id = edit_inline ? (parseInt(edit_inline) || 0) : edit_inline;
105 var prefix = this.name == '_terp_list' ? '' : this.name + '/';
106+ var names = this.name.split('/');
107+ var parent_prefix = names.length < 2 ? '' : names.slice(0, names.length - 1).join('/') + '/';
108
109 var args = jQuery.extend(this.makeArgs(), {
110 _terp_source: this.name,
111@@ -766,7 +768,17 @@
112 jQuery.extend(args, {
113 _terp_search_domain: openobject.dom.get('_terp_search_domain').value,
114 _terp_search_data: openobject.dom.get('_terp_search_data').value,
115- _terp_filter_domain: openobject.dom.get('_terp_filter_domain').value
116+ _terp_filter_domain: openobject.dom.get('_terp_filter_domain').value,
117+ _terp_context: openobject.dom.get(prefix + '_terp_context').value,
118+ _terp_domain: openobject.dom.get(prefix + '_terp_domain').value
119+ });
120+ } else {
121+ jQuery.extend(args, {
122+ _terp_search_domain: "[]",
123+ _terp_search_data: "{}",
124+ _terp_filter_domain: "[]",
125+ _terp_context: openobject.dom.get(parent_prefix + "_terp_context").value,
126+ _terp_domain: openobject.dom.get(parent_prefix + "_terp_domain").value
127 });
128 }
129
130
131=== modified file 'addons/openerp/static/javascript/m2m.js'
132--- addons/openerp/static/javascript/m2m.js 2011-01-17 11:57:11 +0000
133+++ addons/openerp/static/javascript/m2m.js 2012-09-13 15:27:22 +0000
134@@ -184,7 +184,6 @@
135 source_id: options.source || null
136 }, {
137 width: '70%',
138- max_width: 1000,
139 height: '90%',
140 max_height: 700
141 });
142
143=== modified file 'addons/openerp/static/javascript/m2o.js'
144--- addons/openerp/static/javascript/m2o.js 2012-07-19 13:16:48 +0000
145+++ addons/openerp/static/javascript/m2o.js 2012-09-13 15:27:22 +0000
146@@ -664,8 +664,8 @@
147 var $this;
148 if(this == $) $this = $(window);
149 else $this = $(this);
150- if(window != window.top) {
151- return window.top.jQuery.m2o.apply($this[0], arguments);
152+ if(window != window.parent) {
153+ return window.parent.jQuery.m2o.apply($this[0], arguments);
154 }
155 // We're at the top-level window, $this is the window from which the
156 // original $.m2o call was performed, window being the current window
157
158=== modified file 'addons/openerp/static/javascript/o2m.js'
159--- addons/openerp/static/javascript/o2m.js 2012-06-18 12:32:01 +0000
160+++ addons/openerp/static/javascript/o2m.js 2012-09-13 15:27:22 +0000
161@@ -58,15 +58,13 @@
162
163 this.params_parent = false
164 if (this.m2o == "False"){
165- var params_parent_prefix = '';
166- if (!openobject.dom.get('_terp_model')) {
167+ var params_parent_prefix = parent_prefix;
168+ if (!openobject.dom.get(parent_prefix + '_terp_model')) {
169 // Handle case when we create a new one2many record over an unsaved
170 // parent record - in that we not do have a valid '_terp_model'
171 // within the document, so we just copy original information.
172- params_parent_prefix = '_terp_view_params/';
173- } else {
174- params_parent_prefix = parent_prefix;
175- }
176+ params_parent_prefix = '_terp_view_params/' + params_parent_prefix;
177+ }
178 this.params_parent = {
179 '_terp_view_params/_terp_model': openobject.dom.get(params_parent_prefix + '_terp_model').value,
180 '_terp_view_params/_terp_id': openobject.dom.get(params_parent_prefix + '_terp_id').value,
181@@ -175,6 +173,12 @@
182 parents.push(names.shift());
183 var prefix = parents.join('/');
184
185+ if (!openobject.dom.get(prefix+'/_terp_model')) {
186+ // allow skipping some as we only have current level - 1 datas,
187+ // so starting on 3rd level we will not have the 1st level anymore
188+ continue;
189+ }
190+
191 params['_terp_view_params/' + prefix + '/_terp_model'] = openobject.dom.get(prefix + '/_terp_model').value;
192 params['_terp_view_params/' + prefix + '/_terp_id'] = openobject.dom.get(prefix + '/_terp_id').value;
193 params['_terp_view_params/' + prefix + '/_terp_ids'] = openobject.dom.get(prefix + '/_terp_ids').value;
194@@ -190,6 +194,7 @@
195 _terp_parent_view_id: this.parent_view_id,
196 _terp_o2m: o2m_name ? o2m_name : this.name,
197 _terp_o2m_model: this.model,
198+ _terp_o2m_fullname: this.name,
199 _terp_parent_view_type: this.parent_view_type,
200 _terp_editable: readonly ? 0 : 1,
201 _terp_m2o: this.m2o
202@@ -252,7 +257,9 @@
203 * have nested o2ms somehow), as we need to get a frame we can target
204 * with a form submission.
205 */
206- var frame_counter = 0;
207+ if (window.top.$.o2m_frame_counter === undefined) {
208+ window.top.$.o2m_frame_counter = 0;
209+ }
210
211 function frame_data($this, data) {
212 return $($this.attr('frameElement')).data(data);
213@@ -268,7 +275,7 @@
214 * call.
215 */
216 function open($this, options) {
217- var frame_identifier = 'test-frame' + frame_counter++;
218+ var frame_identifier = 'test-frame' + window.top.$.o2m_frame_counter++;
219 var $frame = $.frame_dialog({
220 src: 'about:blank',
221 // never sure whether the iframe is targetted by name or by id,
222@@ -276,7 +283,7 @@
223 id: frame_identifier,
224 name: frame_identifier
225 }, {'source-window': $this[0],
226- 'list': options['_terp_o2m']
227+ 'list': options['_terp_o2m_fullname']
228 }, {
229 width: '70%',
230 height: '90%',
231@@ -296,6 +303,7 @@
232 });
233 setTimeout(function () {
234 $form.submit();
235+ $form.remove();
236 });
237 return $frame;
238 }
239@@ -345,13 +353,14 @@
240 */
241 function refresh($this, close_o2m) {
242 setTimeout(function () {
243- frame_data($this, 'source-window')
244- .ListView(frame_data($this, 'list'))
245- .reload(null, 1);
246+ var source_window = frame_data($this, 'source-window');
247+ var source_list = frame_data($this, 'list');
248 if(close_o2m) {
249+ // close popup before reloading the list, otherwise
250+ // ListView.makeArgs() will be confused by content of frame window
251 close($this);
252 }
253-
254+ source_window.ListView(source_list).reload(null, 1);
255 })
256 }
257
258@@ -391,8 +400,14 @@
259 var $this;
260 if(this == $) $this = $(window);
261 else $this = $(this);
262- if(window != window.top) {
263- return window.top.jQuery.o2m.apply($this[0], arguments);
264+ var form_controller = window.form_controller;
265+ var is_root_window = false;
266+ if (form_controller == '/openerp/openm2o' || form_controller == '/openerp/search/new' || form_controller == '/openerp/openm2m') {
267+ // stop unstacking window on M2O popup window
268+ is_root_window = true;
269+ }
270+ if(window != window.parent && !is_root_window) {
271+ return window.parent.jQuery.o2m.apply($this[0], arguments);
272 }
273 // We're at the top-level window, $this is the window from which the
274 // original $.o2m call was performed, window being the current window
275
276=== modified file 'addons/openerp/static/javascript/openerp/openerp.ui.textarea.js'
277--- addons/openerp/static/javascript/openerp/openerp.ui.textarea.js 2011-01-17 11:57:11 +0000
278+++ addons/openerp/static/javascript/openerp/openerp.ui.textarea.js 2012-09-13 15:27:22 +0000
279@@ -35,7 +35,7 @@
280 openerp.ui.TextArea.prototype = {
281
282 __init__ : function(ta) {
283- this.textarea = jQuery('textarea#' + ta)[0];
284+ this.textarea = jQuery('textarea' + idSelector(ta))[0];
285 this.gripper = DIV({'class' : 'grip'});
286
287 this.ta = this.textarea.cloneNode(true);
288
289=== modified file 'openobject/static/javascript/openobject/openobject.dom.js'
290--- openobject/static/javascript/openobject/openobject.dom.js 2011-04-08 09:24:41 +0000
291+++ openobject/static/javascript/openobject/openobject.dom.js 2012-09-13 15:27:22 +0000
292@@ -108,11 +108,11 @@
293 }
294
295 function get_width(val) {
296- return get_size(val.toString(), $(window.top).width());
297+ return get_size(val.toString(), $(window).width());
298 }
299
300 function get_height(val) {
301- return get_size(val.toString(), $(window.top).height());
302+ return get_size(val.toString(), $(window).height());
303 }
304
305 function get_size(val, available_size) {
306@@ -144,8 +144,14 @@
307 var $this;
308 if(this == $) $this = $(window);
309 else $this = $(this);
310- if(window != window.top) {
311- return window.top.jQuery.frame_dialog.apply($this[0], arguments);
312+ var form_controller = window.form_controller;
313+ var is_root_window = false;
314+ if (form_controller == '/openerp/openm2o' || form_controller == '/openerp/search/new' || form_controller == '/openerp/openm2m') {
315+ // stop unstacking window on M2O popup window, Search window 'New'
316+ is_root_window = true;
317+ }
318+ if(window != window.parent && !is_root_window) {
319+ return window.parent.jQuery.frame_dialog.apply($this[0], arguments);
320 }
321 return open($this, frame_attrs, data, options);
322 }