Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rich text viewer | Implementation of markdown parser #1335

Merged
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
Show all changes
45 commits
Select commit Hold shift + click to select a range
5a348d0
Implemented markdown parser and added markdown value API for viewer c…
vivinkrishna-ni Jun 30, 2023
53bc3ce
Change files
vivinkrishna-ni Jun 30, 2023
590a2c8
Removed tiptap/pm and added only pm-markdown and pm-model as some pac…
vivinkrishna-ni Jun 30, 2023
68b157c
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jun 30, 2023
698f22b
Resolved some of the PR comments
vivinkrishna-ni Jul 4, 2023
8b955cb
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 4, 2023
f625d25
Resolve linting errors
vivinkrishna-ni Jul 4, 2023
5db53e9
Added node polyfills to support punycode used in the markdown-it library
vivinkrishna-ni Jul 4, 2023
c7d4d23
Added append document fragment when setting the markdown value
vivinkrishna-ni Jul 5, 2023
b503590
Cleared the inner HTML and appended the rich text content to viewer c…
vivinkrishna-ni Jul 5, 2023
7d1b9ee
Run npm install in the root directory
vivinkrishna-ni Jul 7, 2023
a713cfd
Updated UI and added storybook matrix tests
vivinkrishna-ni Jul 10, 2023
bb0d76a
Resolved some of the PR comments
vivinkrishna-ni Jul 10, 2023
41531b7
Updated the styles for nodes in viewer component
vivinkrishna-ni Jul 10, 2023
09cc91e
Renamed 'markdown' and removed `fit-to-content` attribute.
vivinkrishna-ni Jul 12, 2023
4a421cf
Resolve linting errors
vivinkrishna-ni Jul 12, 2023
4ee7a61
Changes for resolving some of the comments
vivinkrishna-ni Jul 12, 2023
0704f4c
Resolving lint error
vivinkrishna-ni Jul 12, 2023
18061a9
Moved the type/markdown-it to dependencies from dev
vivinkrishna-ni Jul 12, 2023
68298ce
Fixed issue in setting the margin style for list paragraphs
vivinkrishna-ni Jul 12, 2023
035e583
Resolve linting error
vivinkrishna-ni Jul 12, 2023
e5cff56
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 13, 2023
b579ce0
Updated the name of the viewer function and removed id
vivinkrishna-ni Jul 14, 2023
d4d9fe1
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 14, 2023
a549149
Test commit to check whether methods work on Safari browsers
vivinkrishna-ni Jul 14, 2023
8533518
Revoked the previous test commit
vivinkrishna-ni Jul 14, 2023
1246017
Resolved some of the PR comments
vivinkrishna-ni Jul 17, 2023
9a0b11e
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 17, 2023
5816a66
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 18, 2023
edbec0a
Added aftereach in the unit test cases
vivinkrishna-ni Jul 18, 2023
ff08921
Added the null assertion for markdown observable
vivinkrishna-ni Jul 18, 2023
770a349
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 19, 2023
c520616
Updated and added few test cases for markdown strings. Updated the sp…
vivinkrishna-ni Jul 19, 2023
5757830
Updated few minor changes.
vivinkrishna-ni Jul 19, 2023
351cd1e
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 20, 2023
8eff4f6
Updated package-lock.json
vivinkrishna-ni Jul 20, 2023
a29a7f9
Changes for resolving some comments
vivinkrishna-ni Jul 20, 2023
14ab812
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 21, 2023
426ee92
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 21, 2023
0b22333
Enabled normalize setting back and updated test cases accordingly.
vivinkrishna-ni Jul 21, 2023
9927fc8
Merge branch 'users/vivin/viewer-markdown-parser-implementation' of h…
vivinkrishna-ni Jul 21, 2023
71f520f
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 21, 2023
247c156
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 22, 2023
e3d9d40
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 24, 2023
bc69fb9
Merge branch 'main' into users/vivin/viewer-markdown-parser-implement…
vivinkrishna-ni Jul 25, 2023
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
rajsite marked this conversation as resolved.
Show resolved Hide resolved
"type": "patch",
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
"comment": "Implementation of markdown parser for converting markdown input to rich text content in the viewer",
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
"packageName": "@ni/nimble-components",
"email": "123377523+vivinkrishna-ni@users.noreply.github.com",
"dependentChangeType": "patch"
}
jattasNI marked this conversation as resolved.
Show resolved Hide resolved
2,451 changes: 2,026 additions & 425 deletions package-lock.json

Large diffs are not rendered by default.

3 changes: 3 additions & 0 deletions packages/nimble-components/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,7 @@
"@ni/nimble-tokens": "^6.1.0",
"@tanstack/table-core": "^8.7.0",
"@tanstack/virtual-core": "^3.0.0-beta.44",
"@tiptap/pm": "^2.0.3",
"@types/d3-array": "^3.0.4",
"@types/d3-random": "^3.0.1",
"@types/d3-scale": "^4.0.2",
Expand All @@ -82,6 +83,7 @@
"@ni/eslint-config-javascript": "^4.2.0",
"@ni/eslint-config-typescript": "^4.2.0",
"@rollup/plugin-commonjs": "^24.0.1",
"@rollup/plugin-json": "^6.0.0",
"@rollup/plugin-node-resolve": "^15.0.1",
"@rollup/plugin-replace": "^5.0.1",
"@rollup/plugin-terser": "^0.4.0",
Expand All @@ -98,6 +100,7 @@
"@storybook/html-webpack5": "^7.0.4",
"@storybook/theming": "^7.0.4",
"@types/jasmine": "^4.3.1",
"@types/markdown-it": "^12.2.3",
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
"@types/webpack-env": "^1.15.2",
"babel-loader": "^9.1.2",
"circular-dependency-plugin": "^5.2.0",
Expand Down
19 changes: 17 additions & 2 deletions packages/nimble-components/rollup.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,9 @@ import sourcemaps from 'rollup-plugin-sourcemaps';
import terser from '@rollup/plugin-terser';
import replace from '@rollup/plugin-replace';

// eslint-disable-next-line import/no-extraneous-dependencies
import json from '@rollup/plugin-json';

const umdDevelopmentPlugin = () => replace({
'process.env.NODE_ENV': JSON.stringify('development')
});
Expand All @@ -21,7 +24,13 @@ export default [
format: 'iife',
sourcemap: true
},
plugins: [umdDevelopmentPlugin(), sourcemaps(), resolve(), commonJS()]
plugins: [
umdDevelopmentPlugin(),
sourcemaps(),
resolve(),
commonJS(),
json()
]
},
{
input: 'dist/esm/all-components.js',
Expand All @@ -37,6 +46,12 @@ export default [
})
]
},
plugins: [umdProductionPlugin(), sourcemaps(), resolve(), commonJS()]
plugins: [
umdProductionPlugin(),
sourcemaps(),
resolve(),
commonJS(),
json()
]
}
];
76 changes: 75 additions & 1 deletion packages/nimble-components/src/rich-text-viewer/index.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,10 @@
import { DesignSystem, FoundationElement } from '@microsoft/fast-foundation';
import {
schema,
defaultMarkdownParser,
MarkdownParser
} from '@tiptap/pm/markdown';
import { DOMSerializer } from '@tiptap/pm/model';
import { template } from './template';
import { styles } from './styles';

Expand All @@ -11,7 +17,75 @@ declare global {
/**
* A nimble styled rich text viewer
*/
export class RichTextViewer extends FoundationElement {}
export class RichTextViewer extends FoundationElement {
/**
* @public
* @remarks
* Accessor: uses the parsing logic to convert the input markdown string to render in the component.
*/
public set markdownValue(value: string) {
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
this._markdownValue = value;
this.serializedContent = this.parseMarkdownToDOM(value);
}

/**
* @public
* @remarks
* Accessor: gets the raw markdown string.
*/
public get markdownValue(): string {
return this._markdownValue;
}

public serializedContent?: HTMLElement | DocumentFragment;
private _markdownValue = '';

/**
* @internal
*/
public override connectedCallback(): void {
super.connectedCallback();
this.appendSerializedContentToViewer();
}

/**
*
* This function takes a markdown string, parses it using the ProseMirror MarkdownParser, serializes the parsed content into a
* DOM structure using a DOMSerializer, and returns the serialized result.
*
* @internal
*/
public parseMarkdownToDOM(value: string): HTMLElement | DocumentFragment {
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
const serializer = DOMSerializer.fromSchema(schema);

/**
* It configures the tokenizer of the default Markdown parser with the 'zero' preset.
* The 'zero' preset is a configuration with no rules enabled by default to selectively enable specific rules.
* https://github.com/markdown-it/markdown-it/blob/master/lib/presets/zero.js#L1
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
*
*/
const zeroTokenizerConfiguration = defaultMarkdownParser.tokenizer.configure('zero');
const supportedTokenizerRules = zeroTokenizerConfiguration.enable([
'emphasis',
'list',
'autolink'
]);
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved

const parser = new MarkdownParser(
schema,
supportedTokenizerRules,
defaultMarkdownParser.tokens
);
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
return serializer.serializeFragment(parser.parse(value)!.content);
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
}

private appendSerializedContentToViewer(): void {
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
const viewer = this.shadowRoot?.querySelector('#viewer');
if (viewer && this.serializedContent) {
viewer.appendChild(this.serializedContent.cloneNode(true));
}
}
}

const nimbleRichTextViewer = RichTextViewer.compose({
baseName: 'rich-text-viewer',
Expand Down
31 changes: 30 additions & 1 deletion packages/nimble-components/src/rich-text-viewer/styles.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,41 @@
import { css } from '@microsoft/fast-element';
import { display } from '@microsoft/fast-foundation';
import { bodyFont, bodyFontColor } from '../theme-provider/design-tokens';
import {
bodyFont,
bodyFontColor,
bodyFontLineHeight,
linkActiveFontColor,
linkFontColor,
smallPadding
} from '../theme-provider/design-tokens';

export const styles = css`
${display('flex')}

:host {
font: ${bodyFont};
outline: none;
color: ${bodyFontColor};
padding: ${smallPadding};
width: auto;
overflow: auto;
}

p,
ol,
ul,
li {
margin-block-start: 0px;
margin-block-end: 0px;
line-height: ${bodyFontLineHeight};
}

a {
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
word-break: break-all;
color: ${linkFontColor};
}

a:active {
jattasNI marked this conversation as resolved.
Show resolved Hide resolved
color: ${linkActiveFontColor};
}
`;
Original file line number Diff line number Diff line change
Expand Up @@ -2,5 +2,7 @@ import { html } from '@microsoft/fast-element';
import type { RichTextViewer } from '.';

export const template = html<RichTextViewer>`
<template> Rich Text Viewer here. </template>
<template>
<div id="viewer"></div>
</template>
`;
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import type { RichTextViewer } from '..';

/**
* Page object for the `nimble-rich-text-viewer` component.
*/
export class RichTextViewerPageObject {
public constructor(
private readonly richTextViewerElement: RichTextViewer
) {}

public getFirstChildElementTagName(
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
element: Element | null | undefined
): string {
return element?.tagName || '';
}

public getChildElementTextContent(
element: Element | null | undefined
): string {
return element?.textContent || '';
}
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved

public getFirstChildElement(): Element | null | undefined {
vivinkrishna-ni marked this conversation as resolved.
Show resolved Hide resolved
return this.richTextViewerElement.shadowRoot?.querySelector('#viewer')
?.firstElementChild;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import {
} from '../../utilities/tests/matrix';
import { hiddenWrapper } from '../../utilities/tests/hidden';
import { richTextViewerTag } from '..';
import { richTextMarkdownString } from '../../utilities/tests/rich-text-markdown-string';

const metadata: Meta = {
title: 'Tests/Rich Text Viewer',
Expand All @@ -22,7 +23,7 @@ export default metadata;

// prettier-ignore
const component = (): ViewTemplate => html`
<${richTextViewerTag}></${richTextViewerTag}>
<${richTextViewerTag} :markdownValue="${_ => richTextMarkdownString}"></${richTextViewerTag}>
`;

export const richTextViewerThemeMatrix: StoryFn = createMatrixThemeStory(
Expand Down