@ni/nimble-components 24.1.9 → 24.1.11
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/all-components-bundle.js +129 -112
- package/dist/all-components-bundle.js.map +1 -1
- package/dist/all-components-bundle.min.js +4284 -4294
- package/dist/all-components-bundle.min.js.map +1 -1
- package/dist/esm/anchor/styles.js +56 -68
- package/dist/esm/anchor/styles.js.map +1 -1
- package/dist/esm/anchor-menu-item/index.js +1 -15
- package/dist/esm/anchor-menu-item/index.js.map +1 -1
- package/dist/esm/breadcrumb-item/styles.js +1 -1
- package/dist/esm/breadcrumb-item/styles.js.map +1 -1
- package/dist/esm/rich-text/models/markdown-parser.d.ts +1 -0
- package/dist/esm/rich-text/models/markdown-parser.js +10 -2
- package/dist/esm/rich-text/models/markdown-parser.js.map +1 -1
- package/dist/esm/rich-text/viewer/styles.js +7 -4
- package/dist/esm/rich-text/viewer/styles.js.map +1 -1
- package/dist/esm/src/rich-text/models/markdown-parser.d.ts +1 -0
- package/dist/esm/theme-provider/design-tokens.js +1 -1
- package/dist/esm/theme-provider/design-tokens.js.map +1 -1
- package/package.json +3 -3
|
@@ -1,94 +1,82 @@
|
|
|
1
1
|
import { css } from '@microsoft/fast-element';
|
|
2
2
|
import { display } from '@microsoft/fast-foundation';
|
|
3
3
|
import { focusVisible } from '../utilities/style/focus';
|
|
4
|
-
import {
|
|
4
|
+
import { linkActiveFontColor, linkActiveProminentFontColor, linkDisabledFontColor, linkFont, linkFontColor, linkProminentFontColor } from '../theme-provider/design-tokens';
|
|
5
5
|
export const styles = css `
|
|
6
|
-
|
|
6
|
+
@layer base, hover, focusVisible, active, disabled;
|
|
7
7
|
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
font: ${linkFont};
|
|
11
|
-
}
|
|
12
|
-
|
|
13
|
-
.top-container {
|
|
14
|
-
display: contents;
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
[part='start'] {
|
|
18
|
-
display: none;
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
.control {
|
|
22
|
-
color: ${linkFontColor};
|
|
23
|
-
text-decoration: underline;
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
.control${focusVisible} {
|
|
27
|
-
display: inline;
|
|
28
|
-
outline: none;
|
|
29
|
-
box-shadow: inset 0px -1px ${linkFontColor};
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
.control:active {
|
|
33
|
-
color: ${linkActiveFontColor};
|
|
34
|
-
text-decoration: underline;
|
|
35
|
-
}
|
|
8
|
+
@layer base {
|
|
9
|
+
${display('inline')}
|
|
36
10
|
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
11
|
+
:host {
|
|
12
|
+
box-sizing: border-box;
|
|
13
|
+
font: ${linkFont};
|
|
14
|
+
}
|
|
40
15
|
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
}
|
|
16
|
+
.top-container {
|
|
17
|
+
display: contents;
|
|
18
|
+
}
|
|
45
19
|
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
20
|
+
.control {
|
|
21
|
+
color: ${linkFontColor};
|
|
22
|
+
text-decoration: underline;
|
|
23
|
+
}
|
|
49
24
|
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
25
|
+
:host([underline-hidden]) .control {
|
|
26
|
+
text-decoration: none;
|
|
27
|
+
}
|
|
53
28
|
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
29
|
+
:host([appearance='prominent']) .control {
|
|
30
|
+
color: ${linkProminentFontColor};
|
|
31
|
+
}
|
|
57
32
|
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
33
|
+
[part='start'] {
|
|
34
|
+
display: none;
|
|
35
|
+
}
|
|
61
36
|
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
37
|
+
.content {
|
|
38
|
+
pointer-events: none;
|
|
39
|
+
}
|
|
65
40
|
|
|
66
|
-
|
|
67
|
-
|
|
41
|
+
[part='end'] {
|
|
42
|
+
display: none;
|
|
43
|
+
}
|
|
68
44
|
}
|
|
69
45
|
|
|
70
|
-
|
|
71
|
-
|
|
46
|
+
@layer hover {
|
|
47
|
+
.control:any-link:hover {
|
|
48
|
+
text-decoration: underline;
|
|
49
|
+
}
|
|
72
50
|
}
|
|
73
51
|
|
|
74
|
-
|
|
75
|
-
|
|
52
|
+
@layer focusVisible {
|
|
53
|
+
.control${focusVisible} {
|
|
54
|
+
outline: none;
|
|
55
|
+
box-shadow: inset 0px -1px;
|
|
56
|
+
text-decoration: underline;
|
|
57
|
+
}
|
|
76
58
|
}
|
|
77
59
|
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
60
|
+
@layer active {
|
|
61
|
+
.control:active {
|
|
62
|
+
color: ${linkActiveFontColor};
|
|
63
|
+
text-decoration: underline;
|
|
64
|
+
box-shadow: none;
|
|
65
|
+
}
|
|
81
66
|
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
67
|
+
:host([appearance='prominent']) .control:active {
|
|
68
|
+
color: ${linkActiveProminentFontColor};
|
|
69
|
+
}
|
|
85
70
|
|
|
86
|
-
|
|
87
|
-
|
|
71
|
+
:host([underline-hidden]) .control:active {
|
|
72
|
+
text-decoration: none;
|
|
73
|
+
}
|
|
88
74
|
}
|
|
89
75
|
|
|
90
|
-
|
|
91
|
-
|
|
76
|
+
@layer disabled {
|
|
77
|
+
.control:not(:any-link) {
|
|
78
|
+
color: ${linkDisabledFontColor};
|
|
79
|
+
}
|
|
92
80
|
}
|
|
93
81
|
`;
|
|
94
82
|
//# sourceMappingURL=styles.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"styles.js","sourceRoot":"","sources":["../../../src/anchor/styles.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,MAAM,yBAAyB,CAAC;AAC9C,OAAO,EAAE,OAAO,EAAE,MAAM,4BAA4B,CAAC;AACrD,OAAO,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAC;AACxD,OAAO,EACH,
|
|
1
|
+
{"version":3,"file":"styles.js","sourceRoot":"","sources":["../../../src/anchor/styles.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,MAAM,yBAAyB,CAAC;AAC9C,OAAO,EAAE,OAAO,EAAE,MAAM,4BAA4B,CAAC;AACrD,OAAO,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAC;AACxD,OAAO,EACH,mBAAmB,EACnB,4BAA4B,EAC5B,qBAAqB,EACrB,QAAQ,EACR,aAAa,EACb,sBAAsB,EACzB,MAAM,iCAAiC,CAAC;AAEzC,MAAM,CAAC,MAAM,MAAM,GAAG,GAAG,CAAA;;;;UAIf,OAAO,CAAC,QAAQ,CAAC;;;;oBAIP,QAAQ;;;;;;;;qBAQP,aAAa;;;;;;;;;qBASb,sBAAsB;;;;;;;;;;;;;;;;;;;;;;;kBAuBzB,YAAY;;;;;;;;;qBAST,mBAAmB;;;;;;qBAMnB,4BAA4B;;;;;;;;;;qBAU5B,qBAAqB;;;CAGzC,CAAC","sourcesContent":["import { css } from '@microsoft/fast-element';\nimport { display } from '@microsoft/fast-foundation';\nimport { focusVisible } from '../utilities/style/focus';\nimport {\n linkActiveFontColor,\n linkActiveProminentFontColor,\n linkDisabledFontColor,\n linkFont,\n linkFontColor,\n linkProminentFontColor\n} from '../theme-provider/design-tokens';\n\nexport const styles = css`\n @layer base, hover, focusVisible, active, disabled;\n\n @layer base {\n ${display('inline')}\n\n :host {\n box-sizing: border-box;\n font: ${linkFont};\n }\n\n .top-container {\n display: contents;\n }\n\n .control {\n color: ${linkFontColor};\n text-decoration: underline;\n }\n\n :host([underline-hidden]) .control {\n text-decoration: none;\n }\n\n :host([appearance='prominent']) .control {\n color: ${linkProminentFontColor};\n }\n\n [part='start'] {\n display: none;\n }\n\n .content {\n pointer-events: none;\n }\n\n [part='end'] {\n display: none;\n }\n }\n\n @layer hover {\n .control:any-link:hover {\n text-decoration: underline;\n }\n }\n\n @layer focusVisible {\n .control${focusVisible} {\n outline: none;\n box-shadow: inset 0px -1px;\n text-decoration: underline;\n }\n }\n\n @layer active {\n .control:active {\n color: ${linkActiveFontColor};\n text-decoration: underline;\n box-shadow: none;\n }\n\n :host([appearance='prominent']) .control:active {\n color: ${linkActiveProminentFontColor};\n }\n\n :host([underline-hidden]) .control:active {\n text-decoration: none;\n }\n }\n\n @layer disabled {\n .control:not(:any-link) {\n color: ${linkDisabledFontColor};\n }\n }\n`;\n"]}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { __decorate } from "tslib";
|
|
2
2
|
import { attr, observable } from '@microsoft/fast-element';
|
|
3
|
-
import { DesignSystem
|
|
3
|
+
import { DesignSystem } from '@microsoft/fast-foundation';
|
|
4
4
|
import { keyEnter } from '@microsoft/fast-web-utilities';
|
|
5
5
|
import { AnchorBase } from '../anchor-base';
|
|
6
6
|
import { styles } from './styles';
|
|
@@ -87,18 +87,4 @@ DesignSystem.getOrCreate()
|
|
|
87
87
|
.withPrefix('nimble')
|
|
88
88
|
.register(nimbleAnchorMenuItem());
|
|
89
89
|
export const anchorMenuItemTag = 'nimble-anchor-menu-item';
|
|
90
|
-
// This is a workaround for the fact that FAST's menu uses `instanceof MenuItem`
|
|
91
|
-
// in their logic for indenting menu items. Since our AnchorMenuItem derives from
|
|
92
|
-
// AnchorBase and not FAST's MenuItem, we need to change their MenuItem's definition
|
|
93
|
-
// of `hasInstance` so that it includes our AnchorMenuItem, too.
|
|
94
|
-
//
|
|
95
|
-
// If/when we change FAST to test for the presence of `startColumnCount` instead
|
|
96
|
-
// of using `instanceof MenuItem`, we can remove this workaround. Here is the
|
|
97
|
-
// PR into FAST: https://github.com/microsoft/fast/pull/6667
|
|
98
|
-
const originalInstanceOf = FoundationMenuItem[Symbol.hasInstance].bind(FoundationMenuItem);
|
|
99
|
-
Object.defineProperty(FoundationMenuItem, Symbol.hasInstance, {
|
|
100
|
-
value(instance) {
|
|
101
|
-
return (originalInstanceOf(instance) || instance instanceof AnchorMenuItem);
|
|
102
|
-
}
|
|
103
|
-
});
|
|
104
90
|
//# sourceMappingURL=index.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/anchor-menu-item/index.ts"],"names":[],"mappings":";AAAA,OAAO,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,yBAAyB,CAAC;AAC3D,OAAO,EACH,YAAY,
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/anchor-menu-item/index.ts"],"names":[],"mappings":";AAAA,OAAO,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,yBAAyB,CAAC;AAC3D,OAAO,EACH,YAAY,EAGf,MAAM,4BAA4B,CAAC;AACpC,OAAO,EAAE,QAAQ,EAAE,MAAM,+BAA+B,CAAC;AACzD,OAAO,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AAC5C,OAAO,EAAE,MAAM,EAAE,MAAM,UAAU,CAAC;AAClC,OAAO,EAAE,QAAQ,EAAE,MAAM,YAAY,CAAC;AAQtC;;GAEG;AACH,MAAM,OAAO,cAAe,SAAQ,UAAU;IAA9C;;QAEW,aAAQ,GAAG,KAAK,CAAC;QAQxB;;;;;WAKG;QAEI,qBAAgB,GAAwB,CAAC,CAAC;IAkDrD,CAAC;IAhDG,4FAA4F;IAC5F,uGAAuG;IACvG,gGAAgG;IAChG,gEAAgE;IAEhE;;OAEG;IACI,YAAY,CAAC,CAAa;QAC7B,CAAC,CAAC,eAAe,EAAE,CAAC;QACpB,OAAO,IAAI,CAAC;IAChB,CAAC;IAED;;OAEG;IACI,cAAc,CAAC,CAAgB;QAClC,IAAI,CAAC,CAAC,gBAAgB,EAAE;YACpB,OAAO,KAAK,CAAC;SAChB;QACD,QAAQ,CAAC,CAAC,GAAG,EAAE;YACX,KAAK,QAAQ;gBACT,CAAC,CAAC,eAAe,EAAE,CAAC;gBACpB,MAAM;YACV,QAAQ;SACX;QACD,OAAO,IAAI,CAAC;IAChB,CAAC;IAED,0DAA0D;IAC1D,4EAA4E;IAC5E,6EAA6E;IAC7E,oEAAoE;IACpD,YAAY,CAAC,aAAqB,EAAE,KAAa;QAC7D,IAAI,aAAa,KAAK,UAAU,EAAE;YAC9B,IAAI,CAAC,MAAM,CAAC,YAAY,CAAC,aAAa,EAAE,KAAK,CAAC,CAAC;SAClD;aAAM;YACH,KAAK,CAAC,YAAY,CAAC,aAAa,EAAE,KAAK,CAAC,CAAC;SAC5C;IACL,CAAC;IAED,IAAoB,QAAQ;QACxB,OAAO,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC;IAChC,CAAC;IAED,IAAoB,QAAQ,CAAC,KAAa;QACtC,IAAI,CAAC,MAAM,CAAC,QAAQ,GAAG,KAAK,CAAC;IACjC,CAAC;CACJ;AAjEG;IADC,IAAI,CAAC,EAAE,IAAI,EAAE,SAAS,EAAE,CAAC;gDACF;AAMxB;IADC,UAAU;8CACuB;AASlC;IADC,UAAU;wDACsC;AAoDrD,uFAAuF;AAEvF,MAAM,oBAAoB,GAAG,cAAc,CAAC,OAAO,CAAgB;IAC/D,QAAQ,EAAE,kBAAkB;IAC5B,QAAQ;IACR,MAAM;IACN,aAAa,EAAE;QACX,cAAc,EAAE,IAAI;KACvB;CACJ,CAAC,CAAC;AAEH,YAAY,CAAC,WAAW,EAAE;KACrB,UAAU,CAAC,QAAQ,CAAC;KACpB,QAAQ,CAAC,oBAAoB,EAAE,CAAC,CAAC;AACtC,MAAM,CAAC,MAAM,iBAAiB,GAAG,yBAAyB,CAAC","sourcesContent":["import { attr, observable } from '@microsoft/fast-element';\nimport {\n DesignSystem,\n AnchorOptions,\n MenuItemColumnCount\n} from '@microsoft/fast-foundation';\nimport { keyEnter } from '@microsoft/fast-web-utilities';\nimport { AnchorBase } from '../anchor-base';\nimport { styles } from './styles';\nimport { template } from './template';\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'nimble-anchor-menu-item': AnchorMenuItem;\n }\n}\n\n/**\n * A nimble-styled anchor menu-item\n */\nexport class AnchorMenuItem extends AnchorBase {\n @attr({ mode: 'boolean' })\n public disabled = false;\n\n /**\n * @internal\n */\n @observable\n public anchor!: HTMLAnchorElement;\n\n /**\n * There is an assumption that this component is styled using a grid display, and this property\n * controls which grid column contains the menu item text (i.e. the indentation of the text).\n * The parent menu sets this value on all its child menu items so their indentations align.\n * @internal\n */\n @observable\n public startColumnCount: MenuItemColumnCount = 0;\n\n // The following two handlers are workarounds for issues with anchor menu items in submenus.\n // Events can bubble up the DOM and get handled by the menu item in the parent menu. When that happens,\n // the menu item's handlers (FAST) return false and prevent the default action, i.e. navigation.\n // See tech debt issue: https://github.com/ni/nimble/issues/1740\n\n /**\n * @internal\n */\n public clickHandler(e: MouseEvent): boolean {\n e.stopPropagation();\n return true;\n }\n\n /**\n * @internal\n */\n public keydownHandler(e: KeyboardEvent): boolean {\n if (e.defaultPrevented) {\n return false;\n }\n switch (e.key) {\n case keyEnter:\n e.stopPropagation();\n break;\n default:\n }\n return true;\n }\n\n // The FAST Menu manages the `tabindex` of its menu items.\n // When keyboard navigating to an item, it sets that item's `tabindex` to 0.\n // We need to pass this on to the anchor, otherwise an anchor without an href\n // will not be focusable and will prevent arrowing through the menu.\n public override setAttribute(qualifiedName: string, value: string): void {\n if (qualifiedName === 'tabindex') {\n this.anchor.setAttribute(qualifiedName, value);\n } else {\n super.setAttribute(qualifiedName, value);\n }\n }\n\n public override get tabIndex(): number {\n return this.anchor.tabIndex;\n }\n\n public override set tabIndex(value: number) {\n this.anchor.tabIndex = value;\n }\n}\n\n// FoundationAnchor already applies the StartEnd mixin, so we don't need to do it here.\n\nconst nimbleAnchorMenuItem = AnchorMenuItem.compose<AnchorOptions>({\n baseName: 'anchor-menu-item',\n template,\n styles,\n shadowOptions: {\n delegatesFocus: true\n }\n});\n\nDesignSystem.getOrCreate()\n .withPrefix('nimble')\n .register(nimbleAnchorMenuItem());\nexport const anchorMenuItemTag = 'nimble-anchor-menu-item';\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"styles.js","sourceRoot":"","sources":["../../../src/breadcrumb-item/styles.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,MAAM,yBAAyB,CAAC;AAC9C,OAAO,EAAE,OAAO,EAAE,MAAM,4BAA4B,CAAC;AACrD,OAAO,EACH,aAAa,EACb,gBAAgB,EAChB,WAAW,EACX,aAAa,EACb,QAAQ,EACR,QAAQ,EACR,oBAAoB,EACvB,MAAM,iCAAiC,CAAC;AACzC,OAAO,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAC;AAExD,MAAM,CAAC,MAAM,MAAM,GAAG,GAAG,CAAA;MACnB,OAAO,CAAC,aAAa,CAAC;;;kBAGV,aAAa;;mCAEI,WAAW;;UAEpC;AACE;mDACmD,CAAC,EACxD;iBACS,aAAa;gBACd,QAAQ;;;;;;;;;;;;;kBAaN,WAAW;oCACO,WAAW;;;;;;;;cAQjC,YAAY;kBACR,WAAW,UAAU,gBAAgB;6BAC1B,gBAAgB;;;;;;;;;;;;;;;;;;;;;;;;;;;iBA2B5B,QAAQ;kBACP,QAAQ;gBACV,oBAAoB;;CAEnC,CAAC","sourcesContent":["import { css } from '@microsoft/fast-element';\nimport { display } from '@microsoft/fast-foundation';\nimport {\n bodyFontColor,\n borderHoverColor,\n borderWidth,\n controlHeight,\n iconSize,\n linkFont,\n placeholderFontColor\n} from '../theme-provider/design-tokens';\nimport { focusVisible } from '../utilities/style/focus';\n\nexport const styles = css`\n ${display('inline-flex')}\n\n :host {\n height: ${controlHeight};\n box-sizing: border-box;\n padding-left: calc(4px - ${borderWidth});\n\n ${\n /* When href removed the .control element is also removed\n so this becomes the fallback color for the slot */ ''\n }\n color: ${bodyFontColor};\n font: ${linkFont};\n }\n\n .listitem {\n display: flex;\n align-items: center;\n }\n\n .control {\n color: var(--ni-private-breadcrumb-link-font-color);\n display: flex;\n align-items: center;\n justify-content: center;\n border: ${borderWidth} solid transparent;\n padding-right: calc(4px - ${borderWidth});\n text-decoration: none;\n }\n\n .control:hover {\n text-decoration: underline;\n }\n\n .control${focusVisible} {\n border: ${borderWidth} solid ${borderHoverColor};\n outline: 2px solid ${borderHoverColor};\n outline-offset: 1px;\n }\n\n .control:active {\n color: var(--ni-private-breadcrumb-link-active-font-color);\n text-decoration:
|
|
1
|
+
{"version":3,"file":"styles.js","sourceRoot":"","sources":["../../../src/breadcrumb-item/styles.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,MAAM,yBAAyB,CAAC;AAC9C,OAAO,EAAE,OAAO,EAAE,MAAM,4BAA4B,CAAC;AACrD,OAAO,EACH,aAAa,EACb,gBAAgB,EAChB,WAAW,EACX,aAAa,EACb,QAAQ,EACR,QAAQ,EACR,oBAAoB,EACvB,MAAM,iCAAiC,CAAC;AACzC,OAAO,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAC;AAExD,MAAM,CAAC,MAAM,MAAM,GAAG,GAAG,CAAA;MACnB,OAAO,CAAC,aAAa,CAAC;;;kBAGV,aAAa;;mCAEI,WAAW;;UAEpC;AACE;mDACmD,CAAC,EACxD;iBACS,aAAa;gBACd,QAAQ;;;;;;;;;;;;;kBAaN,WAAW;oCACO,WAAW;;;;;;;;cAQjC,YAAY;kBACR,WAAW,UAAU,gBAAgB;6BAC1B,gBAAgB;;;;;;;;;;;;;;;;;;;;;;;;;;;iBA2B5B,QAAQ;kBACP,QAAQ;gBACV,oBAAoB;;CAEnC,CAAC","sourcesContent":["import { css } from '@microsoft/fast-element';\nimport { display } from '@microsoft/fast-foundation';\nimport {\n bodyFontColor,\n borderHoverColor,\n borderWidth,\n controlHeight,\n iconSize,\n linkFont,\n placeholderFontColor\n} from '../theme-provider/design-tokens';\nimport { focusVisible } from '../utilities/style/focus';\n\nexport const styles = css`\n ${display('inline-flex')}\n\n :host {\n height: ${controlHeight};\n box-sizing: border-box;\n padding-left: calc(4px - ${borderWidth});\n\n ${\n /* When href removed the .control element is also removed\n so this becomes the fallback color for the slot */ ''\n }\n color: ${bodyFontColor};\n font: ${linkFont};\n }\n\n .listitem {\n display: flex;\n align-items: center;\n }\n\n .control {\n color: var(--ni-private-breadcrumb-link-font-color);\n display: flex;\n align-items: center;\n justify-content: center;\n border: ${borderWidth} solid transparent;\n padding-right: calc(4px - ${borderWidth});\n text-decoration: none;\n }\n\n .control:hover {\n text-decoration: underline;\n }\n\n .control${focusVisible} {\n border: ${borderWidth} solid ${borderHoverColor};\n outline: 2px solid ${borderHoverColor};\n outline-offset: 1px;\n }\n\n .control:active {\n color: var(--ni-private-breadcrumb-link-active-font-color);\n text-decoration: none;\n }\n\n [part='start'] {\n display: none;\n }\n\n .content {\n pointer-events: none;\n }\n\n [part='end'] {\n display: none;\n }\n\n slot[name='separator'] {\n display: flex;\n align-items: center;\n }\n\n slot[name='separator'] svg {\n width: ${iconSize};\n height: ${iconSize};\n fill: ${placeholderFontColor};\n }\n`;\n"]}
|
|
@@ -101,12 +101,17 @@ export class RichTextMarkdownParser {
|
|
|
101
101
|
* scheme and no matching mention pattern will be rendered as plain text (anchor with no href).
|
|
102
102
|
* With this, the user can click the links only when the scheme is HTTP/HTTPS
|
|
103
103
|
*/
|
|
104
|
-
href:
|
|
104
|
+
href: RichTextMarkdownParser.startsWithHttpOrHttps(href)
|
|
105
|
+
? href
|
|
106
|
+
: null,
|
|
105
107
|
rel: node.attrs.rel,
|
|
106
108
|
// Adding `class` here is a workaround to render two mentions without a whitespace as display names
|
|
107
109
|
// This attribute can be removed when the below issue is resolved
|
|
108
110
|
// https://github.com/ni/nimble/issues/1707
|
|
109
|
-
class: href
|
|
111
|
+
class: href,
|
|
112
|
+
'underline-hidden': RichTextMarkdownParser.startsWithHttpOrHttps(href)
|
|
113
|
+
? null
|
|
114
|
+
: true
|
|
110
115
|
}
|
|
111
116
|
];
|
|
112
117
|
}
|
|
@@ -124,6 +129,9 @@ export class RichTextMarkdownParser {
|
|
|
124
129
|
RichTextMarkdownParser.mentionConfigs = undefined;
|
|
125
130
|
RichTextMarkdownParser.mentionedHrefs.clear();
|
|
126
131
|
}
|
|
132
|
+
static startsWithHttpOrHttps(href) {
|
|
133
|
+
return /^https?:\/\//i.test(href);
|
|
134
|
+
}
|
|
127
135
|
}
|
|
128
136
|
_a = RichTextMarkdownParser;
|
|
129
137
|
RichTextMarkdownParser.mentionedHrefs = new Set();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"markdown-parser.js","sourceRoot":"","sources":["../../../../src/rich-text/models/markdown-parser.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n schema,\n defaultMarkdownParser,\n MarkdownParser\n} from 'prosemirror-markdown';\nimport { DOMSerializer, Schema } from 'prosemirror-model';\nimport { anchorTag } from '../../anchor';\nimport type { MarkdownParserMentionConfiguration } from './markdown-parser-mention-configuration';\n\nexport interface ParseResult {\n fragment: HTMLElement | DocumentFragment;\n mentionedHrefs: string[];\n}\n\n/**\n * Provides markdown parser for rich text components\n */\nexport class RichTextMarkdownParser {\n private static readonly mentionedHrefs: Set<string> = new Set();\n private static readonly updatedSchema = this.getCustomSchemaConfiguration();\n\n private static readonly markdownParser = this.initializeMarkdownParser();\n private static readonly domSerializer = DOMSerializer.fromSchema(\n this.updatedSchema\n );\n\n /**\n * The markdown parser is static (shared across all rich text components) because it is expensive to create.\n * To configure parse calls with the mention configurations which can be unique per component instance\n * we store static configuration in this member and access it from Prosemirror callbacks.\n */\n private static mentionConfigs?: MarkdownParserMentionConfiguration[];\n\n /**\n * This function takes a markdown string, parses it using the ProseMirror MarkdownParser, serializes the parsed content into a\n * DOM structure using a DOMSerializer, and returns the serialized result.\n * If the markdown parser returns null, it will clear the viewer component by creating an empty document fragment.\n */\n public static parseMarkdownToDOM(\n value: string,\n markdownParserMentionConfig?: MarkdownParserMentionConfiguration[]\n ): ParseResult {\n try {\n RichTextMarkdownParser.setup(markdownParserMentionConfig);\n const parsedMarkdownContent = this.markdownParser.parse(value);\n if (parsedMarkdownContent === null) {\n return {\n fragment: document.createDocumentFragment(),\n mentionedHrefs: Array.from(\n RichTextMarkdownParser.mentionedHrefs\n )\n };\n }\n return {\n fragment: this.domSerializer.serializeFragment(\n parsedMarkdownContent.content\n ),\n mentionedHrefs: Array.from(\n RichTextMarkdownParser.mentionedHrefs\n )\n };\n } finally {\n RichTextMarkdownParser.cleanup();\n }\n }\n\n private static initializeMarkdownParser(): MarkdownParser {\n /**\n * It configures the tokenizer of the default Markdown parser with the 'zero' preset.\n * The 'zero' preset is a configuration with no rules enabled by default to selectively enable specific rules.\n * https://github.com/markdown-it/markdown-it/blob/2b6cac25823af011ff3bc7628bc9b06e483c5a08/lib/presets/zero.js#L1\n *\n */\n const zeroTokenizerConfiguration = defaultMarkdownParser.tokenizer.configure('zero');\n\n // The detailed information of the supported rules were provided in the below CommonMark spec document.\n // https://spec.commonmark.org/0.30/\n const supportedTokenizerRules = zeroTokenizerConfiguration.enable([\n 'emphasis',\n 'list',\n 'escape',\n 'autolink',\n 'newline'\n ]);\n\n /**\n * In order to display encoded characters, non-ASCII characters, emojis, and other special characters in their original form,\n * we bypass the default normalization of link text in markdown-it. This is done because we support only \"AutoLink\" feature in CommonMark flavor.\n * \"normalizeLinkText\" method reference in markdown-it: https://github.com/markdown-it/markdown-it/blob/2b6cac25823af011ff3bc7628bc9b06e483c5a08/lib/index.js#L67C1-L86C2\n *\n * We can use the default normalization once hyperlink support is added.\n * See: https://github.com/ni/nimble/issues/1527\n */\n supportedTokenizerRules.normalizeLinkText = url => url;\n\n return new MarkdownParser(\n this.updatedSchema,\n supportedTokenizerRules,\n defaultMarkdownParser.tokens\n );\n }\n\n private static getCustomSchemaConfiguration(): Schema {\n return new Schema({\n nodes: schema.spec.nodes,\n marks: {\n link: {\n attrs: {\n href: {},\n rel: { default: 'noopener noreferrer' },\n // Adding `class` here is a workaround to render two mentions without a whitespace as display names\n // This attribute can be removed when the below issue is resolved\n // https://github.com/ni/nimble/issues/1707\n class: { default: '' }\n },\n // Inclusive can be updated when hyperlink support added\n // See: https://github.com/ni/nimble/issues/1527\n inclusive: false,\n // Excludes can be removed/enabled when hyperlink support added\n // See: https://github.com/ni/nimble/issues/1527\n excludes: '_',\n toDOM(node) {\n const href = node.attrs.href as string;\n const currentMention = RichTextMarkdownParser.mentionConfigs?.find(\n mention => mention.isValidMentionHref(href)\n );\n const displayName = currentMention?.getDisplayName(href);\n\n if (currentMention && displayName) {\n RichTextMarkdownParser.mentionedHrefs.add(href);\n\n return [\n currentMention.viewElement,\n {\n 'mention-href': href,\n 'mention-label': displayName\n }\n ];\n }\n\n return [\n anchorTag,\n {\n /**\n * Both mention and absolute link markdown share the autolink format in CommonMark flavor.\n * Absolute links with HTTP/HTTPS will be rendered as links. Absolute links that match the\n * mention pattern will be rendered as mention view element. Absolute links without HTTP/HTTPS\n * scheme and no matching mention pattern will be rendered as plain text (anchor with no href).\n * With this, the user can click the links only when the scheme is HTTP/HTTPS\n */\n href: /^https?:\\/\\//i.test(href) ? href : null,\n rel: node.attrs.rel as Attr,\n // Adding `class` here is a workaround to render two mentions without a whitespace as display names\n // This attribute can be removed when the below issue is resolved\n // https://github.com/ni/nimble/issues/1707\n class: href\n }\n ];\n }\n },\n em: schema.spec.marks.get('em')!,\n strong: schema.spec.marks.get('strong')!\n }\n });\n }\n\n private static setup(\n markdownParserMentionConfig:\n | MarkdownParserMentionConfiguration[]\n | undefined\n ): void {\n RichTextMarkdownParser.mentionConfigs = markdownParserMentionConfig;\n RichTextMarkdownParser.mentionedHrefs.clear();\n }\n\n private static cleanup(): void {\n RichTextMarkdownParser.mentionConfigs = undefined;\n RichTextMarkdownParser.mentionedHrefs.clear();\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"markdown-parser.js","sourceRoot":"","sources":["../../../../src/rich-text/models/markdown-parser.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n schema,\n defaultMarkdownParser,\n MarkdownParser\n} from 'prosemirror-markdown';\nimport { DOMSerializer, Schema } from 'prosemirror-model';\nimport { anchorTag } from '../../anchor';\nimport type { MarkdownParserMentionConfiguration } from './markdown-parser-mention-configuration';\n\nexport interface ParseResult {\n fragment: HTMLElement | DocumentFragment;\n mentionedHrefs: string[];\n}\n\n/**\n * Provides markdown parser for rich text components\n */\nexport class RichTextMarkdownParser {\n private static readonly mentionedHrefs: Set<string> = new Set();\n private static readonly updatedSchema = this.getCustomSchemaConfiguration();\n\n private static readonly markdownParser = this.initializeMarkdownParser();\n private static readonly domSerializer = DOMSerializer.fromSchema(\n this.updatedSchema\n );\n\n /**\n * The markdown parser is static (shared across all rich text components) because it is expensive to create.\n * To configure parse calls with the mention configurations which can be unique per component instance\n * we store static configuration in this member and access it from Prosemirror callbacks.\n */\n private static mentionConfigs?: MarkdownParserMentionConfiguration[];\n\n /**\n * This function takes a markdown string, parses it using the ProseMirror MarkdownParser, serializes the parsed content into a\n * DOM structure using a DOMSerializer, and returns the serialized result.\n * If the markdown parser returns null, it will clear the viewer component by creating an empty document fragment.\n */\n public static parseMarkdownToDOM(\n value: string,\n markdownParserMentionConfig?: MarkdownParserMentionConfiguration[]\n ): ParseResult {\n try {\n RichTextMarkdownParser.setup(markdownParserMentionConfig);\n const parsedMarkdownContent = this.markdownParser.parse(value);\n if (parsedMarkdownContent === null) {\n return {\n fragment: document.createDocumentFragment(),\n mentionedHrefs: Array.from(\n RichTextMarkdownParser.mentionedHrefs\n )\n };\n }\n return {\n fragment: this.domSerializer.serializeFragment(\n parsedMarkdownContent.content\n ),\n mentionedHrefs: Array.from(\n RichTextMarkdownParser.mentionedHrefs\n )\n };\n } finally {\n RichTextMarkdownParser.cleanup();\n }\n }\n\n private static initializeMarkdownParser(): MarkdownParser {\n /**\n * It configures the tokenizer of the default Markdown parser with the 'zero' preset.\n * The 'zero' preset is a configuration with no rules enabled by default to selectively enable specific rules.\n * https://github.com/markdown-it/markdown-it/blob/2b6cac25823af011ff3bc7628bc9b06e483c5a08/lib/presets/zero.js#L1\n *\n */\n const zeroTokenizerConfiguration = defaultMarkdownParser.tokenizer.configure('zero');\n\n // The detailed information of the supported rules were provided in the below CommonMark spec document.\n // https://spec.commonmark.org/0.30/\n const supportedTokenizerRules = zeroTokenizerConfiguration.enable([\n 'emphasis',\n 'list',\n 'escape',\n 'autolink',\n 'newline'\n ]);\n\n /**\n * In order to display encoded characters, non-ASCII characters, emojis, and other special characters in their original form,\n * we bypass the default normalization of link text in markdown-it. This is done because we support only \"AutoLink\" feature in CommonMark flavor.\n * \"normalizeLinkText\" method reference in markdown-it: https://github.com/markdown-it/markdown-it/blob/2b6cac25823af011ff3bc7628bc9b06e483c5a08/lib/index.js#L67C1-L86C2\n *\n * We can use the default normalization once hyperlink support is added.\n * See: https://github.com/ni/nimble/issues/1527\n */\n supportedTokenizerRules.normalizeLinkText = url => url;\n\n return new MarkdownParser(\n this.updatedSchema,\n supportedTokenizerRules,\n defaultMarkdownParser.tokens\n );\n }\n\n private static getCustomSchemaConfiguration(): Schema {\n return new Schema({\n nodes: schema.spec.nodes,\n marks: {\n link: {\n attrs: {\n href: {},\n rel: { default: 'noopener noreferrer' },\n // Adding `class` here is a workaround to render two mentions without a whitespace as display names\n // This attribute can be removed when the below issue is resolved\n // https://github.com/ni/nimble/issues/1707\n class: { default: '' }\n },\n // Inclusive can be updated when hyperlink support added\n // See: https://github.com/ni/nimble/issues/1527\n inclusive: false,\n // Excludes can be removed/enabled when hyperlink support added\n // See: https://github.com/ni/nimble/issues/1527\n excludes: '_',\n toDOM(node) {\n const href = node.attrs.href as string;\n const currentMention = RichTextMarkdownParser.mentionConfigs?.find(\n mention => mention.isValidMentionHref(href)\n );\n const displayName = currentMention?.getDisplayName(href);\n\n if (currentMention && displayName) {\n RichTextMarkdownParser.mentionedHrefs.add(href);\n\n return [\n currentMention.viewElement,\n {\n 'mention-href': href,\n 'mention-label': displayName\n }\n ];\n }\n\n return [\n anchorTag,\n {\n /**\n * Both mention and absolute link markdown share the autolink format in CommonMark flavor.\n * Absolute links with HTTP/HTTPS will be rendered as links. Absolute links that match the\n * mention pattern will be rendered as mention view element. Absolute links without HTTP/HTTPS\n * scheme and no matching mention pattern will be rendered as plain text (anchor with no href).\n * With this, the user can click the links only when the scheme is HTTP/HTTPS\n */\n href: RichTextMarkdownParser.startsWithHttpOrHttps(\n href\n )\n ? href\n : null,\n rel: node.attrs.rel as Attr,\n // Adding `class` here is a workaround to render two mentions without a whitespace as display names\n // This attribute can be removed when the below issue is resolved\n // https://github.com/ni/nimble/issues/1707\n class: href,\n 'underline-hidden':\n RichTextMarkdownParser.startsWithHttpOrHttps(\n href\n )\n ? null\n : true\n }\n ];\n }\n },\n em: schema.spec.marks.get('em')!,\n strong: schema.spec.marks.get('strong')!\n }\n });\n }\n\n private static setup(\n markdownParserMentionConfig:\n | MarkdownParserMentionConfiguration[]\n | undefined\n ): void {\n RichTextMarkdownParser.mentionConfigs = markdownParserMentionConfig;\n RichTextMarkdownParser.mentionedHrefs.clear();\n }\n\n private static cleanup(): void {\n RichTextMarkdownParser.mentionConfigs = undefined;\n RichTextMarkdownParser.mentionedHrefs.clear();\n }\n\n private static startsWithHttpOrHttps(href: string): boolean {\n return /^https?:\\/\\//i.test(href);\n }\n}\n"]}
|
|
@@ -42,10 +42,13 @@ export const styles = css `
|
|
|
42
42
|
|
|
43
43
|
${
|
|
44
44
|
/**
|
|
45
|
-
*
|
|
46
|
-
*
|
|
47
|
-
*
|
|
48
|
-
* attribute
|
|
45
|
+
* In the rich-text editor, an absolute link renders as a native anchor, not a `nimble-anchor`. When such a link
|
|
46
|
+
* is not HTTPS/HTTP, the anchor renders without an `href`, appearing as plain text.
|
|
47
|
+
* However, in the rich-text viewer, absolute links are rendered as `nimble-anchor`s, and they do not look like
|
|
48
|
+
* plain text when the `href` attribute is absent. They have a "disabled" color and may have an underline.
|
|
49
|
+
* To ensure a consistent appearance between the editor and viewer, we force the font color to the default link/
|
|
50
|
+
* plain text color regardless of the `href` attribute's presence. To remove the underline, the markdown parser
|
|
51
|
+
* emits an `underline-hidden` attribute when the `href` attribute is absent.
|
|
49
52
|
*
|
|
50
53
|
* See models/markdown-parser.ts where link elements are emitted for more info.
|
|
51
54
|
*/ ''}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"styles.js","sourceRoot":"","sources":["../../../../src/rich-text/viewer/styles.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,MAAM,yBAAyB,CAAC;AAC9C,OAAO,EAAE,OAAO,EAAE,MAAM,4BAA4B,CAAC;AACrD,OAAO,EACH,QAAQ,EACR,aAAa,EACb,aAAa,EAChB,MAAM,oCAAoC,CAAC;AAE5C,MAAM,CAAC,MAAM,MAAM,GAAG,GAAG,CAAA;MACnB,OAAO,CAAC,MAAM,CAAC;;;gBAGL,QAAQ;;iBAEP,aAAa;;;;;;;;;;;;;;;;;;;;;;;;;;;MA2BxB;AACE,gLAAgL,CAAC,EACrL;;;;;MAKE;AACE
|
|
1
|
+
{"version":3,"file":"styles.js","sourceRoot":"","sources":["../../../../src/rich-text/viewer/styles.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,MAAM,yBAAyB,CAAC;AAC9C,OAAO,EAAE,OAAO,EAAE,MAAM,4BAA4B,CAAC;AACrD,OAAO,EACH,QAAQ,EACR,aAAa,EACb,aAAa,EAChB,MAAM,oCAAoC,CAAC;AAE5C,MAAM,CAAC,MAAM,MAAM,GAAG,GAAG,CAAA;MACnB,OAAO,CAAC,MAAM,CAAC;;;gBAGL,QAAQ;;iBAEP,aAAa;;;;;;;;;;;;;;;;;;;;;;;;;;;MA2BxB;AACE,gLAAgL,CAAC,EACrL;;;;;MAKE;AACE;;;;;;;;;;GAUG,CAAC,EACR;;iBAEa,aAAa;;CAE7B,CAAC","sourcesContent":["import { css } from '@microsoft/fast-element';\nimport { display } from '@microsoft/fast-foundation';\nimport {\n bodyFont,\n bodyFontColor,\n linkFontColor\n} from '../../theme-provider/design-tokens';\n\nexport const styles = css`\n ${display('flex')}\n\n :host {\n font: ${bodyFont};\n outline: none;\n color: ${bodyFontColor};\n width: auto;\n overflow: auto;\n height: 100%;\n }\n\n .viewer {\n font: inherit;\n outline: none;\n box-sizing: border-box;\n position: relative;\n color: inherit;\n overflow-wrap: anywhere;\n }\n\n .viewer > :first-child {\n margin-block-start: 0;\n }\n\n .viewer > :last-child {\n margin-block-end: 0;\n }\n\n li > p {\n margin-block: 0;\n }\n\n ${\n /* In Firefox, if the paragraph within the list is empty, the ordered lists overlap. Therefore, hiding the paragraph element allows for the proper rendering of empty lists. */ ''\n }\n li > p:empty {\n display: none;\n }\n\n ${\n /**\n * In the rich-text editor, an absolute link renders as a native anchor, not a `nimble-anchor`. When such a link\n * is not HTTPS/HTTP, the anchor renders without an `href`, appearing as plain text.\n * However, in the rich-text viewer, absolute links are rendered as `nimble-anchor`s, and they do not look like\n * plain text when the `href` attribute is absent. They have a \"disabled\" color and may have an underline.\n * To ensure a consistent appearance between the editor and viewer, we force the font color to the default link/\n * plain text color regardless of the `href` attribute's presence. To remove the underline, the markdown parser\n * emits an `underline-hidden` attribute when the `href` attribute is absent.\n *\n * See models/markdown-parser.ts where link elements are emitted for more info.\n */ ''\n }\n nimble-anchor::part(control) {\n color: ${linkFontColor};\n }\n`;\n"]}
|
|
@@ -97,7 +97,7 @@ export const [subtitleFont, subtitleFontColor, subtitleDisabledFontColor, subtit
|
|
|
97
97
|
export const [linkFont, linkFontColor, linkDisabledFontColor, linkFontFamily, linkFontWeight, linkFontSize, linkFontLineHeight, linkFallbackFontFamily] = createFontTokens(tokenNames.linkFont, (element) => getDefaultFontColorForTheme(element), (element) => hexToRgbaCssColor(getDefaultFontColorForTheme(element), 0.3), LinkLightUiFamily, LinkLightUiWeight, LinkLightUiSize, LinkLineHeight, LinkFallbackFontFamily);
|
|
98
98
|
export const [linkActiveFont, linkActiveFontColor, linkActiveDisabledFontColor, linkActiveFontFamily, linkActiveFontWeight, linkActiveFontSize, linkActiveFontLineHeight, linkActiveFallbackFontFamily] = createFontTokens(tokenNames.linkActiveFont, (element) => getColorForTheme(element, DigitalGreenLight, DigitalGreenLight, hexToRgbaCssColor(White, 0.6)), (element) => hexToRgbaCssColor(getDefaultFontColorForTheme(element), 0.3), LinkLightUiFamily, LinkLightUiWeight, LinkLightUiSize, LinkLineHeight, LinkFallbackFontFamily);
|
|
99
99
|
export const [linkProminentFont, linkProminentFontColor, linkProminentDisabledFontColor, linkProminentFontFamily, linkProminentFontWeight, linkProminentFontSize, linkProminentFontLineHeight, linkProminentFallbackFontFamily] = createFontTokens(tokenNames.linkProminentFont, (element) => getColorForTheme(element, DigitalGreenDark105, PowerGreen, PowerGreen), (element) => hexToRgbaCssColor(getDefaultFontColorForTheme(element), 0.3), LinkLightUiFamily, LinkLightUiWeight, LinkLightUiSize, LinkLineHeight, LinkFallbackFontFamily);
|
|
100
|
-
export const [linkActiveProminentFont, linkActiveProminentFontColor, linkActiveProminentDisabledFontColor, linkActiveProminentFontFamily, linkActiveProminentFontWeight, linkActiveProminentFontSize, linkActiveProminentFontLineHeight, linkActiveProminentFallbackFontFamily] = createFontTokens(tokenNames.linkActiveProminentFont, (element) => getColorForTheme(element, DigitalGreenLight, DigitalGreenLight,
|
|
100
|
+
export const [linkActiveProminentFont, linkActiveProminentFontColor, linkActiveProminentDisabledFontColor, linkActiveProminentFontFamily, linkActiveProminentFontWeight, linkActiveProminentFontSize, linkActiveProminentFontLineHeight, linkActiveProminentFallbackFontFamily] = createFontTokens(tokenNames.linkActiveProminentFont, (element) => getColorForTheme(element, DigitalGreenLight, DigitalGreenLight, hexToRgbaCssColor(White, 0.6)), (element) => hexToRgbaCssColor(getDefaultFontColorForTheme(element), 0.3), LinkLightUiFamily, LinkLightUiWeight, LinkLightUiSize, LinkLineHeight, LinkFallbackFontFamily);
|
|
101
101
|
export const [placeholderFont, placeholderFontColor, placeholderDisabledFontColor, placeholderFontFamily, placeholderFontWeight, placeholderFontSize, placeholderFontLineHeight, placeholderFallbackFontFamily] = createFontTokens(tokenNames.placeholderFont, (element) => hexToRgbaCssColor(getDefaultFontColorForTheme(element), 0.6), (element) => hexToRgbaCssColor(getDefaultFontColorForTheme(element), 0.3), PlaceholderFamily, PlaceholderWeight, PlaceholderSize, PlaceholderLineHeight, PlaceholderFallbackFontFamily);
|
|
102
102
|
export const [bodyFont, bodyFontColor, bodyDisabledFontColor, bodyFontFamily, bodyFontWeight, bodyFontSize, bodyFontLineHeight, bodyFallbackFontFamily] = createFontTokens(tokenNames.bodyFont, (element) => getDefaultFontColorForTheme(element), (element) => hexToRgbaCssColor(getDefaultFontColorForTheme(element), 0.3), BodyFamily, BodyWeight, BodySize, BodyLineHeight, BodyFallbackFontFamily);
|
|
103
103
|
export const [bodyEmphasizedFont, bodyEmphasizedFontColor, bodyEmphasizedDisabledFontColor, bodyEmphasizedFontFamily, bodyEmphasizedFontWeight, bodyEmphasizedFontSize, bodyEmphasizedFontLineHeight, bodyEmphasizedFallbackFontFamily] = createFontTokens(tokenNames.bodyEmphasizedFont, (element) => getDefaultFontColorForTheme(element), (element) => hexToRgbaCssColor(getDefaultFontColorForTheme(element), 0.3), BodyEmphasizedFamily, BodyEmphasizedWeight, BodyEmphasizedSize, BodyEmphasizedLineHeight, BodyEmphasizedFallbackFontFamily);
|