@jxsuite/studio 6.1.2 → 8.0.0
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/README.md +5 -5
- package/dist/chunks/2020-5wtzce5g.js +4 -0
- package/dist/chunks/adapter-5tphg7xe.js +4 -0
- package/dist/chunks/add-new-flow-psym14sn.js +4 -0
- package/dist/chunks/cf-account-picker-haqazq5r.js +4 -0
- package/dist/chunks/cf-settings-h2wrh6hq.js +4 -0
- package/dist/chunks/{color-area-0fj8a4ga.js → color-area-6rbra5dy.js} +2 -2
- package/dist/chunks/{color-field-xch8kx2g.js → color-field-gy56c94g.js} +3 -3
- package/dist/chunks/color-m7r1vk54.js +4 -0
- package/dist/chunks/{color-slider-jxd8v350.js → color-slider-sqqdyf6c.js} +2 -2
- package/dist/chunks/{combobox-p0efwjke.js → combobox-72h32ejk.js} +3 -3
- package/dist/chunks/components-r22xca09.js +4 -0
- package/dist/chunks/content-source-mmppmcyg.js +4 -0
- package/dist/chunks/convert-to-repeater-he70fc2b.js +4 -0
- package/dist/chunks/editor-ccd9jwsa.js +4 -0
- package/dist/chunks/entry-commands-6qxz9e8p.js +4 -0
- package/dist/chunks/extension-sections-0egb88dm.js +4 -0
- package/dist/chunks/file-ops-qnab36ek.js +4 -0
- package/dist/chunks/files-rcn56qvm.js +4 -0
- package/dist/chunks/format-host-yxz0kjjs.js +4 -0
- package/dist/chunks/fs-events-d1qxq4z4.js +4 -0
- package/dist/chunks/grid-open-4z1g062t.js +4 -0
- package/dist/chunks/{grid-view-d2wq9ezg.js → grid-view-qg1b5eqx.js} +25 -25
- package/dist/chunks/{icons-pnfz478q.js → icons-63bjtbs7.js} +2 -2
- package/dist/chunks/{iframe-entry-jdcktez8.js → iframe-entry-2zggzajv.js} +4 -4
- package/dist/chunks/{iframe-entry-zap785cw.js → iframe-entry-76j8vwwx.js} +4 -4
- package/dist/chunks/iframe-entry-99nr5zfb.js +5 -0
- package/dist/chunks/{iframe-entry-x0ygf2yr.js → iframe-entry-pkgmcgp0.js} +4 -4
- package/dist/chunks/iframe-host-ssv7kyj0.js +4 -0
- package/dist/chunks/{index-zpjmzqfk.js → index-32eqzv1k.js} +3 -3
- package/dist/chunks/index-f0jn7nnp.js +4 -0
- package/dist/chunks/{javascript-m54mnwp6.js → javascript-pjp734q4.js} +3 -3
- package/dist/chunks/jsonMode-njkvsa02.js +13 -0
- package/dist/chunks/jx-validate-ttasrbh7.js +4 -0
- package/dist/chunks/layers-bgyr11tr.js +4 -0
- package/dist/chunks/layers-panel-7ez66zeq.js +4 -0
- package/dist/chunks/{listbox-e74qjyq6.js → listbox-c421cf8c.js} +2 -2
- package/dist/chunks/lit-html-v9gh687x.js +4 -0
- package/dist/chunks/media-library-sq468wts.js +4 -0
- package/dist/chunks/media-picker-shfe59pt.js +4 -0
- package/dist/chunks/{menu-n6yzswmy.js → menu-bdpzbfvs.js} +2 -2
- package/dist/chunks/{monaco-binding-7gx83x3r.js → monaco-binding-vq1hgnn0.js} +3 -3
- package/dist/chunks/monaco-buffer-3afgwvbp.js +4 -0
- package/dist/chunks/monaco-setup-xrd2cbkp.js +4 -0
- package/dist/chunks/notify-kzrjr3fv.js +4 -0
- package/dist/chunks/parse-v77xtwv7.js +4 -0
- package/dist/chunks/platform-7v4rtd7m.js +4 -0
- package/dist/chunks/popover-b89sfej7.js +4 -0
- package/dist/chunks/publish-panel-2z9gw8ee.js +4 -0
- package/dist/chunks/publish-quick-qx2455cj.js +4 -0
- package/dist/chunks/publish-workspace-wrc1dgwx.js +4 -0
- package/dist/chunks/quick-search-n0t0eqxb.js +4 -0
- package/dist/chunks/references-9547rg5s.js +4 -0
- package/dist/chunks/right-panel-wsgnr9pn.js +4 -0
- package/dist/chunks/source-control-kwktr9y6.js +4 -0
- package/dist/chunks/{split-n2gfpm5m.js → split-c9zfdgxf.js} +2 -2
- package/dist/chunks/studio-03ct6yfv.js +9 -0
- package/dist/chunks/studio-07rcfje3.js +5 -0
- package/dist/chunks/studio-3e54qh39.js +7 -0
- package/dist/chunks/studio-3exxhz5g.js +5 -0
- package/dist/chunks/studio-3q40e3rj.js +5 -0
- package/dist/chunks/studio-3qeh9t0h.js +6 -0
- package/dist/chunks/studio-3qqjeep5.js +6 -0
- package/dist/chunks/studio-43sd2mam.js +4 -0
- package/dist/chunks/studio-4hp8pkyt.js +5 -0
- package/dist/chunks/studio-58xg6j2q.js +9 -0
- package/dist/chunks/studio-5g0rprdt.js +7 -0
- package/dist/chunks/{studio-2j1cb95x.js → studio-6m380wp7.js} +4 -4
- package/dist/chunks/studio-80jyh1xh.js +4 -0
- package/dist/chunks/studio-83mk4bgg.js +9 -0
- package/dist/chunks/{studio-v0jzqdjm.js → studio-881z1xrx.js} +4 -4
- package/dist/chunks/studio-8m0y2qe7.js +5 -0
- package/dist/chunks/{studio-d81xfh1g.js → studio-8tr6cfrc.js} +4 -4
- package/dist/chunks/studio-8vcvfs7r.js +6 -0
- package/dist/chunks/studio-9tmebf0s.js +5 -0
- package/dist/chunks/studio-a2bvaptz.js +5 -0
- package/dist/chunks/studio-b7y5mr30.js +5 -0
- package/dist/chunks/studio-bavb31r0.js +5 -0
- package/dist/chunks/{studio-dgz8d0c1.js → studio-bbe4c90a.js} +4 -4
- package/dist/chunks/studio-c05wdnt3.js +5 -0
- package/dist/chunks/studio-ccv2svc6.js +5 -0
- package/dist/chunks/studio-d5grtb9e.js +16 -0
- package/dist/chunks/studio-df0baea9.js +5 -0
- package/dist/chunks/studio-dgk4dqtx.js +7 -0
- package/dist/chunks/studio-e1g64q43.js +5 -0
- package/dist/chunks/studio-ed1hp6zf.js +6 -0
- package/dist/chunks/studio-ed3xx40h.js +7 -0
- package/dist/chunks/studio-f14e1zdj.js +5 -0
- package/dist/chunks/studio-fbhxxc5f.js +5 -0
- package/dist/chunks/studio-fyh0jc96.js +5 -0
- package/dist/chunks/studio-gcxk20n7.js +5 -0
- package/dist/chunks/studio-jaaz8ce9.js +5 -0
- package/dist/chunks/{studio-90pq9km1.js → studio-jcnsdaep.js} +4 -4
- package/dist/chunks/studio-jsgf2q5k.js +7 -0
- package/dist/chunks/{studio-0q988f9w.js → studio-k3xxbagr.js} +3 -3
- package/dist/chunks/{studio-5ve6bbep.js → studio-k7evxqh4.js} +4 -4
- package/dist/chunks/studio-kt3pjkwd.js +5 -0
- package/dist/chunks/studio-m8g16bgz.js +5 -0
- package/dist/chunks/studio-mn0476ag.js +5 -0
- package/dist/chunks/studio-mx1smyq0.js +5 -0
- package/dist/chunks/studio-n0c5h6mf.js +5 -0
- package/dist/chunks/{studio-485046te.js → studio-nh6d342n.js} +7 -7
- package/dist/chunks/studio-nqxqf8p2.js +4 -0
- package/dist/chunks/studio-p4nrkvqr.js +5 -0
- package/dist/chunks/{studio-1fxkaaea.js → studio-pbxa5fpc.js} +4 -4
- package/dist/chunks/studio-pgmvdv7z.js +7 -0
- package/dist/chunks/studio-ph84avkf.js +5 -0
- package/dist/chunks/{studio-tq0rtfwj.js → studio-q0mvbaq6.js} +4 -4
- package/dist/chunks/studio-q0tccd43.js +5 -0
- package/dist/chunks/studio-q7rtx6zq.js +14 -0
- package/dist/chunks/{studio-a3g98wjr.js → studio-qgh13jtz.js} +4 -4
- package/dist/chunks/studio-qmn1xc24.js +5 -0
- package/dist/chunks/studio-qwdqwkj0.js +5 -0
- package/dist/chunks/studio-r5qy30vx.js +5 -0
- package/dist/chunks/studio-rj9eamf8.js +5 -0
- package/dist/chunks/studio-rptgsk96.js +5 -0
- package/dist/chunks/studio-rthyg42z.js +928 -0
- package/dist/chunks/studio-s19tp1xr.js +5 -0
- package/dist/chunks/studio-s32578pn.js +5 -0
- package/dist/chunks/studio-svb7yyve.js +5 -0
- package/dist/chunks/studio-syreb644.js +5 -0
- package/dist/chunks/studio-tf9jryb1.js +10 -0
- package/dist/chunks/studio-tfkznv39.js +5 -0
- package/dist/chunks/studio-tft6r105.js +5 -0
- package/dist/chunks/studio-txf2kysx.js +5 -0
- package/dist/chunks/studio-v8867ddv.js +12 -0
- package/dist/chunks/studio-vxq7fcvv.js +5 -0
- package/dist/chunks/studio-w4rz9hdk.js +5 -0
- package/dist/chunks/studio-wbcjbhy1.js +9 -0
- package/dist/chunks/studio-wc649wss.js +5 -0
- package/dist/chunks/studio-wys23mxz.js +5 -0
- package/dist/chunks/studio-x1x167jh.js +5 -0
- package/dist/chunks/studio-x9hsze61.js +5 -0
- package/dist/chunks/studio-y0n7yxea.js +9 -0
- package/dist/chunks/studio-y3ahhdpx.js +5 -0
- package/dist/chunks/studio-z97c48fk.js +5 -0
- package/dist/chunks/studio-zat62m0c.js +5 -0
- package/dist/chunks/studio-zcd2e7yz.js +5 -0
- package/dist/chunks/studio-zz9qe3rw.js +64 -0
- package/dist/chunks/toast-1gv0h53h.js +4 -0
- package/dist/chunks/{toast-host-ke5z4ng7.js → toast-host-1yg5ar8d.js} +3 -3
- package/dist/chunks/{tooltip-5v8ngwj2.js → tooltip-yypz28gq.js} +3 -3
- package/dist/chunks/{tree-mdq3v5cw.js → tree-9xa4hm7n.js} +2 -2
- package/dist/chunks/tsMode-epyfz1hv.js +14 -0
- package/dist/chunks/workspace-dz7nxfhv.js +4 -0
- package/dist/chunks/workspace-home-xsd7hkjw.js +4 -0
- package/dist/chunks/{ws-client-nze0k6mv.js → ws-client-bv552sfx.js} +3 -3
- package/dist/iframe-entry.js +20 -16
- package/dist/manifest.json +77 -63
- package/dist/studio.js +103 -104
- package/dist/workers/ts.worker.js +3 -3
- package/package.json +12 -11
- package/src/browse/component-examples.ts +272 -0
- package/src/browse/library-commands.ts +64 -104
- package/src/browse/library-layouts.ts +263 -49
- package/src/browse/library-model.ts +181 -133
- package/src/browse/library-pane.ts +738 -446
- package/src/browse/library-preview.ts +149 -19
- package/src/browse/library-source.ts +308 -41
- package/src/browse/preview-root.ts +78 -0
- package/src/browse/preview-style.ts +155 -0
- package/src/canvas/asset-refs.ts +16 -1
- package/src/canvas/canvas-live-render.ts +222 -30
- package/src/canvas/canvas-origin.ts +37 -12
- package/src/canvas/canvas-page-context.ts +112 -0
- package/src/canvas/canvas-render.ts +113 -107
- package/src/canvas/canvas-utils.ts +57 -12
- package/src/canvas/iframe-drop.ts +107 -0
- package/src/canvas/iframe-entry.ts +24 -12
- package/src/canvas/iframe-host.ts +134 -62
- package/src/canvas/iframe-keys.ts +11 -0
- package/src/canvas/iframe-patch.ts +8 -7
- package/src/canvas/iframe-protocol.ts +24 -5
- package/src/canvas/iframe-render.ts +48 -1
- package/src/canvas/iframe-subtree.ts +5 -2
- package/src/canvas/npm-modules.ts +22 -0
- package/src/canvas/preview-navigate.ts +16 -0
- package/src/canvas/repeater-sources.ts +200 -0
- package/src/canvas/stage-scrollbar.ts +5 -1
- package/src/canvas/surface-registry.ts +6 -0
- package/src/commands/app-commands.ts +16 -6
- package/src/commands/budget.ts +10 -8
- package/src/commands/context.ts +35 -10
- package/src/commands/defaults.ts +69 -45
- package/src/commands/keymap.ts +9 -0
- package/src/commands/levels.ts +11 -5
- package/src/commands/live-context.ts +2 -0
- package/src/commands/registry.ts +10 -1
- package/src/content/collection-match.ts +6 -5
- package/src/content/collection-pages.ts +412 -0
- package/src/content/content-collections.ts +270 -0
- package/src/content/entry-commands.ts +51 -60
- package/src/content/entry-editor.ts +111 -18
- package/src/content/entry-fields.ts +13 -1
- package/src/content/entry-inspector.ts +225 -0
- package/src/content/entry-model.ts +17 -3
- package/src/content/entry-open.ts +80 -0
- package/src/content/entry-summaries.ts +440 -0
- package/src/content/file-record-ids.ts +80 -0
- package/src/content/file-records.ts +125 -0
- package/src/content/page-summaries.ts +129 -0
- package/src/content/record-entry.ts +201 -0
- package/src/content/writing-banner.ts +177 -0
- package/src/create/add-new-commands.ts +185 -0
- package/src/create/add-new-flow.ts +1116 -0
- package/src/create/add-new.ts +1014 -0
- package/src/create/element-name.ts +121 -0
- package/src/editor/convert-to-component.ts +67 -43
- package/src/editor/file-drop-action.ts +9 -1
- package/src/editor/inline-edit-apply.ts +44 -0
- package/src/editor/inline-edit.ts +10 -0
- package/src/editor/insert-component.ts +91 -0
- package/src/editor/insert-zone-action.ts +13 -4
- package/src/editor/shortcuts.ts +44 -22
- package/src/editor/slash-menu.ts +51 -8
- package/src/files/components.ts +74 -10
- package/src/files/file-ops.ts +15 -5
- package/src/files/files.ts +164 -150
- package/src/files/fs-events.ts +18 -7
- package/src/files/media-meta.ts +95 -1
- package/src/files/media-types.ts +55 -0
- package/src/files/media-upload.ts +209 -52
- package/src/files/new-file-name.ts +156 -0
- package/src/files/serialize-document.ts +13 -3
- package/src/format/format-host.ts +15 -0
- package/src/github/github-auth.ts +2 -2
- package/src/github/github-publish.ts +4 -3
- package/src/grid/grid-controller.ts +5 -1
- package/src/grid/grid-open.ts +0 -27
- package/src/grid/grid-panel.ts +54 -2
- package/src/grid/grid-reveal.ts +34 -0
- package/src/grid/grid-source.ts +3 -25
- package/src/grid/grid-view.ts +31 -6
- package/src/grid/sources/content-source.ts +75 -7
- package/src/grid/tabulator-tables.d.ts +6 -0
- package/src/hosting/document.ts +2 -2
- package/src/i18n/i18n-commands.ts +2 -1
- package/src/media/media-commands.ts +181 -0
- package/src/media/media-library-model.ts +232 -0
- package/src/media/media-library.ts +1283 -0
- package/src/media/media-pane.ts +47 -19
- package/src/packages/pull-package-sync.ts +1 -1
- package/src/panels/activity-panel.ts +21 -5
- package/src/panels/ai-chat/chat-markdown.ts +8 -8
- package/src/panels/block-action-bar.ts +11 -11
- package/src/panels/canvas-dnd-bridge.ts +5 -2
- package/src/panels/chat-panel.ts +6 -6
- package/src/panels/collections-panel.ts +306 -0
- package/src/panels/component-preview.ts +35 -13
- package/src/panels/data-explorer.ts +1 -1
- package/src/panels/data-grid.ts +4 -0
- package/src/panels/dnd.ts +17 -30
- package/src/panels/elements-panel.ts +9 -2
- package/src/panels/empty-state.ts +2 -2
- package/src/panels/formula-workspace.ts +2 -3
- package/src/panels/frontmatter-fields.ts +9 -9
- package/src/panels/git-diff-open.ts +9 -5
- package/src/panels/head-panel.ts +369 -103
- package/src/panels/i18n-panel.ts +11 -10
- package/src/panels/imports-panel.ts +2 -0
- package/src/panels/jump-bar.ts +27 -2
- package/src/panels/layers-panel.ts +36 -30
- package/src/panels/left-panel.ts +22 -8
- package/src/panels/navigator-panels.ts +23 -11
- package/src/panels/pane-context.ts +111 -29
- package/src/panels/pane-grid.ts +6 -6
- package/src/panels/panel-registry.ts +14 -9
- package/src/panels/properties-panel.ts +7 -3
- package/src/panels/right-panel.ts +199 -43
- package/src/panels/seo-modal.ts +41 -108
- package/src/panels/settings-menu.ts +52 -50
- package/src/panels/settings-pane.ts +268 -162
- package/src/panels/signals-panel.ts +3 -4
- package/src/panels/site-model.ts +367 -0
- package/src/panels/site-panel.ts +638 -0
- package/src/panels/style-panel.ts +37 -3
- package/src/panels/stylebook-doc.ts +142 -10
- package/src/panels/stylebook-layers-panel.ts +39 -80
- package/src/panels/stylebook-panel.ts +47 -10
- package/src/panels/styles-panel.ts +327 -0
- package/src/panels/tab-strip.ts +109 -25
- package/src/platform.ts +1 -1
- package/src/platforms/cloud.ts +28 -1
- package/src/platforms/default-platform.ts +4 -4
- package/src/platforms/devserver.ts +51 -25
- package/src/publish/deploy-checklist.ts +12 -7
- package/src/publish/pages-service.ts +38 -14
- package/src/publish/publish-changes.ts +491 -0
- package/src/publish/publish-commands.ts +83 -18
- package/src/publish/publish-ids.ts +49 -0
- package/src/publish/publish-quick.ts +148 -0
- package/src/publish/publish-workspace.ts +926 -0
- package/src/publish/source-control.ts +907 -0
- package/src/services/automation.ts +16 -20
- package/src/services/cf-settings.ts +4 -4
- package/src/services/connection.ts +2 -2
- package/src/services/directory-picker.ts +2 -2
- package/src/services/references.ts +0 -0
- package/src/services/render-critic.ts +21 -2
- package/src/services/settings/definitions.ts +25 -14
- package/src/settings/contributed-section.ts +49 -10
- package/src/settings/css-vars-editor.ts +93 -27
- package/src/settings/developer-panels.ts +43 -0
- package/src/settings/extension-sections.ts +20 -2
- package/src/settings/general-settings.ts +91 -21
- package/src/settings/preferences-dialog.ts +8 -1
- package/src/settings/project-sections.ts +27 -10
- package/src/settings/schema-field-ui.ts +3 -1
- package/src/settings/section-registry.ts +116 -11
- package/src/settings/settings-dialog.ts +192 -0
- package/src/settings/settings-document.ts +182 -162
- package/src/shell.ts +467 -431
- package/src/site-context.ts +64 -10
- package/src/state.ts +28 -9
- package/src/studio.ts +194 -41
- package/src/style/project-styles.ts +34 -0
- package/src/style/stylebook-specimens.ts +89 -0
- package/src/style/stylebook-target.ts +26 -0
- package/src/style/tag-inheritance.ts +105 -0
- package/src/style/variables-focus.ts +61 -0
- package/src/style/variables-view.ts +235 -0
- package/src/surfaces/add-new.json +1482 -0
- package/src/surfaces/add-new.ts +325 -0
- package/src/surfaces/ai-chat.ts +2 -2
- package/src/surfaces/boot-failure.json +4 -3
- package/src/surfaces/bottom-dock.json +1 -1
- package/src/surfaces/canvas-stage.json +30 -19
- package/src/surfaces/canvas-stage.ts +5 -5
- package/src/surfaces/collections-panel.json +615 -0
- package/src/surfaces/collections-panel.ts +168 -0
- package/src/surfaces/commandbar.json +241 -96
- package/src/surfaces/commandbar.ts +134 -99
- package/src/surfaces/empty-state.json +1 -1
- package/src/surfaces/entry-editor.json +136 -0
- package/src/surfaces/entry-editor.ts +21 -0
- package/src/surfaces/entry-inspector.json +371 -0
- package/src/surfaces/entry-inspector.ts +143 -0
- package/src/surfaces/inspector-dock.json +162 -14
- package/src/surfaces/inspector-dock.ts +46 -19
- package/src/surfaces/library-pane.json +670 -437
- package/src/surfaces/library-pane.ts +94 -59
- package/src/surfaces/media-browser.json +62 -6
- package/src/surfaces/media-browser.ts +15 -1
- package/src/surfaces/media-field.json +1 -1
- package/src/surfaces/media-library.json +1586 -0
- package/src/surfaces/media-library.ts +282 -0
- package/src/surfaces/media-pick-dialog.json +71 -0
- package/src/surfaces/media-pick-dialog.ts +132 -0
- package/src/surfaces/menu.ts +18 -0
- package/src/surfaces/pane-context.json +144 -77
- package/src/surfaces/pane-context.ts +24 -0
- package/src/surfaces/panel-deploy-checklist.json +12 -6
- package/src/surfaces/panel-deploy-checklist.ts +3 -1
- package/src/surfaces/panel-page.json +72 -2
- package/src/surfaces/panel-page.ts +38 -7
- package/src/surfaces/panel-signals.json +1 -1
- package/src/surfaces/panel-signals.ts +5 -5
- package/src/surfaces/panel-stylebook-layers.json +71 -204
- package/src/surfaces/panel-stylebook-layers.ts +0 -21
- package/src/surfaces/preferences.json +120 -48
- package/src/surfaces/preferences.ts +8 -0
- package/src/surfaces/publish-quick.json +428 -0
- package/src/surfaces/publish-quick.ts +165 -0
- package/src/surfaces/publish-workspace.json +2892 -0
- package/src/surfaces/publish-workspace.ts +391 -0
- package/src/surfaces/rail.json +1 -159
- package/src/surfaces/rail.ts +18 -75
- package/src/surfaces/schema-form.json +10 -2
- package/src/surfaces/schema-form.ts +2 -0
- package/src/surfaces/seo.json +1 -1
- package/src/surfaces/settings-contributed.json +5 -5
- package/src/surfaces/settings-contributed.ts +18 -2
- package/src/surfaces/settings-css-vars.json +44 -36
- package/src/surfaces/settings-css-vars.ts +77 -4
- package/src/surfaces/settings-deploy.json +2 -15
- package/src/surfaces/settings-deploy.ts +1 -1
- package/src/surfaces/settings-dialog.json +51 -0
- package/src/surfaces/settings-dialog.ts +169 -0
- package/src/surfaces/settings-overview.json +3 -3
- package/src/surfaces/settings-overview.ts +9 -2
- package/src/surfaces/settings-pane.json +269 -46
- package/src/surfaces/settings-pane.ts +85 -24
- package/src/surfaces/shell.json +2 -1
- package/src/surfaces/site-panel.json +1029 -0
- package/src/surfaces/site-panel.ts +233 -0
- package/src/surfaces/slash-menu.json +63 -21
- package/src/surfaces/slash-menu.ts +23 -0
- package/src/surfaces/statusbar.ts +39 -15
- package/src/surfaces/styles-panel.json +735 -0
- package/src/surfaces/styles-panel.ts +195 -0
- package/src/surfaces/styles-variables.json +149 -0
- package/src/surfaces/styles-variables.ts +145 -0
- package/src/surfaces/tab-strip.json +4 -4
- package/src/surfaces/welcome.ts +1 -1
- package/src/surfaces/writing-banner.json +94 -0
- package/src/surfaces/writing-banner.ts +80 -0
- package/src/tabs/bare-repeaters.ts +101 -0
- package/src/tabs/tab.ts +47 -7
- package/src/types.ts +21 -26
- package/src/ui/form-controls.ts +47 -8
- package/src/ui/layers.ts +13 -0
- package/src/ui/media-picker.ts +284 -40
- package/src/ui/regions.ts +7 -6
- package/src/ui/schema-form.ts +259 -27
- package/src/ui/virtual-window.ts +26 -1
- package/src/utils/base64.ts +3 -3
- package/src/utils/edit-display.ts +322 -67
- package/src/utils/local-day.ts +18 -0
- package/src/workspace/pane-derive.ts +4 -4
- package/src/workspace/session.ts +28 -7
- package/src/workspace/tab-workspace.ts +137 -0
- package/src/workspace/workspace-back.ts +189 -0
- package/src/workspace/workspace-home.ts +133 -0
- package/src/workspace/workspace-ids.ts +129 -0
- package/src/workspace/workspace-switch.ts +372 -0
- package/src/workspace/workspace.ts +125 -11
- package/styles/shell-frame.css +30 -7
- package/styles/shell-frame.json +15 -3
- package/dist/chunks/2020-f2gkpy8d.js +0 -4
- package/dist/chunks/adapter-4912g339.js +0 -4
- package/dist/chunks/cf-account-picker-wccaenh6.js +0 -4
- package/dist/chunks/cf-settings-br6105tr.js +0 -4
- package/dist/chunks/color-28ksk2qm.js +0 -4
- package/dist/chunks/components-db68vsn7.js +0 -4
- package/dist/chunks/content-source-1449qesq.js +0 -4
- package/dist/chunks/convert-to-repeater-5h457egj.js +0 -4
- package/dist/chunks/editor-x9jn86a7.js +0 -4
- package/dist/chunks/entry-commands-may24cpt.js +0 -4
- package/dist/chunks/extension-sections-pvr14vxr.js +0 -4
- package/dist/chunks/file-ops-x9v54pcj.js +0 -4
- package/dist/chunks/files-j3knqf0s.js +0 -4
- package/dist/chunks/format-host-tyre2trb.js +0 -4
- package/dist/chunks/fs-events-64ma9htc.js +0 -4
- package/dist/chunks/git-panel-84ps5dex.js +0 -4
- package/dist/chunks/iframe-entry-fvbk89gm.js +0 -5
- package/dist/chunks/iframe-host-ck6vejt5.js +0 -4
- package/dist/chunks/index-b8xw3vy9.js +0 -4
- package/dist/chunks/jsonMode-w15cmrcm.js +0 -13
- package/dist/chunks/jx-validate-at3zn8wa.js +0 -4
- package/dist/chunks/layers-h4xp1pss.js +0 -4
- package/dist/chunks/layers-panel-m5hw1d7g.js +0 -4
- package/dist/chunks/lit-html-8t8t3dnr.js +0 -4
- package/dist/chunks/media-picker-2cweexc5.js +0 -4
- package/dist/chunks/menu-ynw13y0s.js +0 -4
- package/dist/chunks/monaco-buffer-qzxn567r.js +0 -4
- package/dist/chunks/monaco-setup-gxf6656g.js +0 -4
- package/dist/chunks/notify-cj5zbrs2.js +0 -4
- package/dist/chunks/parse-b7ddhr8m.js +0 -4
- package/dist/chunks/platform-3dfws9js.js +0 -4
- package/dist/chunks/popover-jt2gxmzs.js +0 -4
- package/dist/chunks/publish-panel-1gvxbj21.js +0 -4
- package/dist/chunks/quick-search-0dajrwqg.js +0 -4
- package/dist/chunks/references-49qgt404.js +0 -4
- package/dist/chunks/right-panel-jm1bwe53.js +0 -4
- package/dist/chunks/section-registry-6kwc4fky.js +0 -4
- package/dist/chunks/studio-0rt52vpq.js +0 -5
- package/dist/chunks/studio-18vgbhs5.js +0 -5
- package/dist/chunks/studio-24mccdrj.js +0 -5
- package/dist/chunks/studio-2eh507zk.js +0 -9
- package/dist/chunks/studio-2hcbccfv.js +0 -5
- package/dist/chunks/studio-2jbs3rxv.js +0 -5
- package/dist/chunks/studio-4h8k4dw9.js +0 -5
- package/dist/chunks/studio-5f6n18kx.js +0 -5
- package/dist/chunks/studio-5gthpky6.js +0 -5
- package/dist/chunks/studio-6ep3js6b.js +0 -9
- package/dist/chunks/studio-6wkmf3wz.js +0 -9
- package/dist/chunks/studio-841rf3cg.js +0 -5
- package/dist/chunks/studio-8gmwgheg.js +0 -5
- package/dist/chunks/studio-8qm0ep50.js +0 -5
- package/dist/chunks/studio-924p1tm1.js +0 -6
- package/dist/chunks/studio-a3shpz9y.js +0 -5
- package/dist/chunks/studio-amsbaaar.js +0 -6
- package/dist/chunks/studio-at5spjbc.js +0 -7
- package/dist/chunks/studio-b2xv945e.js +0 -5
- package/dist/chunks/studio-bn5nkafw.js +0 -5
- package/dist/chunks/studio-bw6q5xjf.js +0 -9
- package/dist/chunks/studio-c7q0t9x1.js +0 -5
- package/dist/chunks/studio-camnhc96.js +0 -6
- package/dist/chunks/studio-cffqvnzd.js +0 -5
- package/dist/chunks/studio-efvfrsf8.js +0 -5
- package/dist/chunks/studio-er30bpcx.js +0 -5
- package/dist/chunks/studio-ezscgr64.js +0 -5
- package/dist/chunks/studio-ffrrncvz.js +0 -5
- package/dist/chunks/studio-fpphgn8y.js +0 -10
- package/dist/chunks/studio-j1kvhdjk.js +0 -4
- package/dist/chunks/studio-j430n16g.js +0 -7
- package/dist/chunks/studio-jjkg84nj.js +0 -5
- package/dist/chunks/studio-m0q32ars.js +0 -4
- package/dist/chunks/studio-m6bdst11.js +0 -5
- package/dist/chunks/studio-nv2cptd4.js +0 -64
- package/dist/chunks/studio-nwfrc98n.js +0 -5
- package/dist/chunks/studio-p1wgvp7r.js +0 -5
- package/dist/chunks/studio-pag2wncm.js +0 -5
- package/dist/chunks/studio-qvanvzfd.js +0 -5
- package/dist/chunks/studio-qwa64kt7.js +0 -5
- package/dist/chunks/studio-rk1zc4x3.js +0 -928
- package/dist/chunks/studio-se2r3ptc.js +0 -5
- package/dist/chunks/studio-sg2a0dh0.js +0 -5
- package/dist/chunks/studio-tjzjhe68.js +0 -5
- package/dist/chunks/studio-v2w7q8r1.js +0 -7
- package/dist/chunks/studio-v5vjq1h0.js +0 -4
- package/dist/chunks/studio-v8aga3vp.js +0 -14
- package/dist/chunks/studio-vfcdrfmv.js +0 -5
- package/dist/chunks/studio-vmfkgdjf.js +0 -5
- package/dist/chunks/studio-wt1816jj.js +0 -5
- package/dist/chunks/studio-wz73q5kq.js +0 -4
- package/dist/chunks/studio-y04qtxvp.js +0 -7
- package/dist/chunks/studio-y21g8zzg.js +0 -5
- package/dist/chunks/studio-y64hrt8p.js +0 -12
- package/dist/chunks/studio-ynn90f58.js +0 -16
- package/dist/chunks/studio-yxz682sx.js +0 -5
- package/dist/chunks/studio-zp7snvkq.js +0 -5
- package/dist/chunks/studio-zq4z6tm6.js +0 -5
- package/dist/chunks/toast-c9fn075p.js +0 -4
- package/dist/chunks/tsMode-sf49ee9x.js +0 -14
- package/dist/chunks/workspace-jtfahpee.js +0 -4
- package/src/panels/frontmatter-panel.ts +0 -711
- package/src/panels/git-panel.ts +0 -1108
- package/src/surfaces/doc-header.json +0 -776
- package/src/surfaces/doc-header.ts +0 -222
- package/src/surfaces/git-panel.json +0 -1880
- package/src/surfaces/git-panel.ts +0 -264
|
@@ -91,6 +91,7 @@ import { showPromptDialog } from "../ui/layers";
|
|
|
91
91
|
import { parseMediaEntries, schemeOfQuery } from "../utils/canvas-media";
|
|
92
92
|
import { getEffectiveMedia, getEffectiveStyle } from "../site-context";
|
|
93
93
|
import { computeInheritedSources } from "../utils/inherited-style";
|
|
94
|
+
import { tagAncestorSources } from "../style/tag-inheritance";
|
|
94
95
|
import { loadUsages, peekUsages, usageFiles } from "../services/references";
|
|
95
96
|
import { mediaDisplayName } from "./shared";
|
|
96
97
|
import {
|
|
@@ -125,6 +126,7 @@ import type { CssFontPreset, CssLonghand, CssMetaEntry } from "./style-utils";
|
|
|
125
126
|
import { UNIT_RE } from "../ui/unit-selector";
|
|
126
127
|
import { colorTokens, resolvedColor } from "../ui/color-selector";
|
|
127
128
|
import { resolveTokenValue, toTokenRef, tokenRefName } from "../style/token-ref";
|
|
129
|
+
import { PROJECT_VARIABLES_VIEW } from "../style/project-styles";
|
|
128
130
|
import { mountStylePanelSurface } from "../surfaces/style-panel";
|
|
129
131
|
import { openMenu } from "../surfaces/menu";
|
|
130
132
|
import type { MenuHandle, MenuRowProjection } from "../surfaces/menu";
|
|
@@ -1382,6 +1384,11 @@ function shorthandPlaceholder(
|
|
|
1382
1384
|
|
|
1383
1385
|
// ─── The whole view ──────────────────────────────────────────────────────────
|
|
1384
1386
|
|
|
1387
|
+
/** What the Style tab says beside the Variables view, where there is no element to style. */
|
|
1388
|
+
export const VARIABLES_INSPECTOR_MESSAGE =
|
|
1389
|
+
"Variables are edited in the view itself. Switch the view to Elements and pick a tag to style " +
|
|
1390
|
+
"its default here.";
|
|
1391
|
+
|
|
1385
1392
|
/** The three teaching states, and the one that offers a button. */
|
|
1386
1393
|
function emptyView(message: string, withOpen: boolean): StylePanelView {
|
|
1387
1394
|
return {
|
|
@@ -1401,6 +1408,12 @@ function buildView(canvasMode: () => string): StylePanelView {
|
|
|
1401
1408
|
if (!tab) {
|
|
1402
1409
|
return emptyView("Open a page to style what you click.", true);
|
|
1403
1410
|
}
|
|
1411
|
+
/* The Styles workspace's Variables view has no canvas to click and edits its custom properties in
|
|
1412
|
+
the pane itself, so the canvas teaching line would ask for something impossible. Say where the
|
|
1413
|
+
Inspector's half of the workspace is instead. */
|
|
1414
|
+
if (canvasMode() === PROJECT_VARIABLES_VIEW) {
|
|
1415
|
+
return emptyView(VARIABLES_INSPECTOR_MESSAGE, false);
|
|
1416
|
+
}
|
|
1404
1417
|
if (canvasMode() === "stylebook" && shell.stylebook.selection) {
|
|
1405
1418
|
const node = tab.doc.document;
|
|
1406
1419
|
/* Checked, not trusted: a tab's document is whatever the file parsed to, asserted rather than
|
|
@@ -1442,9 +1455,10 @@ function buildEditor(
|
|
|
1442
1455
|
opts: { effectiveStyle?: JxStyle | undefined; stylebookSelector?: string | null },
|
|
1443
1456
|
): StylePanelView {
|
|
1444
1457
|
const { effectiveStyle, stylebookSelector = null } = opts;
|
|
1445
|
-
/*
|
|
1446
|
-
|
|
1447
|
-
|
|
1458
|
+
/* `buildView` calls this with a primary selection it has checked, or in Stylebook, where the
|
|
1459
|
+
edit targets a TAG and the selection is only parked on the root. A Stylebook tab whose session
|
|
1460
|
+
was never parked (or was cleared since) therefore means the root too, rather than a throw. */
|
|
1461
|
+
const sel: JxPath = primarySelection(tab.session.selection) ?? [];
|
|
1448
1462
|
/** The document's OWN style — what a commit writes into. */
|
|
1449
1463
|
const ownRootStyle: JxStyle = node.style || {};
|
|
1450
1464
|
const style = effectiveStyle ?? ownRootStyle;
|
|
@@ -1620,6 +1634,14 @@ function buildEditor(
|
|
|
1620
1634
|
};
|
|
1621
1635
|
}
|
|
1622
1636
|
}
|
|
1637
|
+
// A Project Styles tag rule also inherits from the rules above it in this same file (`body`,
|
|
1638
|
+
// Then each ancestor tag in its path), which is what its specimen is drawn with. The context walk
|
|
1639
|
+
// Above outranks it: a value the tag itself sets at Base is nearer than anything it inherits.
|
|
1640
|
+
if (stylebookPath) {
|
|
1641
|
+
for (const [p, source] of Object.entries(tagAncestorSources(style, stylebookPath, editMedia))) {
|
|
1642
|
+
inheritedInfo[p] ??= { donor: source.donor, value: source.value };
|
|
1643
|
+
}
|
|
1644
|
+
}
|
|
1623
1645
|
const inheritedStyle: Record<string, string | number> = {};
|
|
1624
1646
|
for (const [p, info] of Object.entries(inheritedInfo)) {
|
|
1625
1647
|
inheritedStyle[p] = info.value;
|
|
@@ -2134,6 +2156,11 @@ let _standing: { host: HTMLElement; handle: StylePanelSurface; scope: EffectScop
|
|
|
2134
2156
|
export interface StyleHostDeps {
|
|
2135
2157
|
/** `stylebook` edits a tag catalogue entry; anything else edits the element selection. */
|
|
2136
2158
|
getCanvasMode: () => string;
|
|
2159
|
+
/**
|
|
2160
|
+
* Whether the tab is the one showing. Read inside the projecting effect, so a hidden tab costs
|
|
2161
|
+
* nothing per selection and re-projects the moment it is opened. Absent means always showing.
|
|
2162
|
+
*/
|
|
2163
|
+
isShowing?: () => boolean;
|
|
2137
2164
|
}
|
|
2138
2165
|
|
|
2139
2166
|
/** The default the tab falls back to when the dock names no mode. */
|
|
@@ -2186,9 +2213,16 @@ export function bindStyleHost(el: HTMLElement | null, ctx?: StyleHostDeps): void
|
|
|
2186
2213
|
const handle = mountStylePanelSurface(el, first, ACTIONS, {
|
|
2187
2214
|
target: (element) => attachTargetLine(element ?? undefined),
|
|
2188
2215
|
});
|
|
2216
|
+
const isShowing = ctx?.isShowing ?? (() => true);
|
|
2189
2217
|
const scope = effectScope();
|
|
2190
2218
|
scope.run(() => {
|
|
2191
2219
|
effect(() => {
|
|
2220
|
+
/* A hidden tab does not project. Its editor is thousands of nodes, and a new selection
|
|
2221
|
+
re-keys every row, so projecting behind the Content tab rebuilt the whole of it on every
|
|
2222
|
+
click — most of what selecting an element cost. */
|
|
2223
|
+
if (!isShowing()) {
|
|
2224
|
+
return;
|
|
2225
|
+
}
|
|
2192
2226
|
const view = buildView(_canvasMode);
|
|
2193
2227
|
rememberButtons(view);
|
|
2194
2228
|
handle.update(view);
|
|
@@ -21,8 +21,15 @@ import { isKeyframesAtRule } from "@jxsuite/runtime/css";
|
|
|
21
21
|
import type { StylebookEntry } from "./stylebook-panel";
|
|
22
22
|
import type { ComponentEntry } from "../files/components";
|
|
23
23
|
import type { JxPath } from "../state";
|
|
24
|
-
import { isNonNullObject } from "@jxsuite/schema/guards";
|
|
25
|
-
import type {
|
|
24
|
+
import { isNonNullObject, isRef } from "@jxsuite/schema/guards";
|
|
25
|
+
import type { StylebookSpecimens } from "../style/stylebook-specimens";
|
|
26
|
+
import type {
|
|
27
|
+
JxDocument,
|
|
28
|
+
JxHeadEntry,
|
|
29
|
+
JxMutableNode,
|
|
30
|
+
JxStateDefinition,
|
|
31
|
+
JxStyle,
|
|
32
|
+
} from "@jxsuite/schema/types";
|
|
26
33
|
|
|
27
34
|
export interface StylebookDocResult {
|
|
28
35
|
/** The specimen document (plain JSON — safe to post over the bridge). */
|
|
@@ -142,6 +149,101 @@ export function hasTagStyle(rootStyle: JxStyle, tagPath: string): boolean {
|
|
|
142
149
|
return false;
|
|
143
150
|
}
|
|
144
151
|
|
|
152
|
+
/** One catalogue tag as a list of element defaults draws it: the Styles panel's, and the Outline's. */
|
|
153
|
+
export interface CatalogueRow {
|
|
154
|
+
/** The catalogue entry the row stands for. */
|
|
155
|
+
entry: StylebookEntry;
|
|
156
|
+
tag: string;
|
|
157
|
+
/** The compound path (`ul li`): the row's key, and what selecting the row selects. */
|
|
158
|
+
path: string;
|
|
159
|
+
/** How deep in its specimen the tag sits: 0 for a section's own entries. */
|
|
160
|
+
depth: number;
|
|
161
|
+
/** Whether the selection's leaf is this tag ({@link selectionLeaf}). */
|
|
162
|
+
selected: boolean;
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
/**
|
|
166
|
+
* The leaf of a stylebook selection.
|
|
167
|
+
*
|
|
168
|
+
* A selection is a compound path (`"ul li"`) and the catalogue draws one row per TAG, so the row
|
|
169
|
+
* that is marked is the one whose tag is the path's last segment. That is what the tree has always
|
|
170
|
+
* done; it is written down here because "selected" meaning something other than "equal" is exactly
|
|
171
|
+
* the kind of thing a reader assumes is a bug.
|
|
172
|
+
*/
|
|
173
|
+
export function selectionLeaf(selection: string | null): string | null {
|
|
174
|
+
if (!selection) {
|
|
175
|
+
return null;
|
|
176
|
+
}
|
|
177
|
+
return selection.split(" ").pop() ?? null;
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
/**
|
|
181
|
+
* Flatten catalogue entries and everything under them into rows, in document order.
|
|
182
|
+
*
|
|
183
|
+
* Children are deduplicated by tag: a `<ul>` specimen carries several `<li>`s and they are one row,
|
|
184
|
+
* because the row selects a TAG and there is one rule per tag path to write. The ONE walk both
|
|
185
|
+
* lists draw from, so the two cannot drift; what each says about a row (its dot, its label) is the
|
|
186
|
+
* caller's.
|
|
187
|
+
*
|
|
188
|
+
* @param entries A section's entries, or several sections' in order
|
|
189
|
+
* @param selection The stylebook selection (`shell.stylebook.selection`)
|
|
190
|
+
*/
|
|
191
|
+
export function catalogueRows(
|
|
192
|
+
entries: readonly StylebookEntry[],
|
|
193
|
+
selection: string | null,
|
|
194
|
+
): CatalogueRow[] {
|
|
195
|
+
const leaf = selectionLeaf(selection);
|
|
196
|
+
const out: CatalogueRow[] = [];
|
|
197
|
+
const walk = (entry: StylebookEntry, depth: number, parentPath: string): void => {
|
|
198
|
+
const path = parentPath ? `${parentPath} ${entry.tag}` : entry.tag;
|
|
199
|
+
out.push({ depth, entry, path, selected: entry.tag === leaf, tag: entry.tag });
|
|
200
|
+
const children = entry.children
|
|
201
|
+
? [...new Map(entry.children.map((child) => [child.tag, child])).values()]
|
|
202
|
+
: [];
|
|
203
|
+
for (const child of children) {
|
|
204
|
+
walk(child, depth + 1, path);
|
|
205
|
+
}
|
|
206
|
+
};
|
|
207
|
+
for (const entry of entries) {
|
|
208
|
+
walk(entry, 0, "");
|
|
209
|
+
}
|
|
210
|
+
return out;
|
|
211
|
+
}
|
|
212
|
+
|
|
213
|
+
/**
|
|
214
|
+
* A card's specimen for a component drawn as the first row of a list
|
|
215
|
+
* (`style/stylebook-specimens.ts`): the list's repeater, reading its row from `rootState[key]` so
|
|
216
|
+
* two cards' lists cannot collide, and the rest of the page state the row was drawn in, the first
|
|
217
|
+
* card's value winning a shared name (`$page`, `$site`). Null when the sample is not a repeater
|
|
218
|
+
* over a state list.
|
|
219
|
+
*/
|
|
220
|
+
export function sampleRowSpecimen(
|
|
221
|
+
sample: JxDocument,
|
|
222
|
+
key: string,
|
|
223
|
+
rootState: Record<string, JxStateDefinition>,
|
|
224
|
+
): JxMutableNode | null {
|
|
225
|
+
const [list] = Array.isArray(sample.children) ? sample.children : [];
|
|
226
|
+
if (!isNonNullObject(list) || Array.isArray(list) || !isRef(list.items)) {
|
|
227
|
+
return null;
|
|
228
|
+
}
|
|
229
|
+
const { $ref } = list.items;
|
|
230
|
+
const listKey = $ref.startsWith("#/state/") ? $ref.slice("#/state/".length) : "";
|
|
231
|
+
const rows = sample.state?.[listKey];
|
|
232
|
+
if (!Array.isArray(rows)) {
|
|
233
|
+
return null;
|
|
234
|
+
}
|
|
235
|
+
rootState[key] = rows;
|
|
236
|
+
for (const [name, value] of Object.entries(sample.state ?? {})) {
|
|
237
|
+
if (name !== listKey && !(name in rootState)) {
|
|
238
|
+
rootState[name] = value;
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
/* SAFETY: `list` is the repeater object a page's `children` held; only its `items` is replaced,
|
|
242
|
+
with a ref of the same shape. */
|
|
243
|
+
const repeater = { ...list, items: { $ref: `#/state/${key}` } } as JxMutableNode;
|
|
244
|
+
return { children: [repeater], tagName: "div" };
|
|
245
|
+
}
|
|
246
|
+
|
|
145
247
|
/** Options for {@link buildStylebookDoc}. */
|
|
146
248
|
export interface BuildStylebookDocOpts {
|
|
147
249
|
meta: { $sections: { label: string; elements: StylebookEntry[] }[] };
|
|
@@ -150,9 +252,16 @@ export interface BuildStylebookDocOpts {
|
|
|
150
252
|
effectiveStyle: JxStyle;
|
|
151
253
|
/** Merged $media map (getEffectiveMedia output) — becomes the doc's $media. */
|
|
152
254
|
effectiveMedia: Record<string, string>;
|
|
255
|
+
/** Merged project+document `$head` (getEffectiveHead output) — becomes the doc's `$head`. */
|
|
256
|
+
effectiveHead?: JxHeadEntry[];
|
|
153
257
|
filter: string;
|
|
154
258
|
customizedOnly: boolean;
|
|
155
259
|
projectRoot: string | null;
|
|
260
|
+
/**
|
|
261
|
+
* How each component card is drawn, by tag (`style/stylebook-specimens.ts`). A component with no
|
|
262
|
+
* entry is drawn bare, with its declared defaults as attributes.
|
|
263
|
+
*/
|
|
264
|
+
specimens?: StylebookSpecimens;
|
|
156
265
|
}
|
|
157
266
|
|
|
158
267
|
/**
|
|
@@ -265,6 +374,8 @@ export function buildStylebookDoc(opts: BuildStylebookDocOpts): StylebookDocResu
|
|
|
265
374
|
|
|
266
375
|
// Custom components from the registry — live custom elements registered via $elements.
|
|
267
376
|
const $elements: (string | { $ref: string })[] = [];
|
|
377
|
+
// The data the sample-row cards read: each row's list, and the page context it was drawn in.
|
|
378
|
+
const rootState: Record<string, JxStateDefinition> = {};
|
|
268
379
|
{
|
|
269
380
|
let comps = opts.components;
|
|
270
381
|
if (filter) {
|
|
@@ -288,17 +399,30 @@ export function buildStylebookDoc(opts: BuildStylebookDocOpts): StylebookDocResu
|
|
|
288
399
|
"/",
|
|
289
400
|
),
|
|
290
401
|
});
|
|
291
|
-
const
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
402
|
+
const drawn = opts.specimens?.get(comp.tagName);
|
|
403
|
+
if (drawn?.kind === "props") {
|
|
404
|
+
const specimen: JxMutableNode = { $props: drawn.props, tagName: comp.tagName };
|
|
405
|
+
return cardNode(comp.tagName, `<${comp.tagName}>`, specimen, cardPath, null);
|
|
406
|
+
}
|
|
407
|
+
if (drawn?.kind === "row") {
|
|
408
|
+
const row = sampleRowSpecimen(drawn.sample.doc, `stylebookRow${ci}`, rootState);
|
|
409
|
+
if (row) {
|
|
410
|
+
return cardNode(comp.tagName, `<${comp.tagName}>`, row, cardPath, null);
|
|
295
411
|
}
|
|
296
412
|
}
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
413
|
+
if (drawn?.kind !== "none") {
|
|
414
|
+
const attributes: Record<string, string> = {};
|
|
415
|
+
for (const p of comp.props ?? []) {
|
|
416
|
+
if (p.default !== undefined && p.default !== "false" && p.default !== "''") {
|
|
417
|
+
attributes[p.name] = String(p.default).replaceAll(/^'|'$/g, "");
|
|
418
|
+
}
|
|
419
|
+
}
|
|
420
|
+
const specimen: JxMutableNode = { tagName: comp.tagName };
|
|
421
|
+
if (Object.keys(attributes).length > 0) {
|
|
422
|
+
specimen.attributes = attributes;
|
|
423
|
+
}
|
|
424
|
+
return cardNode(comp.tagName, `<${comp.tagName}>`, specimen, cardPath, null);
|
|
300
425
|
}
|
|
301
|
-
return cardNode(comp.tagName, `<${comp.tagName}>`, specimen, cardPath, null);
|
|
302
426
|
}
|
|
303
427
|
// Npm/format-class components can't be $ref-registered — placeholder box (legacy parity).
|
|
304
428
|
const fallback: JxMutableNode = {
|
|
@@ -325,7 +449,15 @@ export function buildStylebookDoc(opts: BuildStylebookDocOpts): StylebookDocResu
|
|
|
325
449
|
if ($elements.length > 0) {
|
|
326
450
|
doc.$elements = $elements;
|
|
327
451
|
}
|
|
452
|
+
/* The project's `$head` too: its webfont links are what make `fontFamily: 'Barlow'` render as
|
|
453
|
+
Barlow, and a specimen sheet drawn in the system fallback shows styles the site never has. */
|
|
454
|
+
if (opts.effectiveHead && opts.effectiveHead.length > 0) {
|
|
455
|
+
doc.$head = opts.effectiveHead;
|
|
456
|
+
}
|
|
328
457
|
doc.$media = opts.effectiveMedia;
|
|
458
|
+
if (Object.keys(rootState).length > 0) {
|
|
459
|
+
doc.state = rootState;
|
|
460
|
+
}
|
|
329
461
|
doc.attributes = { class: "sb-root" };
|
|
330
462
|
doc.children = sections;
|
|
331
463
|
doc.style = transposeStylebookStyle(opts.effectiveStyle);
|
|
@@ -1,14 +1,21 @@
|
|
|
1
1
|
/// <reference lib="dom" />
|
|
2
2
|
/**
|
|
3
|
-
* The Outline panel while the pane is showing
|
|
4
|
-
*
|
|
3
|
+
* The Outline panel while the pane is showing a document's Elements view — the element catalogue.
|
|
4
|
+
*
|
|
5
|
+
* A page or a component offers **Elements** in its Editor control, which styles that file's element
|
|
6
|
+
* defaults (`docs/studio/design/stylebook.md`), and the Outline beside it lists the catalogue's
|
|
7
|
+
* tags instead of the document's tree. `project.json` in the Styles workspace has its own
|
|
8
|
+
* Navigator, the Styles panel (`panels/styles-panel.ts`), which lists the project's CSS custom
|
|
9
|
+
* properties too; the variables list this body used to draw beside the Variables view went there
|
|
10
|
+
* with it.
|
|
5
11
|
*
|
|
6
12
|
* **The body is a Jx document** (`surfaces/panel-stylebook-layers.json`, mounted by
|
|
7
13
|
* `surfaces/panel-stylebook-layers.ts`), so this module renders nothing and projects everything.
|
|
8
|
-
* What stays here is what is a DECISION:
|
|
9
|
-
*
|
|
10
|
-
*
|
|
11
|
-
*
|
|
14
|
+
* What stays here is what is a DECISION: which tags the open file has already styled, and what each
|
|
15
|
+
* row is called. The walk itself (how the catalogue's recursive `$sections` flatten into a list,
|
|
16
|
+
* how a child's compound path is spelled, which children are duplicates of each other, and which
|
|
17
|
+
* row the current selection marks) is `stylebook-doc.ts`'s `catalogueRows`, which the Styles
|
|
18
|
+
* panel's Elements section draws from too. The surface reads values.
|
|
12
19
|
*
|
|
13
20
|
* The panel does not own the panel RECORD — `panels/layers-panel.ts` does, because the Outline is
|
|
14
21
|
* one panel with two bodies and only the record can know which the pane is asking for. That module
|
|
@@ -23,13 +30,13 @@ import { activeTab } from "../workspace/workspace";
|
|
|
23
30
|
import { shell } from "../shell";
|
|
24
31
|
import { componentRegistry } from "../files/components";
|
|
25
32
|
import { mountStylebookLayersSurface } from "../surfaces/panel-stylebook-layers";
|
|
33
|
+
import { catalogueRows } from "./stylebook-doc";
|
|
26
34
|
|
|
27
35
|
import type { StylebookEntry } from "./stylebook-panel";
|
|
28
36
|
import type {
|
|
29
37
|
StylebookLayersSurfaceHandle,
|
|
30
38
|
StylebookLayersValues,
|
|
31
39
|
StylebookRowView,
|
|
32
|
-
StylebookVariableView,
|
|
33
40
|
} from "../surfaces/panel-stylebook-layers";
|
|
34
41
|
import { isNonNullObject } from "@jxsuite/schema/guards";
|
|
35
42
|
import type { JxStyle } from "@jxsuite/schema/types";
|
|
@@ -55,61 +62,6 @@ function hasTagStyle(rootStyle: JxStyle, tag: string): boolean {
|
|
|
55
62
|
return isNonNullObject(s) && Object.keys(s).length > 0;
|
|
56
63
|
}
|
|
57
64
|
|
|
58
|
-
/**
|
|
59
|
-
* The leaf of the current selection.
|
|
60
|
-
*
|
|
61
|
-
* A selection is a compound path (`"ul li"`) and the catalogue draws one row per TAG, so the row
|
|
62
|
-
* that is marked is the one whose tag is the path's last segment. That is what the tree has always
|
|
63
|
-
* done; it is written down here because "selected" meaning something other than "equal" is exactly
|
|
64
|
-
* the kind of thing a reader assumes is a bug.
|
|
65
|
-
*/
|
|
66
|
-
function selectedLeaf(selection: string | null): string | null {
|
|
67
|
-
if (!selection) {
|
|
68
|
-
return null;
|
|
69
|
-
}
|
|
70
|
-
return selection.includes(" ") ? (selection.split(" ").pop() ?? null) : selection;
|
|
71
|
-
}
|
|
72
|
-
|
|
73
|
-
/**
|
|
74
|
-
* Flatten one catalogue entry and everything under it into rows.
|
|
75
|
-
*
|
|
76
|
-
* Children are deduplicated by tag — a `<ul>` specimen carries two `<li>`s and they are one row,
|
|
77
|
-
* because the row selects a TAG and there is only one `& li` to write.
|
|
78
|
-
*/
|
|
79
|
-
function elementRows(
|
|
80
|
-
entry: StylebookEntry,
|
|
81
|
-
rootStyle: JxStyle,
|
|
82
|
-
leaf: string | null,
|
|
83
|
-
depth: number,
|
|
84
|
-
parentPath: string,
|
|
85
|
-
out: StylebookRowView[],
|
|
86
|
-
): void {
|
|
87
|
-
const { tag } = entry;
|
|
88
|
-
const fullPath = parentPath ? `${parentPath} ${tag}` : tag;
|
|
89
|
-
out.push({
|
|
90
|
-
customized: hasTagStyle(rootStyle, tag),
|
|
91
|
-
indent: `${INDENT_BASE + depth * INDENT_STEP}px`,
|
|
92
|
-
key: fullPath,
|
|
93
|
-
kind: "element",
|
|
94
|
-
label: entry.text || `<${tag}>`,
|
|
95
|
-
selected: tag === leaf,
|
|
96
|
-
tag,
|
|
97
|
-
});
|
|
98
|
-
const children = entry.children
|
|
99
|
-
? [...new Map(entry.children.map((c: StylebookEntry) => [c.tag, c])).values()]
|
|
100
|
-
: [];
|
|
101
|
-
for (const child of children) {
|
|
102
|
-
elementRows(child, rootStyle, leaf, depth + 1, fullPath, out);
|
|
103
|
-
}
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
/** The custom properties the open file declares, in the order it declares them. */
|
|
107
|
-
function variableRows(rootStyle: JxStyle): StylebookVariableView[] {
|
|
108
|
-
return Object.entries(rootStyle)
|
|
109
|
-
.filter(([k]) => k.startsWith("--"))
|
|
110
|
-
.map(([name, value]) => ({ key: name, name, value: String(value) }));
|
|
111
|
-
}
|
|
112
|
-
|
|
113
65
|
/**
|
|
114
66
|
* What the surface should be showing right now.
|
|
115
67
|
*
|
|
@@ -123,14 +75,20 @@ export function stylebookLayersValues(ctx: StylebookLayersCtx): StylebookLayersV
|
|
|
123
75
|
const tab = activeTab.value;
|
|
124
76
|
const rootStyle: JxStyle = tab?.doc.document?.style || {};
|
|
125
77
|
const { selection } = shell.stylebook;
|
|
126
|
-
const leaf = selectedLeaf(selection);
|
|
127
78
|
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
79
|
+
/* The stylebook's own walk (`stylebook-doc.ts` `catalogueRows`), which the Styles panel's
|
|
80
|
+
Elements section draws from too: the path, the nesting, the deduplication and the leaf mark
|
|
81
|
+
are one decision, and only the dot and the label are this list's. */
|
|
82
|
+
const entries = ctx.stylebookMeta.$sections.flatMap((section) => section.elements);
|
|
83
|
+
const rows: StylebookRowView[] = catalogueRows(entries, selection).map((row) => ({
|
|
84
|
+
customized: hasTagStyle(rootStyle, row.tag),
|
|
85
|
+
indent: `${INDENT_BASE + row.depth * INDENT_STEP}px`,
|
|
86
|
+
key: row.path,
|
|
87
|
+
kind: "element",
|
|
88
|
+
label: row.entry.text || `<${row.tag}>`,
|
|
89
|
+
selected: row.selected,
|
|
90
|
+
tag: row.tag,
|
|
91
|
+
}));
|
|
134
92
|
for (const comp of componentRegistry) {
|
|
135
93
|
rows.push({
|
|
136
94
|
customized: false,
|
|
@@ -145,13 +103,7 @@ export function stylebookLayersValues(ctx: StylebookLayersCtx): StylebookLayersV
|
|
|
145
103
|
});
|
|
146
104
|
}
|
|
147
105
|
|
|
148
|
-
|
|
149
|
-
return {
|
|
150
|
-
hasVariables: variables.length > 0,
|
|
151
|
-
rows,
|
|
152
|
-
tab: shell.stylebook.tab,
|
|
153
|
-
variables,
|
|
154
|
-
};
|
|
106
|
+
return { rows };
|
|
155
107
|
}
|
|
156
108
|
|
|
157
109
|
/**
|
|
@@ -161,7 +113,12 @@ export function stylebookLayersValues(ctx: StylebookLayersCtx): StylebookLayersV
|
|
|
161
113
|
* one Navigator, so a mount into a DIFFERENT node is the old one being replaced, and holding both
|
|
162
114
|
* would leave the first one's effects running against a scope nobody writes any more.
|
|
163
115
|
*/
|
|
164
|
-
let standing: {
|
|
116
|
+
let standing: {
|
|
117
|
+
/** The latest ctx: the handlers read it, not the one the first mount closed over. */
|
|
118
|
+
ctx: StylebookLayersCtx;
|
|
119
|
+
host: HTMLElement;
|
|
120
|
+
handle: StylebookLayersSurfaceHandle;
|
|
121
|
+
} | null = null;
|
|
165
122
|
|
|
166
123
|
/**
|
|
167
124
|
* Keep the selected row on screen after a repaint.
|
|
@@ -201,12 +158,14 @@ export function mountStylebookLayersPanel(ctx: StylebookLayersCtx, host: HTMLEle
|
|
|
201
158
|
}
|
|
202
159
|
const values = stylebookLayersValues(ctx);
|
|
203
160
|
if (standing) {
|
|
161
|
+
standing.ctx = ctx;
|
|
204
162
|
standing.handle.update(values);
|
|
205
163
|
} else {
|
|
206
164
|
standing = {
|
|
165
|
+
ctx,
|
|
207
166
|
handle: mountStylebookLayersSurface(target, values, {
|
|
208
167
|
selectRow: (path) => {
|
|
209
|
-
ctx.selectStylebookTag(path, undefined, { panCanvas: true });
|
|
168
|
+
(standing?.ctx ?? ctx).selectStylebookTag(path, undefined, { panCanvas: true });
|
|
210
169
|
},
|
|
211
170
|
}),
|
|
212
171
|
host: target,
|
|
@@ -218,8 +177,8 @@ export function mountStylebookLayersPanel(ctx: StylebookLayersCtx, host: HTMLEle
|
|
|
218
177
|
/**
|
|
219
178
|
* Take the catalogue down.
|
|
220
179
|
*
|
|
221
|
-
* Called by the Outline's record when the pane is no longer showing
|
|
222
|
-
* document survives its own irrelevance: lit's branch renders into the range it owns inside
|
|
180
|
+
* Called by the Outline's record when the pane is no longer showing an Elements view. Without it
|
|
181
|
+
* the document survives its own irrelevance: lit's branch renders into the range it owns inside
|
|
223
182
|
* `.panel-content` and leaves everything appended after it exactly where it was.
|
|
224
183
|
*/
|
|
225
184
|
export function detachStylebookLayers(): void {
|
|
@@ -24,15 +24,16 @@ import { projectState, updateSession } from "../store";
|
|
|
24
24
|
import { createStylebookChromeSurface } from "../surfaces/stylebook-chrome";
|
|
25
25
|
import type { StylebookChromeSurface } from "../surfaces/stylebook-chrome";
|
|
26
26
|
import type { CanvasSurface } from "../canvas/canvas-surface";
|
|
27
|
-
import { tabOfPane } from "../canvas/canvas-surface";
|
|
27
|
+
import { activeMediaOfPane, tabOfPane } from "../canvas/canvas-surface";
|
|
28
28
|
import { activeTab } from "../workspace/workspace";
|
|
29
29
|
import { shell } from "../shell";
|
|
30
30
|
import { componentRegistry } from "../files/components";
|
|
31
|
-
import { getEffectiveMedia, getEffectiveStyle } from "../site-context";
|
|
31
|
+
import { getEffectiveHead, getEffectiveMedia, getEffectiveStyle } from "../site-context";
|
|
32
32
|
import { parseMediaEntries } from "../utils/canvas-media";
|
|
33
33
|
import { mediaDisplayName } from "./shared";
|
|
34
34
|
import { buildStylebookDoc } from "./stylebook-doc";
|
|
35
35
|
import { PROJECT_STYLES_TITLE } from "../style/project-styles";
|
|
36
|
+
import { loadStylebookSpecimens } from "../style/stylebook-specimens";
|
|
36
37
|
import { mountStylebookCanvas, panToStylebookTag } from "../canvas/iframe-host";
|
|
37
38
|
import stylebookMeta from "../../data/stylebook-meta.json";
|
|
38
39
|
import type { CanvasPanelEntry } from "../canvas/canvas-utils";
|
|
@@ -124,11 +125,29 @@ function chromeBar(surface: CanvasSurface): HTMLElement {
|
|
|
124
125
|
* a lit template: the hand-over used to be a `TemplateResult` per artboard, which meant the boards
|
|
125
126
|
* could only be drawn by whoever was already rendering with lit. It is a mount seam instead — the
|
|
126
127
|
* catalogue's bar is a node this module owns, placed in the empty box the stage draws for it, the
|
|
127
|
-
* same way the Compare bar and the
|
|
128
|
+
* same way the Compare bar and the writing banner are.
|
|
128
129
|
*
|
|
129
130
|
* @param {StylebookCtx} ctx
|
|
130
131
|
* @returns {Promise<void>} Settles once the artboards are in the page
|
|
131
132
|
*/
|
|
133
|
+
/**
|
|
134
|
+
* The one breakpoint the specimen sheet is drawn at: the one the Context bar's size switcher names
|
|
135
|
+
* (its `activeMedia`, or the lens a split pane derives), else the base.
|
|
136
|
+
*
|
|
137
|
+
* It drew every declared breakpoint side by side, as Design does for a page, and fitting four
|
|
138
|
+
* artboards into one pane put a 1280px sheet at 24%, where no heading or paragraph can be read; a
|
|
139
|
+
* sheet of type specimens is read, not compared at a glance. One artboard at the breakpoint being
|
|
140
|
+
* styled is what the Styles workspace's board shows (Desktop · Tablet · Phone, one at a time), and
|
|
141
|
+
* it is the breakpoint a style edit lands on, because selecting a specimen writes `activeMedia`.
|
|
142
|
+
*/
|
|
143
|
+
export function stylebookBoards<T extends { name: string }>(
|
|
144
|
+
boards: readonly T[],
|
|
145
|
+
active: string | null,
|
|
146
|
+
): T[] {
|
|
147
|
+
const named = boards.filter((board) => board.name === (active ?? "base"));
|
|
148
|
+
return named.length > 0 ? named : boards.slice(0, 1);
|
|
149
|
+
}
|
|
150
|
+
|
|
132
151
|
export async function renderStylebookMode(
|
|
133
152
|
surface: CanvasSurface,
|
|
134
153
|
ctx: StylebookCtx,
|
|
@@ -142,6 +161,9 @@ export async function renderStylebookMode(
|
|
|
142
161
|
const tab = tabOfPane(surface.paneId);
|
|
143
162
|
const filter = shell.stylebook.filter.toLowerCase();
|
|
144
163
|
const { customizedOnly } = shell.stylebook;
|
|
164
|
+
const generation = surface.renderGeneration;
|
|
165
|
+
const registry = componentRegistry;
|
|
166
|
+
const specimensPending = loadStylebookSpecimens(registry);
|
|
145
167
|
|
|
146
168
|
const effectiveMedia = getEffectiveMedia(tab?.doc.document?.$media);
|
|
147
169
|
const { sizeBreakpoints, baseWidth } = parseMediaEntries(effectiveMedia);
|
|
@@ -185,7 +207,7 @@ export async function renderStylebookMode(
|
|
|
185
207
|
),
|
|
186
208
|
];
|
|
187
209
|
} else {
|
|
188
|
-
panelEntries = allPanelDefs.map((def) =>
|
|
210
|
+
panelEntries = stylebookBoards(allPanelDefs, activeMediaOfPane(surface.paneId)).map((def) =>
|
|
189
211
|
ctx.canvasPanelEntry(def.name, `${def.displayName} (${def.width}px)`, false, def.width),
|
|
190
212
|
);
|
|
191
213
|
}
|
|
@@ -220,11 +242,21 @@ export async function renderStylebookMode(
|
|
|
220
242
|
chromeHost.replaceChildren(chromeBarNode);
|
|
221
243
|
}
|
|
222
244
|
|
|
245
|
+
/* What each component card is drawn with (started before the stage was drawn), asked once per
|
|
246
|
+
registry, so only the first paint after the project's components are read waits for it. A
|
|
247
|
+
render that began while it was being asked owns the stage now, and this one stops. */
|
|
248
|
+
const specimens = await specimensPending;
|
|
249
|
+
if (surface.renderGeneration !== generation) {
|
|
250
|
+
return;
|
|
251
|
+
}
|
|
252
|
+
|
|
223
253
|
// ONE generated doc shared by every panel — per-panel @media differentiation comes from each
|
|
224
254
|
// Iframe's real viewport width, not from a per-panel style flatten.
|
|
225
255
|
const generated = buildStylebookDoc({
|
|
226
|
-
components:
|
|
256
|
+
components: registry,
|
|
257
|
+
specimens,
|
|
227
258
|
customizedOnly: Boolean(customizedOnly),
|
|
259
|
+
effectiveHead: getEffectiveHead(tab?.doc.document?.$head),
|
|
228
260
|
effectiveMedia,
|
|
229
261
|
effectiveStyle: getEffectiveStyle(tab?.doc.document?.style),
|
|
230
262
|
filter,
|
|
@@ -255,18 +287,23 @@ export async function renderStylebookMode(
|
|
|
255
287
|
* @param {string | null} [media]
|
|
256
288
|
*/
|
|
257
289
|
export function selectStylebookTag(tag: string, media?: string | null, { panCanvas = false } = {}) {
|
|
258
|
-
shell.stylebook.selection = tag;
|
|
259
290
|
const ui: Partial<TabUi> = { activeSelector: tag, rightTab: "style" };
|
|
260
291
|
if (media !== undefined) {
|
|
261
292
|
ui.activeMedia = media;
|
|
262
293
|
}
|
|
294
|
+
// The session is written BEFORE the stylebook selection moves: writing `shell.stylebook.selection`
|
|
295
|
+
// Re-runs the Style panel's effect synchronously, and it should find `activeSelector` and the
|
|
296
|
+
// Breakpoint already in place.
|
|
263
297
|
updateSession(activeTab.value, {
|
|
264
|
-
//
|
|
265
|
-
//
|
|
266
|
-
//
|
|
267
|
-
|
|
298
|
+
// EMPTY, not the root. A specimen is not a node of the document, so no document path names
|
|
299
|
+
// What is selected; `stylebookTarget` is how the chrome learns the tag. Parking on the root
|
|
300
|
+
// `[[]]` made every reader of the document selection (the command bar, the Inspector header)
|
|
301
|
+
// Name the catalogue's root `div` while `h1` was being edited, and it is what a canvas hit on
|
|
302
|
+
// A specimen already left behind, so the Outline and the canvas now agree.
|
|
303
|
+
selection: [],
|
|
268
304
|
ui,
|
|
269
305
|
});
|
|
306
|
+
shell.stylebook.selection = tag;
|
|
270
307
|
|
|
271
308
|
if (tag && panCanvas) {
|
|
272
309
|
panToStylebookTag(tag);
|