[FIX] web_editor: fix media dialog's svg upload
Before this commit, the media dialog was not handling properly the upload of svg files from the media library: a whole part of the original ImageWidget was missing in the converted media dialog from [1], which was converting the svg with the appropriate color codes from the color palette, to allow for color customization. See original file from 15.4: web_editor/static/src/js/widgets/media.js. Also, it was not displaying those svg correctly with the appropriate background. This commit fixes those issues by adding back the code handling the dynamic colors detection and the background css rule. [1]: https://github.com/odoo/odoo/commit/31cc10b91dc7762e23b4bde9b945be0c4ce3fe3b task-2687506 Part-of: odoo/odoo#95955
This commit is contained in:
@@ -1,7 +1,7 @@
|
||||
/** @odoo-module */
|
||||
|
||||
import { useService } from '@web/core/utils/hooks';
|
||||
import { getCSSVariableValue } from 'web_editor.utils';
|
||||
import { getCSSVariableValue, DEFAULT_PALETTE } from 'web_editor.utils';
|
||||
import { Attachment, FileSelector, IMAGE_MIMETYPES, IMAGE_EXTENSIONS } from './file_selector';
|
||||
|
||||
const { useRef, useState, useEffect } = owl;
|
||||
@@ -23,7 +23,10 @@ export class AutoResizeImage extends Attachment {
|
||||
}, () => []);
|
||||
}
|
||||
|
||||
onImageLoaded() {
|
||||
async onImageLoaded() {
|
||||
if (this.props.onLoaded) {
|
||||
await this.props.onLoaded(this.image.el);
|
||||
}
|
||||
const aspectRatio = this.image.el.offsetWidth / this.image.el.offsetHeight;
|
||||
const width = aspectRatio * this.props.minRowHeight;
|
||||
this.container.el.style.flexGrow = width;
|
||||
@@ -254,6 +257,37 @@ export class ImageSelector extends FileSelector {
|
||||
return imageEl;
|
||||
}));
|
||||
}
|
||||
|
||||
/**
|
||||
* This converts the colors of an svg coming from the media library to
|
||||
* the palette's ones, and make them dynamic.
|
||||
*
|
||||
* @param {HTMLElement} imgEl
|
||||
* @param {Object} media
|
||||
* @returns
|
||||
*/
|
||||
async onLibraryImageLoaded(imgEl, media) {
|
||||
const mediaUrl = imgEl.src;
|
||||
try {
|
||||
const response = await fetch(mediaUrl);
|
||||
if (response.headers.get('content-type') === 'image/svg+xml') {
|
||||
const svg = await response.text();
|
||||
const dynamicColors = {};
|
||||
const combinedColorsRegex = new RegExp(Object.values(DEFAULT_PALETTE).join('|'), 'gi');
|
||||
svg.replace(combinedColorsRegex, match => {
|
||||
const colorId = Object.keys(DEFAULT_PALETTE).find(key => DEFAULT_PALETTE[key] === match.toUpperCase());
|
||||
const colorKey = 'c' + colorId
|
||||
dynamicColors[colorKey] = getCSSVariableValue('o-color-' + colorId);
|
||||
});
|
||||
if (Object.keys(dynamicColors).length) {
|
||||
media.isDynamicSVG = true;
|
||||
media.dynamicColors = dynamicColors;
|
||||
}
|
||||
}
|
||||
} catch (_e) {
|
||||
console.error('CORS is misconfigured on the API server, image will be treated as non-dynamic.');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ImageSelector.mediaSpecificClasses = ['img', 'img-fluid', 'o_we_custom_image'];
|
||||
|
||||
@@ -49,7 +49,8 @@
|
||||
altDescription="media.tooltip"
|
||||
minRowHeight="MIN_ROW_HEIGHT"
|
||||
selected="this.selectedMediaIds.includes(media.id)"
|
||||
onImageClick="() => this.onClickMedia(media)"/>
|
||||
onImageClick="() => this.onClickMedia(media)"
|
||||
onLoaded="(imgEl) => this.onLibraryImageLoaded(imgEl, media)"/>
|
||||
</t>
|
||||
</t>
|
||||
<!-- 20 placeholders is just enough for a 5K screen, change this if ImageWidget.MIN_ROW_HEIGHT changes -->
|
||||
|
||||
@@ -38,8 +38,12 @@ $min-row-height: 128;
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
img {
|
||||
width: 100%;
|
||||
.o_we_media_dialog_img_wrapper {
|
||||
@extend %o-preview-alpha-background;
|
||||
|
||||
img {
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user