[FIX] web_editor, *: prevent blocked UI when original image not found
*: website When the user uploads an image and remove the original image, some image options continue to work thanks to a backend fallback on another image. Unfortunately, this fallback is not available for images coming from unsplash. This commit fixes this issue by preventing the UI to be blocked when the original image is not found. Steps to reproduce the bug: - Activate the developer mode - Configure Unsplash in the settings - Add a Cover block on a page - Replace the background image with an unsplash image - Save - Edit the page and via the media dialog, remove the original image => The options on the image cannot start anymore. opw-3636499 opw-3474103 closes odoo/odoo#148197 X-original-commit: 3b0ac160a800f70ae965b60110e83e41655bca5f Signed-off-by: Romain Derie (rde) <rde@odoo.com> Signed-off-by: Guillaume Dieleman (gdi) <gdi@odoo.com>
This commit is contained in:
@@ -349,12 +349,29 @@ export async function applyModifications(img, dataOptions = {}) {
|
||||
* @param {String} src URL of the image to load
|
||||
* @param {HTMLImageElement} [img] img element in which to load the image
|
||||
* @returns {Promise<HTMLImageElement>} Promise that resolves to the loaded img
|
||||
* or a placeholder image if the src is not found.
|
||||
*/
|
||||
export function loadImage(src, img = new Image()) {
|
||||
const handleImage = (source, resolve, reject) => {
|
||||
img.addEventListener("load", () => resolve(img), {once: true});
|
||||
img.addEventListener("error", reject, {once: true});
|
||||
img.src = source;
|
||||
};
|
||||
// The server will return a placeholder image with the following src.
|
||||
const placeholderHref = "/web/image/__odoo__unknown__src__/";
|
||||
|
||||
return new Promise((resolve, reject) => {
|
||||
img.addEventListener('load', () => resolve(img), {once: true});
|
||||
img.addEventListener('error', reject, {once: true});
|
||||
img.src = src;
|
||||
fetch(src)
|
||||
.then(response => {
|
||||
if (!response.ok) {
|
||||
src = placeholderHref;
|
||||
}
|
||||
handleImage(src, resolve, reject);
|
||||
})
|
||||
.catch(error => {
|
||||
src = placeholderHref;
|
||||
handleImage(src, resolve, reject);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
@@ -2,6 +2,24 @@
|
||||
|
||||
import wTourUtils from "@website/js/tours/tour_utils";
|
||||
|
||||
const wallRaceConditionClass = "image_wall_race_condition";
|
||||
const preventRaceConditionSteps = [{
|
||||
content: "Wait a few ms to avoid race condition",
|
||||
// Ensure the class is remove from previous call of those steps
|
||||
trigger: `body:not(.${wallRaceConditionClass})`,
|
||||
run() {
|
||||
setTimeout(() => {
|
||||
document.body.classList.add(wallRaceConditionClass);
|
||||
}, 500);
|
||||
}
|
||||
}, {
|
||||
content: "Check the race condition class is added after a few ms",
|
||||
trigger: `body.${wallRaceConditionClass}`,
|
||||
run() {
|
||||
document.body.classList.remove(wallRaceConditionClass);
|
||||
}
|
||||
}];
|
||||
|
||||
const selectSignImageStep = {
|
||||
content: "Click on image 14",
|
||||
extra_trigger: ".o_we_customize_panel:not(:has(.snippet-option-GalleryElement))",
|
||||
@@ -9,7 +27,13 @@ const selectSignImageStep = {
|
||||
};
|
||||
// Without reselecting the image, the tour manages to click on the
|
||||
// move button before the active image is updated.
|
||||
const reselectSignImageSteps = [{
|
||||
|
||||
// We need to wait a few ms before clicking on the footer because after
|
||||
// clicking on reposition option, there may be a delay during the click on
|
||||
// another block would be ignored.
|
||||
const reselectSignImageSteps = [
|
||||
...preventRaceConditionSteps,
|
||||
{
|
||||
content: "Select footer",
|
||||
trigger: "iframe footer",
|
||||
}, selectSignImageStep];
|
||||
|
||||
Reference in New Issue
Block a user