[FIX] web_editor, *: reorder invisible elements panel at snippet move

*website

Steps to reproduce the bug:
- Add a Cover and a Picture snippet on the website.
- Change their visibility to "Conditionally".
- Change the order of the two snippets on the page either with the drag
and drop tool or with the "move up" or "move down" option.
=> Their order on the "Invisible Elements" panel has not been updated.

The problem is fixed by calling `_updateInvisibleDOM()` at the end of
`moveSnippet()` and `_onSnippetDragAndDropStop()`. Note that before this
commit, all the snippets with a conditional visibility were hidden at
the call of `_onSnippetDragAndDropStop()`. This is due to the call of
`cleanForSave()` from `_destroyEditors()`. `_onSnippetDragAndDropStop()`
has been adapted in order to, as for the "move" option, do not change
the visibility of those elements.

task-3203914

closes odoo/odoo#123027

X-original-commit: 3a023cf00812cfbbef7f3b406fbd01b74f07b7c8
Signed-off-by: Dieleman Guillaume (gdi) <gdi@odoo.com>
Signed-off-by: Colin Louis (loco) <loco@odoo.com>
This commit is contained in:
Louis (loco)
2023-06-01 09:14:05 +02:00
parent 0af5ffed31
commit 75ecaa48e6
4 changed files with 86 additions and 5 deletions
@@ -1785,6 +1785,7 @@ var SnippetsMenu = Widget.extend({
'request_editable': '_onRequestEditable',
'disable_loading_effect': '_onDisableLoadingEffect',
'enable_loading_effect': '_onEnableLoadingEffect',
"update_invisible_dom": "_onUpdateInvisibleDom",
},
// enum of the SnippetsMenu's tabs.
tabs: {
@@ -3769,6 +3770,14 @@ var SnippetsMenu = Widget.extend({
*/
_onSnippetDragAndDropStop: async function (ev) {
this.snippetEditorDragging = false;
const visibleConditionalEls = [];
for (const snippetEditor of this.snippetEditors) {
const targetEl = snippetEditor.$target[0];
if (targetEl.dataset["visibility"] === "conditional" &&
!targetEl.classList.contains("o_conditional_hidden")) {
visibleConditionalEls.push(targetEl);
}
}
const modalEl = ev.data.$snippet[0].closest('.modal');
const carouselItemEl = ev.data.$snippet[0].closest('.carousel-item');
// If the snippet is in a modal, destroy editors only in that modal.
@@ -3778,6 +3787,16 @@ var SnippetsMenu = Widget.extend({
// first slide.
await this._destroyEditors(carouselItemEl ? $(carouselItemEl) : modalEl ? $(modalEl) : null);
await this._activateSnippet(ev.data.$snippet);
// Because of _destroyEditors(), all the snippets with a conditional
// visibility are hidden. Show the ones that were visible before the
// drag and drop.
for (const visibleConditionalEl of visibleConditionalEls) {
visibleConditionalEl.classList.remove("o_conditional_hidden");
delete visibleConditionalEl.dataset["invisible"];
}
// Update the "Invisible Elements" panel as the order of invisible
// snippets could have changed on the page.
await this._updateInvisibleDOM();
},
/**
* Returns the droppable snippet from which a dropped snippet originates.
@@ -4234,6 +4253,14 @@ var SnippetsMenu = Widget.extend({
_onSnippetSearchResetClick: function () {
this._filterSnippets('');
},
/**
* Called when a child editor asks to update the "Invisible Elements" panel.
*
* @private
*/
async _onUpdateInvisibleDom() {
await this._updateInvisibleDOM();
},
_addToolbar(toolbarMode = "text") {
if (this.folded) {
return;
@@ -5426,6 +5426,9 @@ registry.SnippetMove = SnippetOptionWidget.extend({
optionName: 'StepsConnector',
name: 'move_snippet',
});
// Update the "Invisible Elements" panel as the order of invisible
// snippets could have changed on the page.
this.trigger_up("update_invisible_dom");
},
});
@@ -28,6 +28,18 @@ function checkEyeIcon(snippetName, visible) {
run: () => {}, // it is a check
};
}
function checkEyesIconAfterSave(footerIsHidden = true) {
const eyeIconChecks = [
checkEyeIcon("Header", false),
checkEyeIcon("Text - Image", true),
checkEyeIcon("Popup", false),
checkEyeIcon("Banner", true),
];
if (footerIsHidden) {
eyeIconChecks.push(checkEyeIcon("Footer", false));
}
return eyeIconChecks;
}
wTourUtils.registerWebsitePreviewTour('conditional_visibility_1', {
edition: true,
url: '/',
@@ -123,9 +135,47 @@ checkEyeIcon("Header", false),
checkEyeIcon("Banner", false),
...wTourUtils.clickOnSave(),
...wTourUtils.clickOnEditAndWaitEditMode(),
checkEyeIcon("Header", false),
checkEyeIcon("Text - Image", true),
checkEyeIcon("Popup", false),
checkEyeIcon("Banner", true),
checkEyeIcon("Footer", false),
...checkEyesIconAfterSave(),
]);
wTourUtils.registerWebsitePreviewTour("conditional_visibility_4", {
edition: true,
test: true,
url: "/",
},
[
// Click on the "Text-Image" snippet.
wTourUtils.clickOnSnippet(snippets[0]),
{
content: "Click on the 'move down' option",
trigger: "iframe we-button.o_we_user_value_widget.fa-angle-down",
},
...checkEyesIconAfterSave(),
{
content: "Check the order on the 'Invisible Elements' panel",
trigger: ".o_we_invisible_el_panel div:nth-child(3):contains('Banner')",
run: () => {}, // it is a check
},
{
content: "Toggle the visibility of the Footer",
trigger: ".o_we_invisible_el_panel .o_we_invisible_entry:contains('Footer')",
},
{
content: "Check that the footer is visible",
trigger: "iframe #wrapwrap footer",
run: () => {}, // it is a check
},
// Click on the "Banner" snippet.
wTourUtils.clickOnSnippet(snippets[1]),
{
content: "Drag the 'Banner' snippet to the end of the page",
trigger: "iframe .o_overlay_move_options .ui-draggable-handle",
run: "drag_and_drop iframe #wrapwrap footer",
},
...checkEyesIconAfterSave(false),
{
content: "Check the order on the 'Invisible Elements' panel",
trigger: ".o_we_invisible_el_panel div:nth-child(3):contains('Text - Image')",
run: () => {}, // it is a check
},
]);
+1
View File
@@ -289,6 +289,7 @@ class TestUi(odoo.tests.HttpCase):
self.start_tour(self.env['website'].get_client_action_url('/'), 'conditional_visibility_1', login='admin')
self.start_tour('/web', 'conditional_visibility_2', login='admin')
self.start_tour(self.env['website'].get_client_action_url('/'), 'conditional_visibility_3', login='admin')
self.start_tour(self.env['website'].get_client_action_url('/'), 'conditional_visibility_4', login='admin')
def test_11_website_snippet_background_edition(self):
self.env['ir.attachment'].create({