Skip to content

Commit 5c1aa7f

Browse files
authored
fix: fix HTML parsing error (#54)
1 parent f3b9392 commit 5c1aa7f

File tree

3 files changed

+36
-26
lines changed

3 files changed

+36
-26
lines changed

src/MarkdownRenderer.tsx

Lines changed: 30 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -2,35 +2,48 @@ import React, { useEffect } from 'react';
22
import classNames from 'classnames';
33
import copy from 'copy-to-clipboard';
44
import mergeRefs from './utils/mergeRefs';
5-
import { iconPath as copyPath } from './icons/Copy';
5+
import { iconPath as copyPath, svgTpl } from './icons/Copy';
66
import { iconPath as checkPath } from './icons/Check';
77

88
interface MarkdownRendererProps extends React.HTMLAttributes<HTMLDivElement> {
99
children?: string | null;
1010
}
1111

12+
function appendCopyButton(container?: HTMLDivElement | null) {
13+
if (!container) {
14+
return;
15+
}
16+
17+
const button = document.createElement('button');
18+
button.className =
19+
'copy-code-button rs-btn-icon rs-btn-icon-circle rs-btn rs-btn-subtle rs-btn-xs';
20+
button.title = 'Copy code';
21+
button.innerHTML = svgTpl(copyPath);
22+
button.onclick = e => {
23+
e.preventDefault();
24+
const code = container?.querySelector('code')?.textContent;
25+
const icon = button.querySelector('.copy-icon-path');
26+
27+
icon?.setAttribute('d', checkPath);
28+
if (code) {
29+
copy(code);
30+
}
31+
32+
setTimeout(() => {
33+
icon?.setAttribute('d', copyPath);
34+
}, 2000);
35+
};
36+
container?.appendChild(button);
37+
}
38+
1239
const MarkdownRenderer = React.forwardRef(
1340
(props: MarkdownRendererProps, ref: React.Ref<HTMLDivElement>) => {
1441
const { children, className, ...rest } = props;
1542
const mdRef = React.useRef<HTMLDivElement>(null);
1643

1744
useEffect(() => {
18-
mdRef.current?.querySelectorAll('.copy-code-button').forEach(el => {
19-
el.addEventListener('click', e => {
20-
e.preventDefault();
21-
22-
const code = (el.nextElementSibling as HTMLInputElement)?.value;
23-
const icon = el.querySelector('.copy-icon-path');
24-
25-
icon?.setAttribute('d', checkPath);
26-
if (code) {
27-
copy(code);
28-
}
29-
30-
setTimeout(() => {
31-
icon?.setAttribute('d', copyPath);
32-
}, 2000);
33-
});
45+
mdRef.current?.querySelectorAll('.rcv-code-renderer').forEach((el: any) => {
46+
appendCopyButton(el);
3447
});
3548
}, []);
3649

src/icons/Copy.tsx

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,9 @@ import React from 'react';
33
export const iconPath =
44
'M320 448v40c0 13.255-10.745 24-24 24H24c-13.255 0-24-10.745-24-24V120c0-13.255 10.745-24 24-24h72v296c0 30.879 25.121 56 56 56h168zm0-344V0H152c-13.255 0-24 10.745-24 24v368c0 13.255 10.745 24 24 24h272c13.255 0 24-10.745 24-24V128H344c-13.2 0-24-10.8-24-24zm120.971-31.029L375.029 7.029A24 24 0 0 0 358.059 0H352v96h96v-6.059a24 24 0 0 0-7.029-16.97z';
55

6+
export const svgTpl = (path: string) =>
7+
`<svg stroke="currentColor" fill="currentColor" stroke-width="0" viewBox="0 0 448 512" height="1em" width="1em" xmlns="http://www.w3.org/2000/svg" class="copy-icon"><path class="copy-icon-path" d="${path}"></path></svg>`;
8+
69
function CopyIcon(props: React.SVGProps<SVGSVGElement>) {
710
return (
811
<svg

webpack-md-loader/renderer.js

Lines changed: 3 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -15,15 +15,9 @@ module.exports = (languages = defaultLanguages) => {
1515
? hl.highlight(code, { language, ignoreIllegals: true })
1616
: hl.highlightAuto(code);
1717

18-
return `<div class="rcv-highlight">
19-
<button type="button" class="copy-code-button rs-btn-icon rs-btn-icon-circle rs-btn rs-btn-subtle rs-btn-xs" title="Copy code" aria-label="Copy code" >
20-
<svg stroke="currentColor" fill="currentColor" stroke-width="0" viewBox="0 0 448 512" height="1em" width="1em" xmlns="http://www.w3.org/2000/svg">
21-
<path class="copy-icon-path" d="M320 448v40c0 13.255-10.745 24-24 24H24c-13.255 0-24-10.745-24-24V120c0-13.255 10.745-24 24-24h72v296c0 30.879 25.121 56 56 56h168zm0-344V0H152c-13.255 0-24 10.745-24 24v368c0 13.255 10.745 24 24 24h272c13.255 0 24-10.745 24-24V128H344c-13.2 0-24-10.8-24-24zm120.971-31.029L375.029 7.029A24 24 0 0 0 358.059 0H352v96h96v-6.059a24 24 0 0 0-7.029-16.97z"></path>
22-
</svg>
23-
</button>
24-
<input type="hidden" class="copy-code-input" value="${code}" />
25-
<pre><code class="${language || ''}">${value}</code></pre>
26-
</div>`;
18+
return `<div class="rcv-highlight rcv-code-renderer"><pre><code class="${
19+
language || ''
20+
}">${value}</code></pre></div>`;
2721
};
2822

2923
renderer.code = codeRenderer;

0 commit comments

Comments
 (0)