pict-section-inlinedocumentation 1.0.1 → 1.0.3
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/LICENSE +21 -0
- package/README.md +11 -13
- package/diagrams/four-levels-of-embeddedness.excalidraw +717 -0
- package/diagrams/four-levels-of-embeddedness.mmd +4 -0
- package/diagrams/four-levels-of-embeddedness.svg +2 -0
- package/docs/README.md +10 -19
- package/docs/_cover.md +6 -0
- package/docs/_sidebar.md +8 -4
- package/docs/_version.json +3 -3
- package/docs/architecture.md +2 -44
- package/docs/diagrams/component-diagram.excalidraw +3546 -0
- package/docs/diagrams/component-diagram.mmd +42 -0
- package/docs/diagrams/component-diagram.svg +2 -0
- package/docs/diagrams/four-levels-of-embeddedness.excalidraw +717 -0
- package/docs/diagrams/four-levels-of-embeddedness.mmd +9 -0
- package/docs/diagrams/four-levels-of-embeddedness.svg +2 -0
- package/docs/diagrams/project-layout.excalidraw +6082 -0
- package/docs/diagrams/project-layout.mmd +25 -0
- package/docs/diagrams/project-layout.svg +2 -0
- package/docs/embedding-level2-routes.md +1 -1
- package/docs/embedding-level4-autogen.md +1 -1
- package/docs/examples/README.md +9 -0
- package/docs/examples/bookshop/README.md +582 -0
- package/docs/examples/bookshop/bookshop_example.js +4519 -0
- package/docs/examples/bookshop/index.html +236 -0
- package/docs/index.html +6 -5
- package/docs/overview.md +4 -4
- package/docs/reference.md +2 -27
- package/docs/retold-catalog.json +77 -178
- package/docs/retold-keyword-index.json +14134 -1917
- package/example_applications/bookshop/package.json +9 -1
- package/package.json +54 -54
- package/source/providers/Pict-Provider-InlineDocumentation.js +27 -3
- package/source/views/Pict-View-InlineDocumentation-Layout.js +135 -3
- package/source/views/Pict-View-InlineDocumentation-Nav.js +101 -10
|
@@ -30,5 +30,13 @@
|
|
|
30
30
|
"from": "./data/pict_documentation_topics.json",
|
|
31
31
|
"to": "./dist/docs/"
|
|
32
32
|
}
|
|
33
|
-
]
|
|
33
|
+
],
|
|
34
|
+
"retold": {
|
|
35
|
+
"ExampleApplication": {
|
|
36
|
+
"Stage": true,
|
|
37
|
+
"Title": "Bookshop",
|
|
38
|
+
"Summary": "E-commerce demo with route-mapped help, data-attribute tooltips, and F1 toggling for pict-section-inlinedocumentation.",
|
|
39
|
+
"Complexity": "Intermediate"
|
|
40
|
+
}
|
|
41
|
+
}
|
|
34
42
|
}
|
package/package.json
CHANGED
|
@@ -1,56 +1,56 @@
|
|
|
1
1
|
{
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
2
|
+
"name": "pict-section-inlinedocumentation",
|
|
3
|
+
"version": "1.0.3",
|
|
4
|
+
"description": "Pict embeddable inline documentation browser with topic support",
|
|
5
|
+
"main": "source/Pict-Section-InlineDocumentation.js",
|
|
6
|
+
"scripts": {
|
|
7
|
+
"start": "node source/Pict-Section-InlineDocumentation.js",
|
|
8
|
+
"test": "npx quack test",
|
|
9
|
+
"tests": "npx quack test -g",
|
|
10
|
+
"coverage": "npx quack coverage",
|
|
11
|
+
"build": "npx quack build",
|
|
12
|
+
"test-browser": "npx mocha test/Browser_Integration_tests.js --timeout 60000"
|
|
13
|
+
},
|
|
14
|
+
"repository": {
|
|
15
|
+
"type": "git",
|
|
16
|
+
"url": "git+https://github.com/fable-retold/pict-section-inlinedocumentation.git"
|
|
17
|
+
},
|
|
18
|
+
"author": "steven velozo <steven@velozo.com>",
|
|
19
|
+
"license": "MIT",
|
|
20
|
+
"bugs": {
|
|
21
|
+
"url": "https://github.com/fable-retold/pict-section-inlinedocumentation/issues"
|
|
22
|
+
},
|
|
23
|
+
"homepage": "https://github.com/fable-retold/pict-section-inlinedocumentation#readme",
|
|
24
|
+
"dependencies": {
|
|
25
|
+
"lunr": "^2.3.9",
|
|
26
|
+
"pict-provider": "^1.0.13",
|
|
27
|
+
"pict-section-content": "^1.0.7",
|
|
28
|
+
"pict-section-markdowneditor": "^1.0.15",
|
|
29
|
+
"pict-section-modal": "^1.1.4",
|
|
30
|
+
"pict-view": "^1.0.68"
|
|
31
|
+
},
|
|
32
|
+
"devDependencies": {
|
|
33
|
+
"pict": "^1.0.372",
|
|
34
|
+
"pict-docuserve": "^1.4.4",
|
|
35
|
+
"puppeteer": "^24.40.0",
|
|
36
|
+
"quackage": "^1.3.0"
|
|
37
|
+
},
|
|
38
|
+
"mocha": {
|
|
39
|
+
"diff": true,
|
|
40
|
+
"extension": [
|
|
41
|
+
"js"
|
|
42
|
+
],
|
|
43
|
+
"package": "./package.json",
|
|
44
|
+
"reporter": "spec",
|
|
45
|
+
"slow": "75",
|
|
46
|
+
"timeout": "5000",
|
|
47
|
+
"ui": "tdd",
|
|
48
|
+
"watch-files": [
|
|
49
|
+
"source/**/*.js",
|
|
50
|
+
"test/**/*.js"
|
|
51
|
+
],
|
|
52
|
+
"watch-ignore": [
|
|
53
|
+
"lib/vendor"
|
|
54
|
+
]
|
|
55
|
+
}
|
|
56
56
|
}
|
|
@@ -2213,24 +2213,48 @@ class InlineDocumentationProvider extends libPictProvider
|
|
|
2213
2213
|
}
|
|
2214
2214
|
else if (tmpCurrentGroup)
|
|
2215
2215
|
{
|
|
2216
|
-
// Indented item — document
|
|
2216
|
+
// Indented item — a document (link) or a sub-folder (no link)
|
|
2217
|
+
// within the current group. Capture the nesting Level from the
|
|
2218
|
+
// indentation so the nav can render real hierarchy.
|
|
2219
|
+
let tmpLevel = Math.max(0, Math.floor((tmpIndent - 2) / 2));
|
|
2217
2220
|
if (tmpLinkMatch)
|
|
2218
2221
|
{
|
|
2219
2222
|
tmpCurrentGroup.Items.push({
|
|
2220
2223
|
Name: tmpLinkMatch[1].trim(),
|
|
2221
|
-
Path: this._normalizePath(tmpLinkMatch[2].trim())
|
|
2224
|
+
Path: this._normalizePath(tmpLinkMatch[2].trim()),
|
|
2225
|
+
Level: tmpLevel
|
|
2222
2226
|
});
|
|
2223
2227
|
}
|
|
2224
2228
|
else
|
|
2225
2229
|
{
|
|
2226
2230
|
tmpCurrentGroup.Items.push({
|
|
2227
2231
|
Name: tmpItemContent,
|
|
2228
|
-
Path: ''
|
|
2232
|
+
Path: '',
|
|
2233
|
+
Level: tmpLevel,
|
|
2234
|
+
IsFolder: true
|
|
2229
2235
|
});
|
|
2230
2236
|
}
|
|
2231
2237
|
}
|
|
2232
2238
|
}
|
|
2233
2239
|
|
|
2240
|
+
// Make sub-folder nodes actionable: resolve each folder's first
|
|
2241
|
+
// descendant document (the items are in depth-first order, so scan
|
|
2242
|
+
// forward until we leave the folder's subtree) so clicking the folder
|
|
2243
|
+
// opens its first child.
|
|
2244
|
+
for (let g = 0; g < tmpGroups.length; g++)
|
|
2245
|
+
{
|
|
2246
|
+
let tmpItems = tmpGroups[g].Items || [];
|
|
2247
|
+
for (let a = 0; a < tmpItems.length; a++)
|
|
2248
|
+
{
|
|
2249
|
+
if (!tmpItems[a].IsFolder) { continue; }
|
|
2250
|
+
for (let b = a + 1; b < tmpItems.length; b++)
|
|
2251
|
+
{
|
|
2252
|
+
if ((tmpItems[b].Level || 0) <= (tmpItems[a].Level || 0)) { break; }
|
|
2253
|
+
if (tmpItems[b].Path) { tmpItems[a].FirstChildPath = tmpItems[b].Path; break; }
|
|
2254
|
+
}
|
|
2255
|
+
}
|
|
2256
|
+
}
|
|
2257
|
+
|
|
2234
2258
|
return tmpGroups;
|
|
2235
2259
|
}
|
|
2236
2260
|
|
|
@@ -25,14 +25,27 @@ const _ViewConfiguration =
|
|
|
25
25
|
overflow: hidden;
|
|
26
26
|
}
|
|
27
27
|
.pict-inline-doc-nav-container {
|
|
28
|
-
width: 240px;
|
|
29
|
-
min-width:
|
|
30
|
-
max-width:
|
|
28
|
+
width: var(--pict-inline-doc-nav-width, 240px);
|
|
29
|
+
min-width: 160px;
|
|
30
|
+
max-width: 640px;
|
|
31
31
|
border-right: 1px solid var(--theme-color-border-default, #E5DED4);
|
|
32
32
|
background: var(--theme-color-background-secondary, #F7F5F0);
|
|
33
33
|
overflow-y: auto;
|
|
34
34
|
flex-shrink: 0;
|
|
35
35
|
}
|
|
36
|
+
.pict-inline-doc-resizer {
|
|
37
|
+
flex: 0 0 6px;
|
|
38
|
+
width: 6px;
|
|
39
|
+
margin: 0 -3px;
|
|
40
|
+
z-index: 2;
|
|
41
|
+
cursor: col-resize;
|
|
42
|
+
background: transparent;
|
|
43
|
+
transition: background 0.12s ease;
|
|
44
|
+
}
|
|
45
|
+
.pict-inline-doc-resizer:hover,
|
|
46
|
+
.pict-inline-doc-resizer.pict-inline-doc-resizing {
|
|
47
|
+
background: var(--theme-color-brand-primary, #2E7D74);
|
|
48
|
+
}
|
|
36
49
|
.pict-inline-doc-content-container {
|
|
37
50
|
flex: 1;
|
|
38
51
|
overflow-y: auto;
|
|
@@ -42,6 +55,26 @@ const _ViewConfiguration =
|
|
|
42
55
|
.pict-inline-doc-nav-container.pict-inline-doc-nav-hidden {
|
|
43
56
|
display: none;
|
|
44
57
|
}
|
|
58
|
+
/* Whole-panel collapse: shrink the nav to a thin strip showing only the
|
|
59
|
+
expand chevron, handing the freed width back to the content. The Nav
|
|
60
|
+
view toggles .pict-inline-doc-nav-collapsed on the container. width is
|
|
61
|
+
!important so it beats any inline width left by the drag-resizer. */
|
|
62
|
+
.pict-inline-doc-nav-container.pict-inline-doc-nav-collapsed {
|
|
63
|
+
width: 40px !important;
|
|
64
|
+
min-width: 40px;
|
|
65
|
+
}
|
|
66
|
+
.pict-inline-doc-nav-container.pict-inline-doc-nav-collapsed + .pict-inline-doc-resizer {
|
|
67
|
+
display: none;
|
|
68
|
+
}
|
|
69
|
+
.pict-inline-doc-nav-collapsed .pict-inline-doc-nav-collapsed-header {
|
|
70
|
+
flex-direction: column;
|
|
71
|
+
padding: 0.6em 0;
|
|
72
|
+
justify-content: flex-start;
|
|
73
|
+
}
|
|
74
|
+
.pict-inline-doc-nav-collapsed .pict-inline-doc-nav-current-title,
|
|
75
|
+
.pict-inline-doc-nav-collapsed .pict-inline-doc-nav-search-icon {
|
|
76
|
+
display: none;
|
|
77
|
+
}
|
|
45
78
|
/* Compact mode: stack nav above content when container is narrow */
|
|
46
79
|
.pict-inline-doc.pict-inline-doc-compact {
|
|
47
80
|
flex-direction: column;
|
|
@@ -55,6 +88,9 @@ const _ViewConfiguration =
|
|
|
55
88
|
overflow-y: visible;
|
|
56
89
|
flex-shrink: 0;
|
|
57
90
|
}
|
|
91
|
+
.pict-inline-doc.pict-inline-doc-compact .pict-inline-doc-resizer {
|
|
92
|
+
display: none;
|
|
93
|
+
}
|
|
58
94
|
`,
|
|
59
95
|
|
|
60
96
|
Templates:
|
|
@@ -64,6 +100,7 @@ const _ViewConfiguration =
|
|
|
64
100
|
Template: /*html*/`
|
|
65
101
|
<div class="pict-inline-doc">
|
|
66
102
|
<div class="pict-inline-doc-nav-container" id="InlineDoc-Nav-Container"></div>
|
|
103
|
+
<div class="pict-inline-doc-resizer" id="InlineDoc-Resizer" title="Drag to resize the navigation"></div>
|
|
67
104
|
<div class="pict-inline-doc-content-container" id="InlineDoc-Content-Container"></div>
|
|
68
105
|
</div>
|
|
69
106
|
`
|
|
@@ -93,12 +130,107 @@ class InlineDocumentationLayoutView extends libPictView
|
|
|
93
130
|
// Inject all view CSS into the PICT-CSS style element
|
|
94
131
|
this.pict.CSSMap.injectCSS();
|
|
95
132
|
|
|
133
|
+
// Restore any saved nav width, then make the nav/content divider draggable
|
|
134
|
+
this._restoreNavWidth();
|
|
135
|
+
this._wireNavResizer();
|
|
136
|
+
|
|
96
137
|
// Watch for size changes and toggle compact mode
|
|
97
138
|
this._setupCompactModeObserver();
|
|
98
139
|
|
|
99
140
|
return super.onAfterRender();
|
|
100
141
|
}
|
|
101
142
|
|
|
143
|
+
/**
|
|
144
|
+
* Make the divider between the nav and the content draggable so the reader
|
|
145
|
+
* can widen or narrow the navigation. The width lives in a CSS custom
|
|
146
|
+
* property on the layout container and is persisted to localStorage.
|
|
147
|
+
*/
|
|
148
|
+
_wireNavResizer()
|
|
149
|
+
{
|
|
150
|
+
if (typeof document === 'undefined')
|
|
151
|
+
{
|
|
152
|
+
return;
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
let tmpResizer = document.getElementById('InlineDoc-Resizer');
|
|
156
|
+
let tmpContainer = document.querySelector('.pict-inline-doc');
|
|
157
|
+
let tmpNav = document.getElementById('InlineDoc-Nav-Container');
|
|
158
|
+
if (!tmpResizer || !tmpContainer || !tmpNav)
|
|
159
|
+
{
|
|
160
|
+
return;
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
let tmpMin = 160;
|
|
164
|
+
let tmpMax = 640;
|
|
165
|
+
let tmpSelf = this;
|
|
166
|
+
|
|
167
|
+
tmpResizer.addEventListener('mousedown', (pDownEvent) =>
|
|
168
|
+
{
|
|
169
|
+
pDownEvent.preventDefault();
|
|
170
|
+
let tmpStartX = pDownEvent.clientX;
|
|
171
|
+
let tmpStartWidth = tmpNav.offsetWidth;
|
|
172
|
+
|
|
173
|
+
tmpResizer.classList.add('pict-inline-doc-resizing');
|
|
174
|
+
document.body.style.userSelect = 'none';
|
|
175
|
+
document.body.style.cursor = 'col-resize';
|
|
176
|
+
|
|
177
|
+
// A drag needs document-level move/up tracking; both listeners are
|
|
178
|
+
// removed on release, so nothing leaks across renders.
|
|
179
|
+
let fMove = (pMoveEvent) =>
|
|
180
|
+
{
|
|
181
|
+
let tmpWidth = tmpStartWidth + (pMoveEvent.clientX - tmpStartX);
|
|
182
|
+
tmpWidth = Math.max(tmpMin, Math.min(tmpMax, tmpWidth));
|
|
183
|
+
tmpContainer.style.setProperty('--pict-inline-doc-nav-width', tmpWidth + 'px');
|
|
184
|
+
};
|
|
185
|
+
let fUp = () =>
|
|
186
|
+
{
|
|
187
|
+
document.removeEventListener('mousemove', fMove);
|
|
188
|
+
document.removeEventListener('mouseup', fUp);
|
|
189
|
+
tmpResizer.classList.remove('pict-inline-doc-resizing');
|
|
190
|
+
document.body.style.userSelect = '';
|
|
191
|
+
document.body.style.cursor = '';
|
|
192
|
+
tmpSelf._persistNavWidth(tmpContainer.style.getPropertyValue('--pict-inline-doc-nav-width'));
|
|
193
|
+
};
|
|
194
|
+
|
|
195
|
+
document.addEventListener('mousemove', fMove);
|
|
196
|
+
document.addEventListener('mouseup', fUp);
|
|
197
|
+
});
|
|
198
|
+
}
|
|
199
|
+
|
|
200
|
+
_persistNavWidth(pWidth)
|
|
201
|
+
{
|
|
202
|
+
try
|
|
203
|
+
{
|
|
204
|
+
if (pWidth && typeof localStorage !== 'undefined')
|
|
205
|
+
{
|
|
206
|
+
localStorage.setItem('pict-inline-doc-nav-width', pWidth);
|
|
207
|
+
}
|
|
208
|
+
}
|
|
209
|
+
catch (pError) { /* storage unavailable — the width just won't persist */ }
|
|
210
|
+
}
|
|
211
|
+
|
|
212
|
+
_restoreNavWidth()
|
|
213
|
+
{
|
|
214
|
+
try
|
|
215
|
+
{
|
|
216
|
+
if (typeof localStorage === 'undefined')
|
|
217
|
+
{
|
|
218
|
+
return;
|
|
219
|
+
}
|
|
220
|
+
let tmpSaved = localStorage.getItem('pict-inline-doc-nav-width');
|
|
221
|
+
if (!tmpSaved)
|
|
222
|
+
{
|
|
223
|
+
return;
|
|
224
|
+
}
|
|
225
|
+
let tmpContainer = document.querySelector('.pict-inline-doc');
|
|
226
|
+
if (tmpContainer)
|
|
227
|
+
{
|
|
228
|
+
tmpContainer.style.setProperty('--pict-inline-doc-nav-width', tmpSaved);
|
|
229
|
+
}
|
|
230
|
+
}
|
|
231
|
+
catch (pError) { /* ignore */ }
|
|
232
|
+
}
|
|
233
|
+
|
|
102
234
|
/**
|
|
103
235
|
* Set up a ResizeObserver to toggle compact mode when the container
|
|
104
236
|
* is too narrow for a side-by-side nav + content layout.
|
|
@@ -112,7 +112,7 @@ const _ViewConfiguration =
|
|
|
112
112
|
}
|
|
113
113
|
.pict-inline-doc-nav-item {
|
|
114
114
|
display: block;
|
|
115
|
-
padding: 0.25em 0.8em 0.25em 1.6em;
|
|
115
|
+
padding: 0.25em 0.8em 0.25em calc(1.6em + var(--doc-nav-level, 0) * 0.85em);
|
|
116
116
|
color: var(--theme-color-text-secondary, #5E5549);
|
|
117
117
|
text-decoration: none;
|
|
118
118
|
font-size: 0.85em;
|
|
@@ -123,6 +123,25 @@ const _ViewConfiguration =
|
|
|
123
123
|
.pict-inline-doc-nav-item:hover {
|
|
124
124
|
background: var(--theme-color-background-tertiary, #EDE8DF);
|
|
125
125
|
}
|
|
126
|
+
.pict-inline-doc-nav-folder {
|
|
127
|
+
font-weight: 600;
|
|
128
|
+
color: var(--theme-color-text-primary, #3D3229);
|
|
129
|
+
}
|
|
130
|
+
.pict-inline-doc-nav-folder-icon {
|
|
131
|
+
margin-right: 0.4em;
|
|
132
|
+
vertical-align: -0.12em;
|
|
133
|
+
opacity: 0.65;
|
|
134
|
+
}
|
|
135
|
+
.pict-inline-doc-nav-file-icon {
|
|
136
|
+
margin-right: 0.4em;
|
|
137
|
+
vertical-align: -0.12em;
|
|
138
|
+
opacity: 0.55;
|
|
139
|
+
}
|
|
140
|
+
.pict-inline-doc-nav-section-dot {
|
|
141
|
+
margin-right: 0.4em;
|
|
142
|
+
vertical-align: -0.12em;
|
|
143
|
+
opacity: 0.3;
|
|
144
|
+
}
|
|
126
145
|
.pict-inline-doc-nav-item.active {
|
|
127
146
|
background: var(--theme-color-background-hover, #E8E3D8);
|
|
128
147
|
color: var(--theme-color-brand-primary, #2E7D74);
|
|
@@ -131,7 +150,7 @@ const _ViewConfiguration =
|
|
|
131
150
|
}
|
|
132
151
|
.pict-inline-doc-nav-heading {
|
|
133
152
|
display: block;
|
|
134
|
-
padding: 0.15em 0.8em 0.15em 2.4em;
|
|
153
|
+
padding: 0.15em 0.8em 0.15em calc(2.4em + var(--doc-nav-level, 0) * 0.85em);
|
|
135
154
|
color: var(--theme-color-text-muted, #8A7F72);
|
|
136
155
|
font-size: 0.78em;
|
|
137
156
|
cursor: pointer;
|
|
@@ -143,7 +162,7 @@ const _ViewConfiguration =
|
|
|
143
162
|
color: var(--theme-color-text-secondary, #5E5549);
|
|
144
163
|
}
|
|
145
164
|
.pict-inline-doc-nav-heading.h3 {
|
|
146
|
-
padding-left: 3.2em;
|
|
165
|
+
padding-left: calc(3.2em + var(--doc-nav-level, 0) * 0.85em);
|
|
147
166
|
font-size: 0.72em;
|
|
148
167
|
}
|
|
149
168
|
/* Search icon in collapsed header */
|
|
@@ -339,6 +358,16 @@ class InlineDocumentationNavView extends libPictView
|
|
|
339
358
|
let tmpFilterText = tmpState.NavFilterText || '';
|
|
340
359
|
let tmpCurrentDocName = this._resolveCurrentDocName(tmpState, tmpCurrentPath);
|
|
341
360
|
|
|
361
|
+
// Reflect the collapsed state on the nav CONTAINER (the layout owns its
|
|
362
|
+
// width). Collapsing then shrinks the whole panel to a thin strip and hands
|
|
363
|
+
// the freed width back to the content, instead of hiding the outline while
|
|
364
|
+
// the container stays full-width.
|
|
365
|
+
let tmpNavContainer = document.getElementById('InlineDoc-Nav-Container');
|
|
366
|
+
if (tmpNavContainer)
|
|
367
|
+
{
|
|
368
|
+
tmpNavContainer.classList.toggle('pict-inline-doc-nav-collapsed', tmpIsCollapsed);
|
|
369
|
+
}
|
|
370
|
+
|
|
342
371
|
let tmpHTML = '';
|
|
343
372
|
|
|
344
373
|
let tmpSearchQuery = tmpState.SearchQuery || '';
|
|
@@ -624,22 +653,44 @@ class InlineDocumentationNavView extends libPictView
|
|
|
624
653
|
let tmpActive = (pCurrentPath === tmpGroup.Path) ? ' active' : '';
|
|
625
654
|
tmpHTML += '<a class="pict-inline-doc-nav-item' + tmpActive
|
|
626
655
|
+ '" data-doc-path="' + this._escapeHTML(tmpGroup.Path) + '">'
|
|
656
|
+
+ this._fileIconSVG()
|
|
627
657
|
+ this._escapeHTML(tmpGroup.Name)
|
|
628
658
|
+ '</a>';
|
|
629
659
|
|
|
630
660
|
// If this is the active item, render heading sub-items
|
|
631
661
|
if (pCurrentPath === tmpGroup.Path)
|
|
632
662
|
{
|
|
633
|
-
tmpHTML += this._renderHeadingSubItems(pHeadings, tmpFilterLower);
|
|
663
|
+
tmpHTML += this._renderHeadingSubItems(pHeadings, tmpFilterLower, 0);
|
|
634
664
|
}
|
|
635
665
|
}
|
|
636
666
|
|
|
637
667
|
for (let j = 0; j < tmpGroupItems.length; j++)
|
|
638
668
|
{
|
|
639
669
|
let tmpItem = tmpGroupItems[j];
|
|
670
|
+
let tmpIndent = ' style="--doc-nav-level:' + (tmpItem.Level || 0) + '"';
|
|
671
|
+
|
|
672
|
+
// Sub-folder node (no document of its own). Indent it by its
|
|
673
|
+
// level and, when it has descendants, make it clickable so it
|
|
674
|
+
// opens its first child document; mark it with a folder glyph.
|
|
640
675
|
if (!tmpItem.Path)
|
|
641
676
|
{
|
|
642
|
-
|
|
677
|
+
if (tmpItem.FirstChildPath)
|
|
678
|
+
{
|
|
679
|
+
// Folders are navigational shortcuts to their first child; the
|
|
680
|
+
// child item carries the active highlight, so the folder doesn't.
|
|
681
|
+
tmpHTML += '<a class="pict-inline-doc-nav-item pict-inline-doc-nav-folder'
|
|
682
|
+
+ '" data-doc-path="' + this._escapeHTML(tmpItem.FirstChildPath) + '"' + tmpIndent + '>'
|
|
683
|
+
+ this._folderIconSVG()
|
|
684
|
+
+ this._escapeHTML(tmpItem.Name)
|
|
685
|
+
+ '</a>';
|
|
686
|
+
}
|
|
687
|
+
else
|
|
688
|
+
{
|
|
689
|
+
tmpHTML += '<span class="pict-inline-doc-nav-item pict-inline-doc-nav-folder"' + tmpIndent + '>'
|
|
690
|
+
+ this._folderIconSVG()
|
|
691
|
+
+ this._escapeHTML(tmpItem.Name)
|
|
692
|
+
+ '</span>';
|
|
693
|
+
}
|
|
643
694
|
continue;
|
|
644
695
|
}
|
|
645
696
|
|
|
@@ -647,7 +698,8 @@ class InlineDocumentationNavView extends libPictView
|
|
|
647
698
|
{
|
|
648
699
|
// External link — opens in a new tab
|
|
649
700
|
tmpHTML += '<a class="pict-inline-doc-nav-item pict-inline-doc-nav-item-external'
|
|
650
|
-
+ '" data-external-url="' + this._escapeHTML(tmpItem.ExternalURL) + '">'
|
|
701
|
+
+ '" data-external-url="' + this._escapeHTML(tmpItem.ExternalURL) + '"' + tmpIndent + '>'
|
|
702
|
+
+ this._fileIconSVG()
|
|
651
703
|
+ this._escapeHTML(tmpItem.Name)
|
|
652
704
|
+ '<svg class="pict-inline-doc-nav-external-icon" width="0.75em" height="0.75em" viewBox="0 0 16 16" fill="none" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"><path d="M12 9v4a1 1 0 01-1 1H3a1 1 0 01-1-1V5a1 1 0 011-1h4"/><polyline points="8,2 14,2 14,8"/><line x1="14" y1="2" x2="7" y2="9"/></svg>'
|
|
653
705
|
+ '</a>';
|
|
@@ -656,14 +708,15 @@ class InlineDocumentationNavView extends libPictView
|
|
|
656
708
|
{
|
|
657
709
|
let tmpActive = (pCurrentPath === tmpItem.Path) ? ' active' : '';
|
|
658
710
|
tmpHTML += '<a class="pict-inline-doc-nav-item' + tmpActive
|
|
659
|
-
+ '" data-doc-path="' + this._escapeHTML(tmpItem.Path) + '">'
|
|
711
|
+
+ '" data-doc-path="' + this._escapeHTML(tmpItem.Path) + '"' + tmpIndent + '>'
|
|
712
|
+
+ this._fileIconSVG()
|
|
660
713
|
+ this._escapeHTML(tmpItem.Name)
|
|
661
714
|
+ '</a>';
|
|
662
715
|
|
|
663
716
|
// If this is the active item, render heading sub-items
|
|
664
717
|
if (pCurrentPath === tmpItem.Path)
|
|
665
718
|
{
|
|
666
|
-
tmpHTML += this._renderHeadingSubItems(pHeadings, tmpFilterLower);
|
|
719
|
+
tmpHTML += this._renderHeadingSubItems(pHeadings, tmpFilterLower, tmpItem.Level || 0);
|
|
667
720
|
}
|
|
668
721
|
}
|
|
669
722
|
}
|
|
@@ -675,6 +728,40 @@ class InlineDocumentationNavView extends libPictView
|
|
|
675
728
|
return tmpHTML;
|
|
676
729
|
}
|
|
677
730
|
|
|
731
|
+
/**
|
|
732
|
+
* A small folder glyph for sub-folder nav nodes. Uses currentColor so it
|
|
733
|
+
* follows the theme like the other inline nav icons.
|
|
734
|
+
*
|
|
735
|
+
* @returns {string} inline SVG HTML
|
|
736
|
+
*/
|
|
737
|
+
_folderIconSVG()
|
|
738
|
+
{
|
|
739
|
+
return '<svg class="pict-inline-doc-nav-folder-icon" width="0.85em" height="0.85em" viewBox="0 0 16 16" fill="none" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"><path d="M1.5 5a1 1 0 0 1 1-1h3.2l1.3 1.4h5.5a1 1 0 0 1 1 1V12a1 1 0 0 1-1 1h-11a1 1 0 0 1-1-1z"/></svg>';
|
|
740
|
+
}
|
|
741
|
+
|
|
742
|
+
/**
|
|
743
|
+
* A small document glyph (a page with a folded corner) for markdown file
|
|
744
|
+
* nodes. Same footprint as the folder glyph so files and folders line up at
|
|
745
|
+
* the same depth.
|
|
746
|
+
*
|
|
747
|
+
* @returns {string} inline SVG HTML
|
|
748
|
+
*/
|
|
749
|
+
_fileIconSVG()
|
|
750
|
+
{
|
|
751
|
+
return '<svg class="pict-inline-doc-nav-file-icon" width="0.85em" height="0.85em" viewBox="0 0 16 16" fill="none" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"><path d="M4 2.5H9L12 5.5V13.5H4Z"/><polyline points="9 2.5 9 5.5 12 5.5"/></svg>';
|
|
752
|
+
}
|
|
753
|
+
|
|
754
|
+
/**
|
|
755
|
+
* A small filled dot marking an in-document section (a heading sub-item shown
|
|
756
|
+
* beneath the active document). currentColor + low opacity keeps it quiet.
|
|
757
|
+
*
|
|
758
|
+
* @returns {string} inline SVG HTML
|
|
759
|
+
*/
|
|
760
|
+
_sectionDotSVG()
|
|
761
|
+
{
|
|
762
|
+
return '<svg class="pict-inline-doc-nav-section-dot" width="0.85em" height="0.85em" viewBox="0 0 16 16" aria-hidden="true"><circle cx="8" cy="8" r="2.3" fill="currentColor"/></svg>';
|
|
763
|
+
}
|
|
764
|
+
|
|
678
765
|
/**
|
|
679
766
|
* Render heading sub-items (h2 and h3) beneath the active nav item.
|
|
680
767
|
*
|
|
@@ -682,13 +769,16 @@ class InlineDocumentationNavView extends libPictView
|
|
|
682
769
|
* @param {string} pFilterText - Lowercase filter text
|
|
683
770
|
* @returns {string} HTML string for heading sub-items
|
|
684
771
|
*/
|
|
685
|
-
_renderHeadingSubItems(pHeadings, pFilterText)
|
|
772
|
+
_renderHeadingSubItems(pHeadings, pFilterText, pBaseLevel)
|
|
686
773
|
{
|
|
687
774
|
if (!pHeadings || pHeadings.length < 1)
|
|
688
775
|
{
|
|
689
776
|
return '';
|
|
690
777
|
}
|
|
691
778
|
|
|
779
|
+
// Indent the headings relative to their (possibly nested) parent
|
|
780
|
+
// document item, so they line up one notch under it at any tree depth.
|
|
781
|
+
let tmpLevelStyle = ' style="--doc-nav-level:' + (pBaseLevel || 0) + '"';
|
|
692
782
|
let tmpHTML = '';
|
|
693
783
|
|
|
694
784
|
for (let i = 0; i < pHeadings.length; i++)
|
|
@@ -704,7 +794,8 @@ class InlineDocumentationNavView extends libPictView
|
|
|
704
794
|
|
|
705
795
|
let tmpLevelClass = (tmpHeading.Level === 3) ? ' h3' : '';
|
|
706
796
|
tmpHTML += '<a class="pict-inline-doc-nav-heading' + tmpLevelClass
|
|
707
|
-
+ '" data-heading-slug="' + this._escapeHTML(tmpHeading.Slug) + '">'
|
|
797
|
+
+ '" data-heading-slug="' + this._escapeHTML(tmpHeading.Slug) + '"' + tmpLevelStyle + '>'
|
|
798
|
+
+ this._sectionDotSVG()
|
|
708
799
|
+ this._escapeHTML(tmpText)
|
|
709
800
|
+ '</a>';
|
|
710
801
|
}
|