general mechanism for default css

This commit is contained in:
Julie Blanc 2026-03-08 10:38:59 +01:00
parent ec1b23d67a
commit fc227bf519
4 changed files with 126 additions and 40 deletions

View file

@ -267,71 +267,96 @@ export function useElementSettings({ margin, padding, basePopup }) {
const displayedCssOrder = [
{ css: 'font-family', group: 'font', special: true,
getValue: () => { const val = settingEnabled.font ? fontFamily.value : textDefaults.fontFamily; return val === 'sans-serif' ? 'sans-serif' : `"${val}"`; } },
getValue: () => { const val = fontFamily.value; return val === 'sans-serif' ? 'sans-serif' : `"${val}"`; } },
{ css: 'font-style', group: 'font',
getValue: () => italic.value ? 'italic' : (INLINE_DEFAULTS[currentTag.value]?.fontStyle || null),
skip: () => !italic.value && !INLINE_DEFAULTS[currentTag.value]?.fontStyle },
skip: () => !italic.value && !INLINE_DEFAULTS[currentTag.value]?.fontStyle && !hasInCss('font-style') },
{ css: 'font-weight', group: 'font',
getValue: () => bold.value ? 'bold' : (INLINE_DEFAULTS[currentTag.value]?.fontWeight || null),
skip: () => !bold.value && !INLINE_DEFAULTS[currentTag.value]?.fontWeight },
skip: () => !bold.value && !INLINE_DEFAULTS[currentTag.value]?.fontWeight && !hasInCss('font-weight') },
{ css: 'font-size', group: 'fontSize', special: true,
getValue: () => `${(settingEnabled.fontSize ? fontSize : textDefaults.fontSize).value}${(settingEnabled.fontSize ? fontSize : textDefaults.fontSize).unit}` },
getValue: () => `${fontSize.value}${fontSize.unit}` },
{ css: 'line-height', group: 'lineHeight', special: true,
getValue: () => `${(settingEnabled.lineHeight ? lineHeight : textDefaults.lineHeight).value}${(settingEnabled.lineHeight ? lineHeight : textDefaults.lineHeight).unit}` },
getValue: () => `${lineHeight.value}${lineHeight.unit}` },
{ css: 'text-align', group: 'textAlign',
getValue: () => textAlign.value,
skip: () => !settingEnabled.textAlign },
skip: () => !settingEnabled.textAlign && !hasInCss('text-align') },
{ css: 'color', group: 'color', special: true,
getValue: () => settingEnabled.color ? color.value : textDefaults.color },
getValue: () => color.value },
{ css: 'background', group: 'background',
getValue: () => background.value,
skip: () => !settingEnabled.background },
skip: () => !settingEnabled.background && !hasInCss('background') },
{ css: 'border-width', group: 'border',
getValue: () => `${borderWidth.value}${borderWidth.unit}`,
skip: () => !settingEnabled.border },
skip: () => !settingEnabled.border && !hasInCss('border-width') },
{ css: 'border-style', group: 'border',
getValue: () => borderStyle.value,
skip: () => !settingEnabled.border || borderWidth.value === 0 },
skip: () => (!settingEnabled.border && !hasInCss('border-style')) || borderWidth.value === 0 },
{ css: 'border-color', group: 'border',
getValue: () => borderColor.value,
skip: () => !settingEnabled.border || borderWidth.value === 0 },
skip: () => (!settingEnabled.border && !hasInCss('border-color')) || borderWidth.value === 0 },
{ css: 'text-decoration-line', group: 'textDecoration',
getValue: () => textDecorationLine.value,
skip: () => !settingEnabled.textDecoration },
getValue: () => textDecorationLine.value || (INLINE_DEFAULTS[currentTag.value]?.textDecorationLine || null),
skip: () => !settingEnabled.textDecoration && !INLINE_DEFAULTS[currentTag.value]?.textDecorationLine && !hasInCss('text-decoration-line') },
{ css: 'text-decoration-style', group: 'textDecoration',
getValue: () => textDecorationStyle.value,
skip: () => !settingEnabled.textDecoration },
skip: () => !settingEnabled.textDecoration && !hasInCss('text-decoration-style') },
{ css: 'text-decoration-thickness', group: 'textDecoration',
getValue: () => `${textDecorationThickness.value}${textDecorationThickness.unit}`,
skip: () => !settingEnabled.textDecoration },
skip: () => !settingEnabled.textDecoration && !hasInCss('text-decoration-thickness') },
{ css: 'text-decoration-color', group: 'textDecoration',
getValue: () => textDecorationColor.value,
skip: () => !settingEnabled.textDecoration },
skip: () => !settingEnabled.textDecoration && !hasInCss('text-decoration-color') },
{ css: 'text-underline-offset', group: 'textDecoration',
getValue: () => `${textUnderlineOffset.value}${textUnderlineOffset.unit}`,
skip: () => !settingEnabled.textDecoration },
skip: () => !settingEnabled.textDecoration && !hasInCss('text-underline-offset') },
];
const isInlineElement = computed(() => !!INLINE_DEFAULTS[currentTag.value]);
// Check if the current selector has a CSS property in the store
const hasInCss = (cssProp) => {
if (!selector.value) return false;
return !!stylesheetStore.extractValue(selector.value, cssProp);
};
const displayedCss = computed(() => {
if (!selector.value) return '';
const lines = [];
for (const entry of displayedCssOrder) {
if (entry.skip && entry.skip()) continue;
// For inline elements, skip special groups (TextSettings defaults) when toggle is OFF
if (entry.special && isInlineElement.value && !settingEnabled[entry.group]) continue;
// Exception: keep if the current tag has an inline default for this CSS property
if (entry.special && isInlineElement.value && !settingEnabled[entry.group]) {
const tagDefaults = INLINE_DEFAULTS[currentTag.value];
const cssToDefaultKey = { 'color': 'color', 'font-family': 'fontFamily' };
const defaultKey = cssToDefaultKey[entry.css];
if (!defaultKey || !tagDefaults?.[defaultKey]) continue;
}
const val = entry.getValue();
if (val === null || val === undefined) continue;
const comment = (entry.special && !settingEnabled[entry.group]) ? ' /* valeur par défaut */' : '';
// Show "valeur par défaut" only if the value actually matches the TextSettings default
let isTextDefault = false;
if (entry.special && !settingEnabled[entry.group]) {
const textDefaultValues = {
'font-family': textDefaults.fontFamily === 'sans-serif' ? 'sans-serif' : `"${textDefaults.fontFamily}"`,
'font-size': `${textDefaults.fontSize.value}${textDefaults.fontSize.unit}`,
'line-height': `${textDefaults.lineHeight.value}${textDefaults.lineHeight.unit}`,
'color': textDefaults.color,
};
isTextDefault = val === textDefaultValues[entry.css];
}
const comment = isTextDefault ? ' /* valeur par défaut */' : '';
lines.push(` ${entry.css}: ${val};${comment}`);
}
if (settingEnabled.margin) {
const showMargin = settingEnabled.margin || ['top', 'right', 'bottom', 'left'].some(s => hasInCss(`margin-${s}`));
if (showMargin) {
for (const side of ['top', 'right', 'bottom', 'left']) {
lines.push(` margin-${side}: ${margin[side].value}${margin[side].unit};`);
}
}
if (settingEnabled.padding) {
const showPadding = settingEnabled.padding || ['top', 'right', 'bottom', 'left'].some(s => hasInCss(`padding-${s}`));
if (showPadding) {
for (const side of ['top', 'right', 'bottom', 'left']) {
lines.push(` padding-${side}: ${padding[side].value}${padding[side].unit};`);
}
@ -588,25 +613,38 @@ export function useElementSettings({ margin, padding, basePopup }) {
}
}
// Fallback to TextSettings defaults only if the selector doesn't already have the value
if (!settingEnabled.font && !settingCache.font) {
const ff = stylesheetStore.extractValue('body', 'font-family');
if (ff) fontFamily.value = (typeof ff === 'string' ? ff : ff.value).replace(/['"]/g, '');
const fs = stylesheetStore.extractValue('p', 'font-style');
if (fs) italic.value = (typeof fs === 'string' ? fs : fs.value) === 'italic';
const fw = stylesheetStore.extractValue('p', 'font-weight');
if (fw) { const v = typeof fw === 'string' ? fw : fw.value; bold.value = v === 'bold' || parseInt(v) >= 700; }
if (!stylesheetStore.extractValue(selector.value, 'font-family')) {
const ff = stylesheetStore.extractValue('body', 'font-family');
if (ff) fontFamily.value = (typeof ff === 'string' ? ff : ff.value).replace(/['"]/g, '');
}
if (!stylesheetStore.extractValue(selector.value, 'font-style')) {
const fs = stylesheetStore.extractValue('p', 'font-style');
if (fs) italic.value = (typeof fs === 'string' ? fs : fs.value) === 'italic';
}
if (!stylesheetStore.extractValue(selector.value, 'font-weight')) {
const fw = stylesheetStore.extractValue('p', 'font-weight');
if (fw) { const v = typeof fw === 'string' ? fw : fw.value; bold.value = v === 'bold' || parseInt(v) >= 700; }
}
}
if (!settingEnabled.fontSize && !settingCache.fontSize) {
const data = stylesheetStore.extractValue('p', 'font-size');
if (data && data.value !== undefined) { fontSize.value = data.value; fontSize.unit = data.unit; }
if (!stylesheetStore.extractValue(selector.value, 'font-size')) {
const data = stylesheetStore.extractValue('p', 'font-size');
if (data && data.value !== undefined) { fontSize.value = data.value; fontSize.unit = data.unit; }
}
}
if (!settingEnabled.lineHeight && !settingCache.lineHeight) {
const data = stylesheetStore.extractValue('p', 'line-height');
if (data && data.value !== undefined) { lineHeight.value = data.value; lineHeight.unit = data.unit; }
if (!stylesheetStore.extractValue(selector.value, 'line-height')) {
const data = stylesheetStore.extractValue('p', 'line-height');
if (data && data.value !== undefined) { lineHeight.value = data.value; lineHeight.unit = data.unit; }
}
}
if (!settingEnabled.color && settingCache.color === null) {
const c = stylesheetStore.extractValue('body', 'color');
if (c) color.value = typeof c === 'string' ? c : c.value;
if (!stylesheetStore.extractValue(selector.value, 'color')) {
const c = stylesheetStore.extractValue('body', 'color');
if (c) color.value = typeof c === 'string' ? c : c.value;
}
}
} catch (error) {
console.error('Error loading values from stylesheet:', error);
@ -639,12 +677,19 @@ export function useElementSettings({ margin, padding, basePopup }) {
settingCache.color = null;
}
// Apply tag-based defaults (em/i → italic, strong/b → bold)
// Reset inline-specific values, then apply tag-based defaults
italic.value = ELEMENT_DEFAULTS.italic;
bold.value = ELEMENT_DEFAULTS.bold;
color.value = ELEMENT_DEFAULTS.color;
textDecorationLine.value = ELEMENT_DEFAULTS.textDecorationLine;
const tag = element.tagName.toLowerCase();
const inlineDefaults = INLINE_DEFAULTS[tag];
if (inlineDefaults) {
if (inlineDefaults.fontStyle === 'italic') italic.value = true;
if (inlineDefaults.fontWeight === 'bold') bold.value = true;
if (inlineDefaults.color) color.value = inlineDefaults.color;
if (inlineDefaults.textDecorationLine) textDecorationLine.value = inlineDefaults.textDecorationLine;
}
loadValuesFromStylesheet(true);