@salesforcedevs/docs-components 0.56.2-comp-flex-ref-1 → 0.56.2-example
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/lwc.config.json +10 -2
- package/package.json +18 -12
- package/src/modules/doc/{amfReference/utils.ts → amfModelParser/amfModelParser.ts} +10 -5
- package/src/modules/doc/amfReference/amfReference.css +23 -3
- package/src/modules/doc/amfReference/amfReference.html +34 -21
- package/src/modules/doc/amfReference/amfReference.ts +386 -102
- package/src/modules/doc/amfReference/types.ts +5 -12
- package/src/modules/doc/amfTopic/amfTopic.css +20 -0
- package/src/modules/doc/amfTopic/amfTopic.ts +35 -18
- package/src/modules/doc/amfTopic/types.ts +15 -13
- package/src/modules/doc/amfTopic/utils.ts +12 -6
- package/src/modules/doc/breadcrumbItem/breadcrumbItem.css +2 -1
- package/src/modules/doc/breadcrumbItem/breadcrumbItem.html +1 -1
- package/src/modules/doc/breadcrumbItem/breadcrumbItem.ts +22 -0
- package/src/modules/doc/breadcrumbs/breadcrumbs.css +9 -1
- package/src/modules/doc/breadcrumbs/breadcrumbs.html +44 -34
- package/src/modules/doc/breadcrumbs/breadcrumbs.ts +62 -23
- package/src/modules/doc/componentPlayground/componentPlayground.css +22 -0
- package/src/modules/doc/componentPlayground/componentPlayground.html +20 -0
- package/src/modules/doc/componentPlayground/componentPlayground.ts +42 -0
- package/src/modules/doc/content/content.css +70 -76
- package/src/modules/doc/content/content.html +1 -0
- package/src/modules/doc/content/content.ts +26 -47
- package/src/modules/doc/contentCallout/contentCallout.css +15 -7
- package/src/modules/doc/contentCallout/contentCallout.html +13 -4
- package/src/modules/doc/contentCallout/contentCallout.ts +14 -2
- package/src/modules/doc/contentLayout/contentLayout.css +1 -100
- package/src/modules/doc/contentLayout/contentLayout.html +30 -17
- package/src/modules/doc/contentLayout/contentLayout.ts +315 -70
- package/src/modules/doc/doDont/doDont.css +47 -0
- package/src/modules/doc/doDont/doDont.html +27 -0
- package/src/modules/doc/doDont/doDont.ts +17 -0
- package/src/modules/doc/header/header.css +65 -36
- package/src/modules/doc/header/header.html +41 -139
- package/src/modules/doc/header/header.ts +54 -76
- package/src/modules/doc/heading/heading.css +16 -37
- package/src/modules/doc/heading/heading.html +4 -4
- package/src/modules/doc/heading/heading.ts +12 -10
- package/src/modules/doc/headingAnchor/headingAnchor.css +2 -2
- package/src/modules/doc/headingAnchor/headingAnchor.ts +2 -2
- package/src/modules/doc/headingContent/headingContent.css +6 -8
- package/src/modules/doc/headingContent/headingContent.html +9 -15
- package/src/modules/doc/headingContent/headingContent.ts +2 -14
- package/src/modules/doc/lwcContentLayout/lwcContentLayout.css +1 -0
- package/src/modules/doc/lwcContentLayout/lwcContentLayout.html +68 -0
- package/src/modules/doc/lwcContentLayout/lwcContentLayout.ts +256 -0
- package/src/modules/doc/overview/overview.css +40 -0
- package/src/modules/doc/overview/overview.html +34 -0
- package/src/modules/doc/overview/overview.ts +12 -0
- package/src/modules/doc/phase/phase.css +18 -3
- package/src/modules/doc/phase/phase.html +15 -3
- package/src/modules/doc/phase/phase.ts +44 -8
- package/src/modules/doc/specificationContent/specificationContent.css +36 -0
- package/src/modules/doc/specificationContent/specificationContent.html +167 -0
- package/src/modules/doc/specificationContent/specificationContent.ts +127 -0
- package/src/modules/doc/sprigSurvey/sprigSurvey.html +20 -0
- package/src/modules/doc/sprigSurvey/sprigSurvey.scoped.css +16 -0
- package/src/modules/doc/sprigSurvey/sprigSurvey.ts +16 -0
- package/src/modules/doc/toc/toc.ts +1 -1
- package/src/modules/doc/versionPicker/versionPicker.css +64 -0
- package/src/modules/doc/versionPicker/versionPicker.html +38 -0
- package/src/modules/doc/versionPicker/versionPicker.ts +65 -0
- package/src/modules/doc/xmlContent/types.ts +12 -3
- package/src/modules/doc/xmlContent/utils.ts +17 -12
- package/src/modules/doc/xmlContent/xmlContent.css +32 -3
- package/src/modules/doc/xmlContent/xmlContent.html +41 -15
- package/src/modules/doc/xmlContent/xmlContent.ts +310 -96
- package/src/modules/docHelpers/amfStyle/amfStyle.css +10 -45
- package/src/modules/docHelpers/contentLayoutStyle/contentLayoutStyle.css +131 -0
- package/src/modules/docHelpers/imgStyle/imgStyle.css +59 -0
- package/src/modules/docHelpers/status/status.css +1 -1
- package/src/modules/docUtils/{SearchSyncer/SearchSyncer.ts → searchSyncer/searchSyncer.ts} +1 -0
- package/src/modules/docUtils/utils/__mocks__/coveo.analytics.ts +16 -0
- package/src/modules/docUtils/utils/coveo.analytics.d.ts +10 -0
- package/src/modules/docUtils/utils/utils.ts +32 -0
- package/src/modules/docBaseElements/lightningElementWithState/lightningElementWithState.ts +0 -93
- package/src/modules/docHelpers/phaseContentLayout/phaseContentLayout.css +0 -39
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
<template>
|
|
2
2
|
<h1 class={className} if:true={isAriaLevelOne}>
|
|
3
|
-
<doc-heading-content
|
|
3
|
+
<doc-heading-content header={header} hash={hash}></doc-heading-content>
|
|
4
4
|
</h1>
|
|
5
5
|
<h2 class={className} if:true={isAriaLevelTwo}>
|
|
6
|
-
<doc-heading-content
|
|
6
|
+
<doc-heading-content header={header} hash={hash}></doc-heading-content>
|
|
7
7
|
</h2>
|
|
8
8
|
<h3 class={className} if:true={isAriaLevelThree}>
|
|
9
|
-
<doc-heading-content
|
|
9
|
+
<doc-heading-content header={header} hash={hash}></doc-heading-content>
|
|
10
10
|
</h3>
|
|
11
11
|
<h4 class={className} if:true={isAriaLevelFour}>
|
|
12
|
-
<doc-heading-content
|
|
12
|
+
<doc-heading-content header={header} hash={hash}></doc-heading-content>
|
|
13
13
|
</h4>
|
|
14
14
|
</template>
|
|
@@ -1,22 +1,24 @@
|
|
|
1
1
|
import { LightningElement, api } from "lwc";
|
|
2
2
|
|
|
3
|
-
export const displayLevels = ["3", "4", "5", "6"];
|
|
4
|
-
|
|
5
|
-
export const ariaLevels = ["1", "2", "3", "4"];
|
|
6
|
-
|
|
7
3
|
export const ariaDisplayLevels: { [key: string]: string } = {
|
|
8
|
-
"1": "
|
|
9
|
-
"2": "
|
|
10
|
-
"3": "
|
|
11
|
-
"4": "
|
|
4
|
+
"1": "4",
|
|
5
|
+
"2": "5",
|
|
6
|
+
"3": "6",
|
|
7
|
+
"4": "8"
|
|
12
8
|
};
|
|
13
9
|
|
|
10
|
+
export const ariaLevels = Object.keys(ariaDisplayLevels);
|
|
11
|
+
|
|
12
|
+
export const displayLevels = Object.values(ariaDisplayLevels);
|
|
13
|
+
|
|
14
|
+
// @ts-ignore: Really Dark Magic (TM) to do with ariaLevel needing explicit getter/setters
|
|
14
15
|
export default class Heading extends LightningElement {
|
|
15
|
-
@api
|
|
16
|
+
@api header: string = "";
|
|
16
17
|
@api hash: string | null = null;
|
|
17
18
|
|
|
18
19
|
@api
|
|
19
20
|
private get ariaLevel(): string {
|
|
21
|
+
// Really Dark Magic (TM)
|
|
20
22
|
return this._ariaLevel || "2";
|
|
21
23
|
}
|
|
22
24
|
private set ariaLevel(value: string | null) {
|
|
@@ -60,6 +62,6 @@ export default class Heading extends LightningElement {
|
|
|
60
62
|
}
|
|
61
63
|
|
|
62
64
|
private get className(): string {
|
|
63
|
-
return `display-${this.displayLevel}`;
|
|
65
|
+
return `dx-text-display-${this.displayLevel}`;
|
|
64
66
|
}
|
|
65
67
|
}
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
button {
|
|
4
4
|
opacity: 0;
|
|
5
|
-
color: rgb(11
|
|
5
|
+
color: rgb(11 92 171);
|
|
6
6
|
}
|
|
7
7
|
|
|
8
8
|
button:hover {
|
|
@@ -17,7 +17,7 @@ button:focus {
|
|
|
17
17
|
|
|
18
18
|
button:focus-visible {
|
|
19
19
|
border-radius: 4px;
|
|
20
|
-
border: 2px solid rgb(11
|
|
20
|
+
border: 2px solid rgb(11 92 171);
|
|
21
21
|
}
|
|
22
22
|
|
|
23
23
|
.icon-wrapper {
|
|
@@ -6,7 +6,7 @@ export default class HeadingAnchor extends LightningElement {
|
|
|
6
6
|
@api iconSize?: IconSize = "override";
|
|
7
7
|
@api iconSprite?: IconSprite = "utility";
|
|
8
8
|
@api iconSymbol?: IconSymbol;
|
|
9
|
-
@api
|
|
9
|
+
@api header: string = "";
|
|
10
10
|
@api urlText: string = "";
|
|
11
11
|
|
|
12
12
|
label: string = "Copy link to clipboard";
|
|
@@ -22,7 +22,7 @@ export default class HeadingAnchor extends LightningElement {
|
|
|
22
22
|
}, 2000);
|
|
23
23
|
|
|
24
24
|
try {
|
|
25
|
-
if (this.
|
|
25
|
+
if (this.header && this.urlText) {
|
|
26
26
|
const [hostUrl] = window.location.href.split("#");
|
|
27
27
|
const url = `${hostUrl}#${this.urlText}`;
|
|
28
28
|
await navigator.clipboard.writeText(url);
|
|
@@ -8,12 +8,14 @@
|
|
|
8
8
|
|
|
9
9
|
dx-tooltip {
|
|
10
10
|
line-height: var(--button-size);
|
|
11
|
+
padding-right: var(--dx-g-spacing-xs);
|
|
11
12
|
}
|
|
12
13
|
|
|
13
14
|
.button-container {
|
|
14
15
|
height: 100%;
|
|
15
16
|
margin-right: calc(var(--dx-g-spacing-xl) - 4px);
|
|
16
17
|
position: relative;
|
|
18
|
+
padding-right: var(--dx-g-spacing-xs);
|
|
17
19
|
}
|
|
18
20
|
|
|
19
21
|
button {
|
|
@@ -21,7 +23,7 @@ button {
|
|
|
21
23
|
bottom: var(--doc-c-heading-anchor-button-bottom);
|
|
22
24
|
left: 0;
|
|
23
25
|
opacity: 0;
|
|
24
|
-
color: rgb(11
|
|
26
|
+
color: rgb(11 92 171);
|
|
25
27
|
display: flex;
|
|
26
28
|
justify-content: center;
|
|
27
29
|
align-items: center;
|
|
@@ -34,12 +36,8 @@ dx-icon {
|
|
|
34
36
|
--dx-c-icon-size: var(--doc-c-heading-anchor-icon-size);
|
|
35
37
|
}
|
|
36
38
|
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
}
|
|
40
|
-
|
|
41
|
-
.nowrap {
|
|
42
|
-
white-space: nowrap;
|
|
39
|
+
.title {
|
|
40
|
+
word-break: break-word;
|
|
43
41
|
}
|
|
44
42
|
|
|
45
43
|
button:focus {
|
|
@@ -49,7 +47,7 @@ button:focus {
|
|
|
49
47
|
button:focus,
|
|
50
48
|
button:hover,
|
|
51
49
|
span:hover dx-tooltip button,
|
|
52
|
-
span:hover ~
|
|
50
|
+
span:hover ~ dx-tooltip button {
|
|
53
51
|
opacity: 1;
|
|
54
52
|
outline: none;
|
|
55
53
|
}
|
|
@@ -1,19 +1,13 @@
|
|
|
1
1
|
<template>
|
|
2
|
-
<template if:false={hash}>{
|
|
2
|
+
<template if:false={hash}>{header}</template>
|
|
3
3
|
<template if:true={hash}>
|
|
4
|
-
<
|
|
5
|
-
|
|
6
|
-
<span
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
<button onclick={copy} aria-label="copy">
|
|
13
|
-
<dx-icon size="override" symbol="link"></dx-icon>
|
|
14
|
-
</button>
|
|
15
|
-
</span>
|
|
16
|
-
</dx-tooltip>
|
|
17
|
-
</span>
|
|
4
|
+
<span class="title">{header} </span>
|
|
5
|
+
<dx-tooltip placement="top" label={label}>
|
|
6
|
+
<span class="button-container">
|
|
7
|
+
<button onclick={copy} aria-label="copy">
|
|
8
|
+
<dx-icon size="override" symbol="link"></dx-icon>
|
|
9
|
+
</button>
|
|
10
|
+
</span>
|
|
11
|
+
</dx-tooltip>
|
|
18
12
|
</template>
|
|
19
13
|
</template>
|
|
@@ -1,24 +1,12 @@
|
|
|
1
1
|
import { LightningElement, api } from "lwc";
|
|
2
2
|
|
|
3
3
|
export default class HeadingContent extends LightningElement {
|
|
4
|
-
@api
|
|
4
|
+
@api header: string = "";
|
|
5
5
|
@api hash: string | null = null;
|
|
6
6
|
|
|
7
7
|
label: string = "Copy link to clipboard";
|
|
8
8
|
timeout: number | null = null;
|
|
9
9
|
|
|
10
|
-
private get titleToWrap(): string {
|
|
11
|
-
return this.title.substring(0, this.title.lastIndexOf(" "));
|
|
12
|
-
}
|
|
13
|
-
|
|
14
|
-
private get needsSpace(): boolean {
|
|
15
|
-
return this.titleToWrap.length > 0;
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
private get titleNoWrap(): string {
|
|
19
|
-
return this.title.substring(this.title.lastIndexOf(" ") + 1);
|
|
20
|
-
}
|
|
21
|
-
|
|
22
10
|
private async copy() {
|
|
23
11
|
if (this.timeout) {
|
|
24
12
|
window.clearTimeout(this.timeout);
|
|
@@ -30,7 +18,7 @@ export default class HeadingContent extends LightningElement {
|
|
|
30
18
|
}, 2000);
|
|
31
19
|
|
|
32
20
|
try {
|
|
33
|
-
if (this.
|
|
21
|
+
if (this.header && this.hash) {
|
|
34
22
|
const [hostUrl] = window.location.href.split("#");
|
|
35
23
|
const url = `${hostUrl}#${this.hash}`;
|
|
36
24
|
await navigator.clipboard.writeText(url);
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
@import "docHelpers/contentLayoutStyle";
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
<template>
|
|
2
|
+
<div class="content">
|
|
3
|
+
<template lwc:if={useOldSidebar}>
|
|
4
|
+
<dx-sidebar-old
|
|
5
|
+
class="is-sticky left-nav-bar"
|
|
6
|
+
trees={sidebarContent}
|
|
7
|
+
value={sidebarValue}
|
|
8
|
+
header={sidebarHeader}
|
|
9
|
+
ontogglesidebar={onToggleSidebar}
|
|
10
|
+
languages={languages}
|
|
11
|
+
language={language}
|
|
12
|
+
bail-href={bailHref}
|
|
13
|
+
bail-label={bailLabel}
|
|
14
|
+
dev-center={devCenter}
|
|
15
|
+
brand={brand}
|
|
16
|
+
>
|
|
17
|
+
<slot name="sidebar-header" slot="version-picker"></slot>
|
|
18
|
+
</dx-sidebar-old>
|
|
19
|
+
</template>
|
|
20
|
+
<template lwc:else>
|
|
21
|
+
<dx-sidebar
|
|
22
|
+
class="is-sticky left-nav-bar"
|
|
23
|
+
trees={sidebarContent}
|
|
24
|
+
value={sidebarValue}
|
|
25
|
+
header={sidebarHeader}
|
|
26
|
+
coveo-organization-id={coveoOrganizationId}
|
|
27
|
+
coveo-public-access-token={coveoPublicAccessToken}
|
|
28
|
+
coveo-search-hub={coveoSearchHub}
|
|
29
|
+
coveo-advanced-query-config={coveoAdvancedQueryConfig}
|
|
30
|
+
ontogglesidebar={onToggleSidebar}
|
|
31
|
+
languages={languages}
|
|
32
|
+
language={language}
|
|
33
|
+
bail-href={bailHref}
|
|
34
|
+
bail-label={bailLabel}
|
|
35
|
+
dev-center={devCenter}
|
|
36
|
+
brand={brand}
|
|
37
|
+
>
|
|
38
|
+
<slot name="sidebar-header" slot="version-picker"></slot>
|
|
39
|
+
</dx-sidebar>
|
|
40
|
+
</template>
|
|
41
|
+
<div class="content-body-doc-phase-container">
|
|
42
|
+
<slot name="doc-phase"></slot>
|
|
43
|
+
<slot name="version-banner"></slot>
|
|
44
|
+
<div class="content-body-container">
|
|
45
|
+
<div class="content-body">
|
|
46
|
+
<doc-breadcrumbs
|
|
47
|
+
lwc:if={showBreadcrumbs}
|
|
48
|
+
breadcrumbs={breadcrumbs}
|
|
49
|
+
></doc-breadcrumbs>
|
|
50
|
+
<slot onslotchange={onSlotChange}></slot>
|
|
51
|
+
<doc-sprig-survey
|
|
52
|
+
lwc:if={shouldDisplayFeedback}
|
|
53
|
+
></doc-sprig-survey>
|
|
54
|
+
</div>
|
|
55
|
+
<div lwc:if={showToc} class="right-nav-bar is-sticky">
|
|
56
|
+
<dx-toc
|
|
57
|
+
header={tocTitle}
|
|
58
|
+
options={tocOptions}
|
|
59
|
+
value={tocValue}
|
|
60
|
+
></dx-toc>
|
|
61
|
+
</div>
|
|
62
|
+
</div>
|
|
63
|
+
<div lwc:if={showFooter} class="footer-container">
|
|
64
|
+
<dx-footer variant="no-signup"></dx-footer>
|
|
65
|
+
</div>
|
|
66
|
+
</div>
|
|
67
|
+
</div>
|
|
68
|
+
</template>
|
|
@@ -0,0 +1,256 @@
|
|
|
1
|
+
import ContentLayout from "doc/contentLayout";
|
|
2
|
+
|
|
3
|
+
const TOC_HEADER_TAG = "doc-heading";
|
|
4
|
+
const RNB_BY_TAB = "docs-tab";
|
|
5
|
+
const SPECIFICATION_TAG = "doc-specification-content";
|
|
6
|
+
export const OBSERVER_ATTACH_WAIT_TIME = 500;
|
|
7
|
+
|
|
8
|
+
export default class LwcContentLayout extends ContentLayout {
|
|
9
|
+
private rnbByTab: boolean = false;
|
|
10
|
+
|
|
11
|
+
// DOM element caches to avoid repeated queries
|
|
12
|
+
private tabPanelListCache: any = null;
|
|
13
|
+
private hasSpecContentCache: boolean | null = null;
|
|
14
|
+
private allTabsCache: any[] | null = null;
|
|
15
|
+
private mainSlotCache: any = null;
|
|
16
|
+
|
|
17
|
+
private setRNBByTab() {
|
|
18
|
+
const tabPanelListItem = this.getTabPanelList();
|
|
19
|
+
this.rnbByTab = tabPanelListItem?.id === RNB_BY_TAB;
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
get showTabBasedRNB() {
|
|
23
|
+
return this.rnbByTab;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
/**
|
|
27
|
+
* Check if the main slot contains doc-specification-content
|
|
28
|
+
* Uses caching to avoid repeated DOM queries
|
|
29
|
+
*/
|
|
30
|
+
private hasSpecificationContent(): boolean {
|
|
31
|
+
if (this.hasSpecContentCache !== null) {
|
|
32
|
+
return this.hasSpecContentCache;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
const mainSlot = this.getMainSlot();
|
|
36
|
+
if (mainSlot) {
|
|
37
|
+
const assignedElements = (mainSlot as any).assignedElements();
|
|
38
|
+
|
|
39
|
+
for (const element of assignedElements) {
|
|
40
|
+
if (
|
|
41
|
+
element.tagName === SPECIFICATION_TAG ||
|
|
42
|
+
element.querySelector(SPECIFICATION_TAG) ||
|
|
43
|
+
element.shadowRoot?.querySelector(SPECIFICATION_TAG)
|
|
44
|
+
) {
|
|
45
|
+
return (this.hasSpecContentCache = true);
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
return (this.hasSpecContentCache = false);
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
/**
|
|
53
|
+
* Clear all caches when content changes
|
|
54
|
+
*/
|
|
55
|
+
private clearAllCaches(): void {
|
|
56
|
+
this.hasSpecContentCache = null;
|
|
57
|
+
this.tabPanelListCache = null;
|
|
58
|
+
this.allTabsCache = null;
|
|
59
|
+
this.mainSlotCache = null;
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
/**
|
|
63
|
+
* Get the main slot element with caching
|
|
64
|
+
*/
|
|
65
|
+
private getMainSlot(): any {
|
|
66
|
+
if (!this.mainSlotCache) {
|
|
67
|
+
this.mainSlotCache =
|
|
68
|
+
this.template.querySelector("slot:not([name])");
|
|
69
|
+
}
|
|
70
|
+
return this.mainSlotCache;
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
/**
|
|
74
|
+
* Get tab panel list with caching
|
|
75
|
+
*/
|
|
76
|
+
private getTabPanelList(): any {
|
|
77
|
+
if (!this.tabPanelListCache) {
|
|
78
|
+
// eslint-disable-next-line @lwc/lwc/no-document-query
|
|
79
|
+
this.tabPanelListCache =
|
|
80
|
+
document.querySelector("dx-tab-panel-list");
|
|
81
|
+
}
|
|
82
|
+
return this.tabPanelListCache;
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
onRNBClick = (event: CustomEvent) => {
|
|
86
|
+
event.stopPropagation();
|
|
87
|
+
if (this.hasSpecificationContent()) {
|
|
88
|
+
this.didScrollToSelectedHash = false;
|
|
89
|
+
}
|
|
90
|
+
};
|
|
91
|
+
|
|
92
|
+
onTabChanged = () => {
|
|
93
|
+
this.updateRNB();
|
|
94
|
+
|
|
95
|
+
const { hash } = window.location;
|
|
96
|
+
if (this.hasSpecificationContent() && hash) {
|
|
97
|
+
this.didScrollToSelectedHash = false;
|
|
98
|
+
|
|
99
|
+
requestAnimationFrame(() => this.updateHeadingForRNB());
|
|
100
|
+
}
|
|
101
|
+
};
|
|
102
|
+
|
|
103
|
+
protected getHeadingElements() {
|
|
104
|
+
let headingElements = super.getHeadingElements();
|
|
105
|
+
if (this.showTabBasedRNB) {
|
|
106
|
+
const tabPanelListItem = this.getTabPanelList();
|
|
107
|
+
const tabPanels =
|
|
108
|
+
tabPanelListItem?.querySelectorAll("dx-tab-panel");
|
|
109
|
+
|
|
110
|
+
for (const tabPanelItem of tabPanels) {
|
|
111
|
+
if (tabPanelItem.active) {
|
|
112
|
+
// This is needed for Specification tab content
|
|
113
|
+
const specificationElement = tabPanelItem.querySelector(
|
|
114
|
+
"doc-specification-content"
|
|
115
|
+
);
|
|
116
|
+
if (specificationElement) {
|
|
117
|
+
headingElements =
|
|
118
|
+
specificationElement.shadowRoot.querySelectorAll(
|
|
119
|
+
TOC_HEADER_TAG
|
|
120
|
+
);
|
|
121
|
+
} else {
|
|
122
|
+
headingElements =
|
|
123
|
+
tabPanelItem.querySelectorAll(TOC_HEADER_TAG);
|
|
124
|
+
}
|
|
125
|
+
break;
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
return headingElements;
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
private updateURL() {
|
|
133
|
+
const tabs = this.getAllTabs();
|
|
134
|
+
const selectedTabId = this.getSelectedTabId();
|
|
135
|
+
|
|
136
|
+
tabs.forEach((tab: any) => {
|
|
137
|
+
if (tab.getAttribute("aria-selected") === "true") {
|
|
138
|
+
const tabID = tab.getAttribute("aria-label");
|
|
139
|
+
const url = new URL(window.location.href);
|
|
140
|
+
if (selectedTabId !== tabID) {
|
|
141
|
+
url.searchParams.set("type", tabID);
|
|
142
|
+
url.hash = "";
|
|
143
|
+
window.history.pushState({}, "", url.toString());
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
});
|
|
147
|
+
}
|
|
148
|
+
|
|
149
|
+
// This event gets triggered when navigating back/forward
|
|
150
|
+
handlePopState = (): void => {
|
|
151
|
+
if (this.showTabBasedRNB) {
|
|
152
|
+
this.restoreTabSelection();
|
|
153
|
+
}
|
|
154
|
+
};
|
|
155
|
+
|
|
156
|
+
connectedCallback(): void {
|
|
157
|
+
super.connectedCallback();
|
|
158
|
+
window.addEventListener("popstate", this.handlePopState);
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
private getSelectedTabId() {
|
|
162
|
+
const urlParams = new URLSearchParams(window.location.search);
|
|
163
|
+
const selectedTabId = urlParams.get("type");
|
|
164
|
+
return selectedTabId;
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
private restoreTabSelection() {
|
|
168
|
+
requestAnimationFrame(() => {
|
|
169
|
+
const selectedTabId = this.getSelectedTabId();
|
|
170
|
+
if (selectedTabId) {
|
|
171
|
+
this.selectTabById(selectedTabId);
|
|
172
|
+
|
|
173
|
+
// If there's a hash and we have specification content,
|
|
174
|
+
// we need to wait for the content to load before scrolling
|
|
175
|
+
const { hash } = window.location;
|
|
176
|
+
if (this.hasSpecificationContent() && hash) {
|
|
177
|
+
// Reset the scroll flag to allow scrolling once content is loaded
|
|
178
|
+
this.didScrollToSelectedHash = false;
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
});
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
private getAllTabs(): any[] {
|
|
185
|
+
// Return cached result if available
|
|
186
|
+
if (this.allTabsCache) {
|
|
187
|
+
return this.allTabsCache;
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
const tabPanelListItem = this.getTabPanelList();
|
|
191
|
+
if (tabPanelListItem?.shadowRoot) {
|
|
192
|
+
this.allTabsCache = Array.from(
|
|
193
|
+
tabPanelListItem.shadowRoot.querySelectorAll(
|
|
194
|
+
"dx-tab-panel-item"
|
|
195
|
+
)
|
|
196
|
+
).map((tabPanelItem: any) =>
|
|
197
|
+
tabPanelItem.shadowRoot.querySelector("button")
|
|
198
|
+
);
|
|
199
|
+
} else {
|
|
200
|
+
this.allTabsCache = [];
|
|
201
|
+
}
|
|
202
|
+
|
|
203
|
+
return this.allTabsCache;
|
|
204
|
+
}
|
|
205
|
+
|
|
206
|
+
private selectTabById(tabId: string) {
|
|
207
|
+
const tabs = this.getAllTabs();
|
|
208
|
+
tabs.forEach((tab: any) => {
|
|
209
|
+
if (tab.getAttribute("aria-label") === tabId) {
|
|
210
|
+
tab.click();
|
|
211
|
+
}
|
|
212
|
+
});
|
|
213
|
+
}
|
|
214
|
+
|
|
215
|
+
postRenderedCallback(): void {
|
|
216
|
+
this.setRNBByTab();
|
|
217
|
+
if (this.showTabBasedRNB) {
|
|
218
|
+
window.addEventListener("tabchanged", this.onTabChanged);
|
|
219
|
+
window.addEventListener(
|
|
220
|
+
"specificationdatarendered",
|
|
221
|
+
this.onTabChanged
|
|
222
|
+
);
|
|
223
|
+
window.addEventListener("selectedcontent", (event) =>
|
|
224
|
+
this.onRNBClick(event as CustomEvent)
|
|
225
|
+
);
|
|
226
|
+
this.restoreTabSelection();
|
|
227
|
+
}
|
|
228
|
+
}
|
|
229
|
+
|
|
230
|
+
disconnectedCallback(): void {
|
|
231
|
+
super.disconnectedCallback();
|
|
232
|
+
if (this.showTabBasedRNB) {
|
|
233
|
+
window.removeEventListener("tabchanged", this.onTabChanged);
|
|
234
|
+
window.removeEventListener(
|
|
235
|
+
"specificationdatarendered",
|
|
236
|
+
this.onTabChanged
|
|
237
|
+
);
|
|
238
|
+
window.removeEventListener("selectedcontent", (event) =>
|
|
239
|
+
this.onRNBClick(event as CustomEvent)
|
|
240
|
+
);
|
|
241
|
+
window.removeEventListener("popstate", this.handlePopState);
|
|
242
|
+
}
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
onSlotChange(): void {
|
|
246
|
+
this.clearAllCaches();
|
|
247
|
+
super.onSlotChange();
|
|
248
|
+
}
|
|
249
|
+
|
|
250
|
+
updateHeadingForRNB(): void {
|
|
251
|
+
if (this.showTabBasedRNB) {
|
|
252
|
+
this.updateURL();
|
|
253
|
+
}
|
|
254
|
+
super.updateHeadingForRNB();
|
|
255
|
+
}
|
|
256
|
+
}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
doc-phase {
|
|
2
|
+
--doc-c-phase-top: calc(
|
|
3
|
+
var(--dx-g-global-header-height) + var(--dx-g-doc-header-height)
|
|
4
|
+
);
|
|
5
|
+
}
|
|
6
|
+
|
|
7
|
+
dx-section {
|
|
8
|
+
--dx-c-section-padding-top: 0;
|
|
9
|
+
--dx-c-section-padding-bottom: var(--dx-g-spacing-2xl);
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
dx-section::part(content) {
|
|
13
|
+
max-width: 1280px;
|
|
14
|
+
margin: auto;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
dx-group-text:first-of-type {
|
|
18
|
+
margin-top: var(--dx-g-spacing-2xl);
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
dx-group-text.features {
|
|
22
|
+
margin-top: var(--dx-g-spacing-xl);
|
|
23
|
+
margin-bottom: var(--dx-g-spacing-xl);
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
.content {
|
|
27
|
+
padding-right: var(--dx-g-spacing-xl);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
@media (max-width: 1024px) {
|
|
31
|
+
.content {
|
|
32
|
+
padding-right: 0;
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
@media (max-width: 800px) {
|
|
37
|
+
dx-group-text.description {
|
|
38
|
+
margin-top: var(--dx-g-spacing-lg);
|
|
39
|
+
}
|
|
40
|
+
}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
<template>
|
|
2
|
+
<div class="container">
|
|
3
|
+
<doc-phase
|
|
4
|
+
if:true={docPhaseInfo}
|
|
5
|
+
doc-phase-info={docPhaseInfo}
|
|
6
|
+
></doc-phase>
|
|
7
|
+
|
|
8
|
+
<dx-section>
|
|
9
|
+
<dx-grid columns="two-slim-right">
|
|
10
|
+
<div class="content">
|
|
11
|
+
<dx-group-text
|
|
12
|
+
class="description"
|
|
13
|
+
header={header}
|
|
14
|
+
body={description}
|
|
15
|
+
size="large"
|
|
16
|
+
title-aria-level="1"
|
|
17
|
+
primary-link={primaryLink}
|
|
18
|
+
secondary-link={secondaryLink}
|
|
19
|
+
></dx-group-text>
|
|
20
|
+
</div>
|
|
21
|
+
<div>
|
|
22
|
+
<dx-group-text
|
|
23
|
+
header={featuresListTitle}
|
|
24
|
+
size="medium"
|
|
25
|
+
class="features"
|
|
26
|
+
></dx-group-text>
|
|
27
|
+
<dx-features-list
|
|
28
|
+
options={featuresListOptions}
|
|
29
|
+
></dx-features-list>
|
|
30
|
+
</div>
|
|
31
|
+
</dx-grid>
|
|
32
|
+
</dx-section>
|
|
33
|
+
</div>
|
|
34
|
+
</template>
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { LightningElement, api } from "lwc";
|
|
2
|
+
import { DocPhaseInfo, FeatureItem, Link } from "typings/custom";
|
|
3
|
+
|
|
4
|
+
export default class Overview extends LightningElement {
|
|
5
|
+
@api docPhaseInfo!: DocPhaseInfo;
|
|
6
|
+
@api header!: string;
|
|
7
|
+
@api description!: string;
|
|
8
|
+
@api primaryLink!: Link;
|
|
9
|
+
@api secondaryLink!: Link;
|
|
10
|
+
@api featuresListTitle!: string;
|
|
11
|
+
@api featuresListOptions!: FeatureItem[];
|
|
12
|
+
}
|
|
@@ -2,25 +2,39 @@
|
|
|
2
2
|
@import "dxHelpers/text";
|
|
3
3
|
@import "docHelpers/status";
|
|
4
4
|
|
|
5
|
+
:host {
|
|
6
|
+
--doc-c-phase-top: 0;
|
|
7
|
+
--doc-c-phase-container-align-items: flex-start;
|
|
8
|
+
|
|
9
|
+
position: sticky;
|
|
10
|
+
top: var(--doc-c-phase-top);
|
|
11
|
+
|
|
12
|
+
/* NOTE: If you are changing z-index value here, ensure it's less than z-index of dx-sidebar in contentLayout.css */
|
|
13
|
+
z-index: var(--dx-g-z-index-100);
|
|
14
|
+
}
|
|
15
|
+
|
|
5
16
|
.doc-phase-container {
|
|
6
17
|
display: flex;
|
|
7
18
|
flex-direction: column;
|
|
8
|
-
|
|
9
|
-
padding-
|
|
19
|
+
align-items: var(--doc-c-phase-container-align-items);
|
|
20
|
+
padding-left: var(--dx-g-global-header-padding-horizontal);
|
|
21
|
+
padding-right: var(--dx-g-global-header-padding-horizontal);
|
|
10
22
|
width: 100%;
|
|
23
|
+
border: none;
|
|
11
24
|
}
|
|
12
25
|
|
|
13
26
|
.doc-phase-title-container {
|
|
14
27
|
display: flex;
|
|
15
28
|
flex-direction: row;
|
|
16
29
|
align-items: center;
|
|
30
|
+
width: 100%;
|
|
17
31
|
}
|
|
18
32
|
|
|
19
33
|
dx-button {
|
|
20
34
|
margin-left: auto;
|
|
21
35
|
}
|
|
22
36
|
|
|
23
|
-
/*
|
|
37
|
+
/*
|
|
24
38
|
NOTE: Here we are assuming that indicator height won't go beyond 1000px.
|
|
25
39
|
|
|
26
40
|
It's one of the suggested way to achieve the expand/collapse animation
|
|
@@ -31,6 +45,7 @@ dx-button {
|
|
|
31
45
|
*/
|
|
32
46
|
|
|
33
47
|
.doc-phase-body {
|
|
48
|
+
display: block;
|
|
34
49
|
max-height: 1000px;
|
|
35
50
|
overflow: hidden;
|
|
36
51
|
padding-top: var(--dx-g-spacing-smd);
|