Skip to content
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.

Commit 81524c6

Browse files
committedMar 24, 2025
image gallery edit interaction
1 parent 6e5c893 commit 81524c6

9 files changed

+97
-19
lines changed
 

‎addons/html_builder/__manifest__.py

+8
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@
4444
('remove', 'html_builder/static/src/website_preview/**/*'),
4545
('remove', 'html_builder/static/src/website_mass_mailing/**/*'),
4646
('remove', 'html_builder/static/src/website_builder/plugins/website_edit_service.js'),
47+
('remove', 'html_builder/static/src/interactions/**/*'),
4748
],
4849
'html_builder.inside_builder_style': [
4950
('include', 'web._assets_helpers'),
@@ -66,6 +67,13 @@
6667
'html_builder/static/tests/**/*',
6768
('include', 'html_builder.assets'),
6869
],
70+
'web.assets_frontend': [
71+
'html_builder/static/src/interactions/**/*',
72+
('remove', 'html_builder/static/src/interactions/**/*.edit.*'),
73+
],
74+
'website.assets_edit_frontend': [
75+
'html_builder/static/src/interactions/**/*.edit.*',
76+
],
6977
},
7078
'license': 'LGPL-3',
7179
}

‎addons/html_builder/static/src/builder.js

+1
Original file line numberDiff line numberDiff line change
@@ -119,6 +119,7 @@ export class Builder extends Component {
119119
replaceSnippet: async (snippet) => await this.snippetModel.replaceSnippet(snippet),
120120
saveSnippet: (snippetEl, cleanForSaveHandlers) =>
121121
this.snippetModel.saveSnippet(snippetEl, cleanForSaveHandlers),
122+
getShared: () => this.editor.shared,
122123
},
123124
this.env.services
124125
);

‎addons/html_builder/static/src/core/save_plugin.js

+17
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,23 @@ export class SavePlugin extends Plugin {
1212

1313
resources = {
1414
handleNewRecords: this.handleMutations,
15+
// Resource definitions:
16+
before_save_handlers: [
17+
// () => {
18+
// called at the very beginning of the save process
19+
// }
20+
],
21+
clean_for_save_handlers: [
22+
// ({root, preserveSelection = false}) => {
23+
// clean DOM before save (leaving edit mode)
24+
// root is the clone of a node that was o_dirty
25+
// }
26+
],
27+
save_handlers: [
28+
// () => {
29+
// called at the very end of the save process
30+
// }
31+
],
1532
};
1633

1734
async save(isTranslation) {
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
import { Interaction } from "@web/public/interaction";
2+
import { registry } from "@web/core/registry";
3+
4+
export class ImageGalleryEdit extends Interaction {
5+
static selector = ".s_image_gallery";
6+
dynamicContent = {
7+
".o_empty_gallery_alert": {
8+
"t-on-click": this.onAddImage.bind(this),
9+
},
10+
};
11+
setup() {
12+
const containerEl = this.el.querySelector(
13+
".container, .container-fluid, .o_container_small"
14+
);
15+
this.renderAt("html_builder.empty_image_gallery_alert", {}, containerEl);
16+
}
17+
onAddImage() {
18+
const applySpec = { editingElement: this.el };
19+
this.services["website_edit"].applyAction("addImage", applySpec);
20+
}
21+
}
22+
23+
registry.category("public.interactions.edit").add("html_builder.image_gallery_edit", {
24+
Interaction: ImageGalleryEdit,
25+
});
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<templates xml:space="preserve">
3+
4+
<t t-name="html_builder.empty_image_gallery_alert">
5+
<div class="alert alert-info o_empty_gallery_alert text-center o_not_editable" contentEditable="false">
6+
<i class="fa fa-plus-circle"/>
7+
<span class="o_add_images"> Add Images</span>
8+
</div>
9+
</t>
10+
11+
</templates>

‎addons/html_builder/static/src/website_builder/plugins/edit_interaction_plugin.js

+3-8
Original file line numberDiff line numberDiff line change
@@ -3,12 +3,12 @@ import { registry } from "@web/core/registry";
33

44
export class EditInteractionPlugin extends Plugin {
55
static id = "edit_interaction";
6-
static dependencies = ["history"];
76

87
resources = {
98
normalize_handlers: this.restartInteractions.bind(this),
109
option_visibility_updated: this.restartInteractions.bind(this),
1110
content_manually_updated_handlers: this.restartInteractions.bind(this),
11+
before_save_handlers: () => this.stopInteractions(),
1212
};
1313

1414
setup() {
@@ -20,17 +20,12 @@ export class EditInteractionPlugin extends Plugin {
2020
{ once: true }
2121
);
2222
const event = new CustomEvent("edit_interaction_plugin_loaded");
23-
event.historyCallbacks = {
24-
ignoreDOMMutations: this.dependencies.history.ignoreDOMMutations,
25-
};
23+
event.shared = this.config.getShared();
2624
window.parent.document.dispatchEvent(event);
2725
}
2826
destroy() {
2927
this.websiteEditService?.uninstallPatches?.();
30-
}
31-
32-
destroy() {
33-
this.stopInteractions(this.editable);
28+
this.stopInteractions();
3429
}
3530

3631
updateEditInteraction({ detail: { websiteEditService } }) {
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
.s_image_gallery {
2+
&:has(.img) .o_empty_gallery_alert {
3+
display: none;
4+
}
5+
.o_empty_gallery_alert {
6+
.o_add_images {
7+
cursor: pointer;
8+
}
9+
}
10+
}

‎addons/html_builder/static/src/website_builder/plugins/options/image_gallery_option_plugin.js

+1-10
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,6 @@ class ImageGalleryOption extends Plugin {
1616
builder_actions: this.getActions(),
1717
system_classes: ["o_empty_gallery_alert"],
1818
clean_for_save_handlers: this.cleanForSave.bind(this),
19-
normalize_handlers: this.updateAlertBanner.bind(this),
2019
on_reorder_items_handlers: this.reorderGalleryItems.bind(this),
2120
on_remove_handlers: this.onRemove.bind(this),
2221
after_remove_handlers: this.afterRemove.bind(this),
@@ -70,20 +69,12 @@ class ImageGalleryOption extends Plugin {
7069
}
7170

7271
cleanForSave({ root }) {
72+
// TODO This should not be needed if interaction's lifecycle worked.
7373
for (const emptyGalleryAlert of root.querySelectorAll(".o_empty_gallery_alert")) {
7474
emptyGalleryAlert.remove();
7575
}
7676
}
7777

78-
updateAlertBanner() {
79-
const imageGalleries = this.document.querySelectorAll(".s_image_gallery");
80-
for (const imageGallery of imageGalleries) {
81-
const container = this.getContainer(imageGallery);
82-
if (!container.querySelector("img") && !container.querySelector(".alert")) {
83-
this.insertEmptyGalleryAlert(container);
84-
}
85-
}
86-
}
8778
reorderGalleryItems({ elementToReorder, position, optionName }) {
8879
if (optionName === "GalleryImageList") {
8980
const editingGalleryElement = elementToReorder.closest(".s_image_gallery");

‎addons/html_builder/static/src/website_builder/plugins/website_edit_service.js

+21-1
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ registry.category("services").add("website_edit", {
5050
let editMode = false;
5151
const patches = [];
5252
const historyCallbacks = {};
53+
const shared = {};
5354

5455
const update = (target, mode) => {
5556
// editMode = true;
@@ -133,13 +134,31 @@ registry.category("services").add("website_edit", {
133134
}
134135
patches.length = 0;
135136
};
137+
const applyAction = (actionId, spec) => {
138+
const action = shared.builderActions.getAction(actionId);
139+
shared.operation.next(
140+
() => {
141+
action.apply(spec);
142+
shared.history.addStep();
143+
},
144+
{
145+
load: async () => {
146+
if (action.load) {
147+
const loadResult = await action.load(spec);
148+
spec.loadResult = loadResult;
149+
}
150+
},
151+
}
152+
);
153+
};
136154

137155
const websiteEditService = {
138156
isEditingTranslations,
139157
update,
140158
stop,
141159
installPatches,
142160
uninstallPatches,
161+
applyAction,
143162
};
144163

145164
// Transfer the iframe website_edit service to the EditInteractionPlugin
@@ -151,7 +170,8 @@ registry.category("services").add("website_edit", {
151170
},
152171
})
153172
);
154-
Object.assign(historyCallbacks, ev.historyCallbacks);
173+
Object.assign(shared, ev.shared);
174+
historyCallbacks.ignoreDOMMutations = shared.history.ignoreDOMMutations;
155175
});
156176

157177
return websiteEditService;

0 commit comments

Comments
 (0)
Please sign in to comment.