Skip to content

Commit c63eadb

Browse files
authored
feat(yfmHtmlBlock): updated yfm-html-block (#354)
1 parent 22d0129 commit c63eadb

File tree

9 files changed

+59
-23
lines changed

9 files changed

+59
-23
lines changed

demo/RememberMode.stories.tsx

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -86,8 +86,11 @@ aside blockquote {
8686
8787
<div class="container">
8888
<div class="main">
89+
<h3 id="top">Top</h3>
8990
<p>HTML, or HyperText Markup Language, is the standard language used to create web pages. It allows developers to structure content and make it accessible and attractive to users.</p>
9091
92+
<a href="http://yandex.com">Yandex site</a>
93+
9194
<p>HTML was first developed by Tim Berners-Lee in 1991, and since then, it has gone through numerous iterations to become the versatile tool it is today. One of the core tenets of HTML is its simplicity and accessibility. By using a series of tags, you can define various elements on a webpage, such as headings, paragraphs, links, images, and more.</p>
9295
9396
<p>HTML documents are plain text files that can be created and edited with any text editor. When opened in a web browser, the HTML code is parsed and rendered to display the structured content. This is achieved through the use of various HTML elements, each represented by tags.</p>
@@ -103,6 +106,8 @@ aside blockquote {
103106
104107
<p>HTML also supports multimedia, allowing you to embed videos, audio, and interactive content. Modern HTML (HTML5) introduces several new elements and APIs to enhance functionality, making it easier for developers to create rich, interactive web experiences.</p>
105108
109+
<a href="#top">to top</a>
110+
106111
<p>In conclusion, understanding HTML is fundamental for web development. Its role in structuring and presenting content on the web is indispensable. Whether you are a beginner or a seasoned developer, mastering HTML opens the door to creating engaging and effective web pages.</p>
107112
</div>
108113

demo/hooks/useYfmHtmlBlockStyles.ts

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,8 +31,6 @@ export const useYfmHtmlBlockStyles = () => {
3131
setConfig({
3232
styles: getYfmHtmlBlockCssVariables(styles),
3333
classNames: [theme],
34-
resizePadding: 50,
35-
resizeDelay: 100,
3634
});
3735
}, [theme]);
3836

package-lock.json

Lines changed: 5 additions & 5 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -200,7 +200,7 @@
200200
},
201201
"devDependencies": {
202202
"@diplodoc/folding-headings-extension": "0.1.0",
203-
"@diplodoc/html-extension": "1.5.0",
203+
"@diplodoc/html-extension": "2.1.0",
204204
"@diplodoc/latex-extension": "1.0.3",
205205
"@diplodoc/mermaid-extension": "1.2.1",
206206
"@diplodoc/transform": "4.22.0",
@@ -275,7 +275,7 @@
275275
},
276276
"peerDependencies": {
277277
"@diplodoc/folding-headings-extension": "^0.1.0",
278-
"@diplodoc/html-extension": "^1.2.7",
278+
"@diplodoc/html-extension": "2.1.0",
279279
"@diplodoc/latex-extension": "^1.0.3",
280280
"@diplodoc/mermaid-extension": "^1.0.0",
281281
"@diplodoc/transform": "^4.5.0",

src/extensions/yfm/YfmHtmlBlock/YfmHtmlBlock.test.ts

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -29,8 +29,6 @@ describe('YfmHtmlBlock extension', () => {
2929
doc(
3030
yfmHtmlBlock({
3131
[YfmHtmlBlockAttrs.srcdoc]: 'content\n',
32-
[YfmHtmlBlockAttrs.style]: 'width:100%',
33-
[YfmHtmlBlockAttrs.frameborder]: '0',
3432
}),
3533
),
3634
));

src/extensions/yfm/YfmHtmlBlock/YfmHtmlBlockNodeView/YfmHtmlBlockView.tsx

Lines changed: 31 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,18 @@ export function generateID() {
3636
const DEFAULT_PADDING = 20;
3737
const DEFAULT_DELAY = 100;
3838

39+
const createLinkCLickHandler = (value: Element, document: Document) => (event: Event) => {
40+
event.preventDefault();
41+
const targetId = value.getAttribute('href');
42+
43+
if (targetId) {
44+
const targetElement = document.querySelector(targetId);
45+
if (targetElement) {
46+
targetElement.scrollIntoView({behavior: 'smooth'});
47+
}
48+
}
49+
};
50+
3951
const YfmHtmlBlockPreview: React.FC<YfmHtmlBlockViewProps> = ({html, onСlick, config}) => {
4052
const ref = useRef<HTMLIFrameElement>(null);
4153
const styles = useRef<Record<string, string>>({});
@@ -45,10 +57,6 @@ const YfmHtmlBlockPreview: React.FC<YfmHtmlBlockViewProps> = ({html, onСlick, c
4557
const [height, setHeight] = useState('100%');
4658

4759
useEffect(() => {
48-
resizeConfig.current = {
49-
padding: config?.resizePadding ?? DEFAULT_PADDING,
50-
delay: config?.resizeDelay ?? DEFAULT_DELAY,
51-
};
5260
setStyles(config?.styles);
5361
setClassNames(config?.classNames);
5462
}, [config, ref.current?.contentWindow?.document?.body]);
@@ -130,17 +138,35 @@ const YfmHtmlBlockPreview: React.FC<YfmHtmlBlockViewProps> = ({html, onСlick, c
130138
}
131139
};
132140

141+
// finds all relative links (href^="#") and changes their click behavior
142+
const createAnchorLinkHandlers = (type: 'add' | 'remove') => () => {
143+
const document = ref.current?.contentWindow!.document;
144+
145+
if (document) {
146+
document.querySelectorAll('a[href^="#"]').forEach((value: Element) => {
147+
const handler = createLinkCLickHandler(value, document);
148+
if (type === 'add') {
149+
value.addEventListener('click', handler);
150+
} else {
151+
value.removeEventListener('click', handler);
152+
}
153+
});
154+
}
155+
};
156+
133157
useEffect(() => {
134158
ref.current?.addEventListener('load', handleLoadIFrame);
159+
ref.current?.addEventListener('load', createAnchorLinkHandlers('add'));
135160
return () => {
136161
ref.current?.removeEventListener('load', handleLoadIFrame);
162+
ref.current?.removeEventListener('load', createAnchorLinkHandlers('remove'));
137163
};
138164
}, [html]);
139165

140166
useEffect(() => {
141167
if (ref.current) {
142168
const resizeObserver = new window.ResizeObserver(
143-
debounce(handleResizeIFrame, resizeConfig.current?.delay ?? DEFAULT_DELAY),
169+
debounce(handleResizeIFrame, DEFAULT_DELAY),
144170
);
145171
resizeObserver.observe(ref.current);
146172
}

src/extensions/yfm/YfmHtmlBlock/YfmHtmlBlockSpecs/index.tsx

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ import {YfmHtmlBlockConsts} from './const';
99
export {yfmHtmlBlockNodeName} from './const';
1010

1111
export interface YfmHtmlBlockSpecsOptions
12-
extends Omit<PluginOptions, 'runtimeJsPath' | 'containerClasses' | 'bundle'> {
12+
extends Omit<PluginOptions, 'runtimeJsPath' | 'containerClasses' | 'bundle' | 'embeddingMode'> {
1313
nodeView?: ExtensionNodeSpec['view'];
1414
}
1515

@@ -18,14 +18,23 @@ const YfmHtmlBlockSpecsExtension: ExtensionAuto<YfmHtmlBlockSpecsOptions> = (
1818
{nodeView, ...options},
1919
) => {
2020
builder
21-
.configureMd((md) => md.use(transform({bundle: false, ...options}), {}))
21+
.configureMd((md) =>
22+
md.use(
23+
transform({
24+
bundle: false,
25+
embeddingMode: 'srcdoc',
26+
...options,
27+
}),
28+
{},
29+
),
30+
)
2231
.addNode(YfmHtmlBlockConsts.NodeName, () => ({
2332
fromMd: {
2433
tokenSpec: {
2534
name: YfmHtmlBlockConsts.NodeName,
2635
type: 'node',
2736
noCloseToken: true,
28-
getAttrs: (token) => Object.fromEntries(token.attrs ?? []),
37+
getAttrs: ({content}) => ({srcdoc: content}),
2938
},
3039
},
3140
spec: {

src/extensions/yfm/YfmHtmlBlock/index.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ import {YfmHtmlBlockAction} from './YfmHtmlBlockSpecs/const';
99
import {addYfmHtmlBlock} from './actions';
1010

1111
export interface YfmHtmlBlockOptions
12-
extends Omit<PluginOptions, 'runtimeJsPath' | 'containerClasses' | 'bundle'> {
12+
extends Omit<PluginOptions, 'runtimeJsPath' | 'containerClasses' | 'bundle' | 'embeddingMode'> {
1313
useConfig?: () => IHTMLIFrameElementConfig | undefined;
1414
}
1515

src/view/hocs/withYfmHtml/index.tsx

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import React, {ComponentType, RefAttributes, forwardRef, useEffect} from 'react';
22

3-
import {useDiplodocHtml} from '@diplodoc/html-extension/react';
3+
import {useDiplodocEmbeddedContentController} from '@diplodoc/html-extension/react';
44
import {IHTMLIFrameElementConfig} from '@diplodoc/html-extension/runtime';
55

66
import type {PluginRuntime, TransformMeta} from '../withMermaid/types';
@@ -25,14 +25,14 @@ export function withYfmHtmlBlock(opts: WithYfmHtmlBlockOptions) {
2525

2626
useYfmHtmlBlockRuntime(meta, opts.runtime);
2727

28-
const yfmHtmlBlock = useDiplodocHtml();
28+
const yfmHtmlBlock = useDiplodocEmbeddedContentController();
2929

3030
useEffect(() => {
3131
if (yfmHtmlBlock) {
3232
if (yfmHtmlBlockConfig) {
3333
yfmHtmlBlock.setConfig(yfmHtmlBlockConfig);
3434
}
35-
yfmHtmlBlock.reinitialize();
35+
yfmHtmlBlock.initialize();
3636
}
3737
}, [yfmHtmlBlock, html, yfmHtmlBlockConfig]);
3838

0 commit comments

Comments
 (0)