SVG: improve detection

This commit is contained in:
Enrico Ros
2024-11-18 08:55:27 -08:00
parent c498c31050
commit 010de2b1f1
2 changed files with 22 additions and 2 deletions
+2 -2
View File
@@ -20,7 +20,7 @@ import { useUIPreferencesStore } from '~/common/state/store-ui';
import { OVERLAY_BUTTON_RADIUS, OverlayButton, overlayButtonsActiveSx, overlayButtonsClassName, overlayButtonsTopRightSx, overlayGroupWithShadowSx, StyledOverlayButton } from '../OverlayButton';
import { RenderCodeHtmlIFrame } from './code-renderers/RenderCodeHtmlIFrame';
import { RenderCodeMermaid } from './code-renderers/RenderCodeMermaid';
import { RenderCodeSVG } from './code-renderers/RenderCodeSVG';
import { heuristicIsSVGCode, RenderCodeSVG } from './code-renderers/RenderCodeSVG';
import { RenderCodeSyntax } from './code-renderers/RenderCodeSyntax';
import { heuristicIsBlockPureHTML } from '../danger-html/RenderDangerousHtml';
import { heuristicIsCodePlantUML, RenderCodePlantUML, usePlantUmlSvg } from './code-renderers/RenderCodePlantUML';
@@ -163,7 +163,7 @@ function RenderCodeImpl(props: RenderCodeBaseProps & {
const { data: plantUmlSvgData, error: plantUmlError } = usePlantUmlSvg(renderPlantUML, code);
renderPlantUML = renderPlantUML && (!!plantUmlSvgData || !!plantUmlError);
const isSVGCode = (code.startsWith('<svg') || code.startsWith('<?xml version="1.0" encoding="UTF-8"?>\n<svg')) && code.endsWith('</svg>');
const isSVGCode = heuristicIsSVGCode(code);
const renderSVG = isSVGCode && showSVG;
const canScaleSVG = renderSVG && code.includes('viewBox="');
@@ -4,6 +4,26 @@ import type { SxProps } from '@mui/joy/styles/types';
import { Box } from '@mui/joy';
function _removePotentialComments(code: string): string {
return code.replace(/^(<!--[^>]*-->)*\s*/i, '');
}
/**
* Detects whether a string contains valid SVG trimmedCode
*/
export function heuristicIsSVGCode(trimmedCode: string): boolean {
// quick outs
if (!trimmedCode.startsWith('<') || !trimmedCode.endsWith('</svg>')) return false;
// strip HTML comments from the start of the trimmedCode
const codeWithoutInitialComments = trimmedCode.startsWith('<!--') ? _removePotentialComments(trimmedCode) : trimmedCode;
// check for standard SVG patterns
return codeWithoutInitialComments.startsWith('<svg') || codeWithoutInitialComments.startsWith('<?xml version="1.0" encoding="UTF-8"?>\\n<svg');
}
export function patchSvgString(fitScreen: boolean, svgCode?: string | null): string | null {
return fitScreen ? svgCode?.replace('<svg ', `<svg style="width: 100%; height: 100%; object-fit: contain" `) || null : svgCode || null;
}