@ciderpress/ui 1.0.0-rc.1
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 +23 -0
- package/dist/0~142.js +2 -0
- package/dist/0~164.js +2 -0
- package/dist/0~2.js +2 -0
- package/dist/0~225.js +2 -0
- package/dist/0~288.js +2 -0
- package/dist/0~299.js +2 -0
- package/dist/0~3.js +2 -0
- package/dist/0~301.js +2 -0
- package/dist/0~311.js +2 -0
- package/dist/0~326.js +2 -0
- package/dist/0~40.js +2 -0
- package/dist/0~43.js +2 -0
- package/dist/0~433.js +2 -0
- package/dist/0~453.js +2 -0
- package/dist/0~457.js +2 -0
- package/dist/0~497.js +2 -0
- package/dist/0~511.js +2 -0
- package/dist/0~603.js +2 -0
- package/dist/0~616.js +2 -0
- package/dist/0~659.js +2 -0
- package/dist/0~670.js +2 -0
- package/dist/0~687.js +2 -0
- package/dist/0~706.js +2 -0
- package/dist/0~729.js +2 -0
- package/dist/0~768.js +2 -0
- package/dist/0~819.js +2 -0
- package/dist/0~830.js +2 -0
- package/dist/0~854.js +2 -0
- package/dist/0~863.js +2 -0
- package/dist/0~879.js +2 -0
- package/dist/0~96.js +2 -0
- package/dist/0~97.js +2 -0
- package/dist/components/FileTree/FileTree.css +90 -0
- package/dist/components/FileTree/FileTree.d.ts +7 -0
- package/dist/components/FileTree/FileTree.js +531 -0
- package/dist/components/FileTree/FileTreeItem.d.ts +8 -0
- package/dist/components/FileTree/RemoteSvgIcon.d.ts +11 -0
- package/dist/components/FileTree/index.d.ts +4 -0
- package/dist/components/folder-icons.d.ts +32 -0
- package/dist/components/languages.d.ts +7 -0
- package/dist/components/tree-parser/tree-parser.d.ts +12 -0
- package/dist/components/tree-parser/types.d.ts +11 -0
- package/dist/head/css/loader-apple.css +1 -0
- package/dist/head/css/loader-backdrop.css +1 -0
- package/dist/head/css/loader-dots.css +1 -0
- package/dist/head/css/themes/amber.css +1 -0
- package/dist/head/css/themes/arcade.css +1 -0
- package/dist/head/css/themes/grannysmith.css +1 -0
- package/dist/head/css/themes/honeycrisp.css +1 -0
- package/dist/head/css/themes/midnight.css +1 -0
- package/dist/head/css/themes/mulled.css +1 -0
- package/dist/head/js/loader-dots.js +1 -0
- package/dist/head/js/vscode-nav.js +1 -0
- package/dist/index.d.ts +43 -0
- package/dist/index.mjs +40 -0
- package/dist/node.d.ts +81 -0
- package/dist/node.mjs +17762 -0
- package/dist/plugins/mermaid/MermaidRenderer.tsx +480 -0
- package/dist/plugins/mermaid/mermaid.css +199 -0
- package/dist/theme/components/announcement/announcement-bar.css +103 -0
- package/dist/theme/components/announcement/announcement-bar.tsx +173 -0
- package/dist/theme/components/ask-ai/ask-ai-button.css +52 -0
- package/dist/theme/components/ask-ai/ask-ai-button.tsx +56 -0
- package/dist/theme/components/content-footer/content-footer-portal.tsx +70 -0
- package/dist/theme/components/content-footer/feedback.css +47 -0
- package/dist/theme/components/content-footer/feedback.tsx +96 -0
- package/dist/theme/components/content-footer/meta-actions.css +25 -0
- package/dist/theme/components/content-footer/meta-actions.tsx +57 -0
- package/dist/theme/components/content-footer/page-pager.css +61 -0
- package/dist/theme/components/content-footer/page-pager.tsx +110 -0
- package/dist/theme/components/edit-source-button.tsx +97 -0
- package/dist/theme/components/footer/site-footer.css +179 -0
- package/dist/theme/components/footer/site-footer.tsx +115 -0
- package/dist/theme/components/home/cta.css +67 -0
- package/dist/theme/components/home/cta.tsx +77 -0
- package/dist/theme/components/home/feature-card.css +52 -0
- package/dist/theme/components/home/feature-card.tsx +131 -0
- package/dist/theme/components/home/feature.tsx +79 -0
- package/dist/theme/components/home/hero-demo.css +66 -0
- package/dist/theme/components/home/hero-demo.tsx +46 -0
- package/dist/theme/components/home/hero.css +96 -0
- package/dist/theme/components/home/hero.tsx +111 -0
- package/dist/theme/components/home/layout.tsx +183 -0
- package/dist/theme/components/home/page-rail.css +21 -0
- package/dist/theme/components/home/page-rail.tsx +19 -0
- package/dist/theme/components/home/split.css +148 -0
- package/dist/theme/components/home/split.tsx +120 -0
- package/dist/theme/components/home/trust-strip.css +33 -0
- package/dist/theme/components/home/trust-strip.tsx +43 -0
- package/dist/theme/components/home/workspaces.tsx +71 -0
- package/dist/theme/components/nav/branch-tag.css +54 -0
- package/dist/theme/components/nav/branch-tag.tsx +101 -0
- package/dist/theme/components/nav/ciderpress-doc-layout.tsx +247 -0
- package/dist/theme/components/nav/ciderpress-docs-bar.css +505 -0
- package/dist/theme/components/nav/ciderpress-docs-bar.tsx +426 -0
- package/dist/theme/components/nav/ciderpress-header.css +172 -0
- package/dist/theme/components/nav/ciderpress-header.tsx +113 -0
- package/dist/theme/components/nav/ciderpress-layout-context.tsx +49 -0
- package/dist/theme/components/nav/ciderpress-nav-hamburger.css +193 -0
- package/dist/theme/components/nav/ciderpress-nav-hamburger.tsx +112 -0
- package/dist/theme/components/nav/ciderpress-nav-menu.css +130 -0
- package/dist/theme/components/nav/ciderpress-nav-menu.tsx +372 -0
- package/dist/theme/components/nav/ciderpress-nav-search.css +73 -0
- package/dist/theme/components/nav/ciderpress-nav-search.tsx +55 -0
- package/dist/theme/components/nav/ciderpress-nav-social-links.css +35 -0
- package/dist/theme/components/nav/ciderpress-nav-social-links.tsx +87 -0
- package/dist/theme/components/nav/floating-branch-indicator.css +106 -0
- package/dist/theme/components/nav/floating-branch-indicator.tsx +109 -0
- package/dist/theme/components/nav/layout.tsx +268 -0
- package/dist/theme/components/nav/mobile-nav-cta.tsx +79 -0
- package/dist/theme/components/nav/nav-divider.css +15 -0
- package/dist/theme/components/nav/nav-divider.tsx +19 -0
- package/dist/theme/components/nav/nav-logo.css +42 -0
- package/dist/theme/components/nav/nav-logo.tsx +262 -0
- package/dist/theme/components/nav/theme-switcher.css +92 -0
- package/dist/theme/components/nav/theme-switcher.tsx +298 -0
- package/dist/theme/components/nav/topbar-cta.css +45 -0
- package/dist/theme/components/nav/topbar-cta.tsx +39 -0
- package/dist/theme/components/nav/variant-toggle.css +70 -0
- package/dist/theme/components/nav/variant-toggle.tsx +83 -0
- package/dist/theme/components/nav/version-chip.css +31 -0
- package/dist/theme/components/nav/version-chip.tsx +45 -0
- package/dist/theme/components/nav/vscode-tag.css +32 -0
- package/dist/theme/components/nav/vscode-tag.tsx +20 -0
- package/dist/theme/components/openapi/code-sample.tsx +341 -0
- package/dist/theme/components/openapi/copy-markdown-button.tsx +41 -0
- package/dist/theme/components/openapi/icons.tsx +45 -0
- package/dist/theme/components/openapi/index.ts +6 -0
- package/dist/theme/components/openapi/method-badge.tsx +24 -0
- package/dist/theme/components/openapi/openapi.css +665 -0
- package/dist/theme/components/openapi/operation.tsx +200 -0
- package/dist/theme/components/openapi/overview.tsx +207 -0
- package/dist/theme/components/openapi/parameters-table.tsx +149 -0
- package/dist/theme/components/openapi/request-body.tsx +90 -0
- package/dist/theme/components/openapi/response-list.tsx +112 -0
- package/dist/theme/components/openapi/schema-viewer.tsx +277 -0
- package/dist/theme/components/openapi/security-badges.tsx +63 -0
- package/dist/theme/components/openapi/spec-utils.ts +122 -0
- package/dist/theme/components/shared/accordion.css +118 -0
- package/dist/theme/components/shared/accordion.stories.tsx +96 -0
- package/dist/theme/components/shared/accordion.tsx +191 -0
- package/dist/theme/components/shared/brand-logo.stories.tsx +49 -0
- package/dist/theme/components/shared/brand-mark.stories.tsx +53 -0
- package/dist/theme/components/shared/browser-window.css +1 -0
- package/dist/theme/components/shared/browser-window.stories.tsx +100 -0
- package/dist/theme/components/shared/browser-window.tsx +2 -0
- package/dist/theme/components/shared/card.stories.tsx +50 -0
- package/dist/theme/components/shared/card.tsx +35 -0
- package/dist/theme/components/shared/ciderpress-logo.tsx +93 -0
- package/dist/theme/components/shared/ciderpress-mark.tsx +77 -0
- package/dist/theme/components/shared/color.css +56 -0
- package/dist/theme/components/shared/color.stories.tsx +47 -0
- package/dist/theme/components/shared/color.tsx +69 -0
- package/dist/theme/components/shared/columns.css +37 -0
- package/dist/theme/components/shared/columns.stories.tsx +91 -0
- package/dist/theme/components/shared/columns.tsx +50 -0
- package/dist/theme/components/shared/desktop-window.css +339 -0
- package/dist/theme/components/shared/desktop-window.tsx +535 -0
- package/dist/theme/components/shared/field.css +158 -0
- package/dist/theme/components/shared/field.stories.tsx +100 -0
- package/dist/theme/components/shared/field.tsx +186 -0
- package/dist/theme/components/shared/frame.css +39 -0
- package/dist/theme/components/shared/frame.stories.tsx +49 -0
- package/dist/theme/components/shared/frame.tsx +76 -0
- package/dist/theme/components/shared/icon.stories.tsx +90 -0
- package/dist/theme/components/shared/icon.tsx +41 -0
- package/dist/theme/components/shared/prompt.css +178 -0
- package/dist/theme/components/shared/prompt.stories.tsx +57 -0
- package/dist/theme/components/shared/prompt.tsx +369 -0
- package/dist/theme/components/shared/resolve-card-icon.ts +28 -0
- package/dist/theme/components/shared/section-card.stories.tsx +51 -0
- package/dist/theme/components/shared/section-card.tsx +44 -0
- package/dist/theme/components/shared/section-grid.stories.tsx +46 -0
- package/dist/theme/components/shared/section-grid.tsx +15 -0
- package/dist/theme/components/shared/status-badge.css +37 -0
- package/dist/theme/components/shared/status-badge.stories.tsx +61 -0
- package/dist/theme/components/shared/status-badge.tsx +74 -0
- package/dist/theme/components/shared/steps.css +88 -0
- package/dist/theme/components/shared/steps.stories.tsx +68 -0
- package/dist/theme/components/shared/steps.tsx +100 -0
- package/dist/theme/components/shared/tech-icon-table.stories.tsx +29 -0
- package/dist/theme/components/shared/tech-icon-table.tsx +71 -0
- package/dist/theme/components/shared/tech-tag.stories.tsx +40 -0
- package/dist/theme/components/shared/tech-tag.tsx +31 -0
- package/dist/theme/components/shared/theme-color-palette.css +80 -0
- package/dist/theme/components/shared/theme-color-palette.stories.tsx +52 -0
- package/dist/theme/components/shared/theme-color-palette.tsx +275 -0
- package/dist/theme/components/shared/tooltip.css +69 -0
- package/dist/theme/components/shared/tooltip.stories.tsx +72 -0
- package/dist/theme/components/shared/tooltip.tsx +77 -0
- package/dist/theme/components/sidebar/framework-picker.css +77 -0
- package/dist/theme/components/sidebar/framework-picker.tsx +78 -0
- package/dist/theme/components/sidebar/sidebar-filter.test.ts +140 -0
- package/dist/theme/components/sidebar/sidebar-filter.ts +79 -0
- package/dist/theme/components/sidebar/sidebar-links.css +102 -0
- package/dist/theme/components/sidebar/sidebar-links.tsx +122 -0
- package/dist/theme/components/sidebar/sidebar-promo.css +42 -0
- package/dist/theme/components/sidebar/sidebar-promo.tsx +52 -0
- package/dist/theme/components/sidebar/sidebar-scope.tsx +151 -0
- package/dist/theme/components/sidebar/sidebar-toggle.css +181 -0
- package/dist/theme/components/sidebar/sidebar-toggle.tsx +127 -0
- package/dist/theme/components/theme-provider.tsx +637 -0
- package/dist/theme/components/workspaces/card.css +151 -0
- package/dist/theme/components/workspaces/card.tsx +166 -0
- package/dist/theme/components/workspaces/grid.tsx +62 -0
- package/dist/theme/css.d.ts +1 -0
- package/dist/theme/env.d.ts +12 -0
- package/dist/theme/fonts/GeistMono-Variable.woff2 +0 -0
- package/dist/theme/fonts/GeistPixel-Square.woff2 +0 -0
- package/dist/theme/fonts/GeistSans-Variable.woff2 +0 -0
- package/dist/theme/hooks/use-ciderpress.ts +61 -0
- package/dist/theme/hooks/use-nav-items.ts +76 -0
- package/dist/theme/icons/index.ts +2 -0
- package/dist/theme/icons/tech-map.ts +228 -0
- package/dist/theme/index.tsx +180 -0
- package/dist/theme/lib/read-social-links.ts +27 -0
- package/dist/theme/lib/route-link.tsx +126 -0
- package/dist/theme/lib/safe-url.test.ts +0 -0
- package/dist/theme/lib/safe-url.ts +68 -0
- package/dist/theme/lib/theme-favicon.ts +125 -0
- package/dist/theme/lib/user-config-stub.ts +12 -0
- package/dist/theme/styles/layers.css +32 -0
- package/dist/theme/styles/overrides/badge.css +26 -0
- package/dist/theme/styles/overrides/content-footer.css +80 -0
- package/dist/theme/styles/overrides/details.css +61 -0
- package/dist/theme/styles/overrides/fonts.css +32 -0
- package/dist/theme/styles/overrides/home-card.css +133 -0
- package/dist/theme/styles/overrides/home.css +243 -0
- package/dist/theme/styles/overrides/rail.css +337 -0
- package/dist/theme/styles/overrides/rspress.css +62 -0
- package/dist/theme/styles/overrides/scrollbar.css +25 -0
- package/dist/theme/styles/overrides/section-card.css +114 -0
- package/dist/theme/styles/overrides/sidebar.css +144 -0
- package/dist/theme/styles/overrides/tokens.css +288 -0
- package/dist/theme/styles/overrides/vscode.css +88 -0
- package/dist/theme/styles/themes/amber.css +545 -0
- package/dist/theme/styles/themes/arcade-fx.css +366 -0
- package/dist/theme/styles/themes/arcade.css +273 -0
- package/dist/theme/styles/themes/grannysmith.css +545 -0
- package/dist/theme/styles/themes/honeycrisp.css +545 -0
- package/dist/theme/styles/themes/midnight.css +273 -0
- package/dist/theme/styles/themes/mulled.css +817 -0
- package/package.json +103 -0
- package/src/theme/components/announcement/announcement-bar.css +103 -0
- package/src/theme/components/announcement/announcement-bar.tsx +173 -0
- package/src/theme/components/ask-ai/ask-ai-button.css +52 -0
- package/src/theme/components/ask-ai/ask-ai-button.tsx +56 -0
- package/src/theme/components/content-footer/content-footer-portal.tsx +70 -0
- package/src/theme/components/content-footer/feedback.css +47 -0
- package/src/theme/components/content-footer/feedback.tsx +96 -0
- package/src/theme/components/content-footer/meta-actions.css +25 -0
- package/src/theme/components/content-footer/meta-actions.tsx +57 -0
- package/src/theme/components/content-footer/page-pager.css +61 -0
- package/src/theme/components/content-footer/page-pager.tsx +110 -0
- package/src/theme/components/edit-source-button.tsx +97 -0
- package/src/theme/components/footer/site-footer.css +179 -0
- package/src/theme/components/footer/site-footer.tsx +115 -0
- package/src/theme/components/home/cta.css +67 -0
- package/src/theme/components/home/cta.tsx +77 -0
- package/src/theme/components/home/feature-card.css +52 -0
- package/src/theme/components/home/feature-card.tsx +131 -0
- package/src/theme/components/home/feature.tsx +79 -0
- package/src/theme/components/home/hero-demo.css +66 -0
- package/src/theme/components/home/hero-demo.tsx +46 -0
- package/src/theme/components/home/hero.css +96 -0
- package/src/theme/components/home/hero.tsx +111 -0
- package/src/theme/components/home/layout.tsx +183 -0
- package/src/theme/components/home/page-rail.css +21 -0
- package/src/theme/components/home/page-rail.tsx +19 -0
- package/src/theme/components/home/split.css +148 -0
- package/src/theme/components/home/split.tsx +120 -0
- package/src/theme/components/home/trust-strip.css +33 -0
- package/src/theme/components/home/trust-strip.tsx +43 -0
- package/src/theme/components/home/workspaces.tsx +71 -0
- package/src/theme/components/nav/branch-tag.css +54 -0
- package/src/theme/components/nav/branch-tag.tsx +101 -0
- package/src/theme/components/nav/ciderpress-doc-layout.tsx +247 -0
- package/src/theme/components/nav/ciderpress-docs-bar.css +505 -0
- package/src/theme/components/nav/ciderpress-docs-bar.tsx +426 -0
- package/src/theme/components/nav/ciderpress-header.css +172 -0
- package/src/theme/components/nav/ciderpress-header.tsx +113 -0
- package/src/theme/components/nav/ciderpress-layout-context.tsx +49 -0
- package/src/theme/components/nav/ciderpress-nav-hamburger.css +193 -0
- package/src/theme/components/nav/ciderpress-nav-hamburger.tsx +112 -0
- package/src/theme/components/nav/ciderpress-nav-menu.css +130 -0
- package/src/theme/components/nav/ciderpress-nav-menu.tsx +372 -0
- package/src/theme/components/nav/ciderpress-nav-search.css +73 -0
- package/src/theme/components/nav/ciderpress-nav-search.tsx +55 -0
- package/src/theme/components/nav/ciderpress-nav-social-links.css +35 -0
- package/src/theme/components/nav/ciderpress-nav-social-links.tsx +87 -0
- package/src/theme/components/nav/floating-branch-indicator.css +106 -0
- package/src/theme/components/nav/floating-branch-indicator.tsx +109 -0
- package/src/theme/components/nav/layout.tsx +268 -0
- package/src/theme/components/nav/mobile-nav-cta.tsx +79 -0
- package/src/theme/components/nav/nav-divider.css +15 -0
- package/src/theme/components/nav/nav-divider.tsx +19 -0
- package/src/theme/components/nav/nav-logo.css +42 -0
- package/src/theme/components/nav/nav-logo.tsx +262 -0
- package/src/theme/components/nav/theme-switcher.css +92 -0
- package/src/theme/components/nav/theme-switcher.tsx +298 -0
- package/src/theme/components/nav/topbar-cta.css +45 -0
- package/src/theme/components/nav/topbar-cta.tsx +39 -0
- package/src/theme/components/nav/variant-toggle.css +70 -0
- package/src/theme/components/nav/variant-toggle.tsx +83 -0
- package/src/theme/components/nav/version-chip.css +31 -0
- package/src/theme/components/nav/version-chip.tsx +45 -0
- package/src/theme/components/nav/vscode-tag.css +32 -0
- package/src/theme/components/nav/vscode-tag.tsx +20 -0
- package/src/theme/components/openapi/code-sample.tsx +341 -0
- package/src/theme/components/openapi/copy-markdown-button.tsx +41 -0
- package/src/theme/components/openapi/icons.tsx +45 -0
- package/src/theme/components/openapi/index.ts +6 -0
- package/src/theme/components/openapi/method-badge.tsx +24 -0
- package/src/theme/components/openapi/openapi.css +665 -0
- package/src/theme/components/openapi/operation.tsx +200 -0
- package/src/theme/components/openapi/overview.tsx +207 -0
- package/src/theme/components/openapi/parameters-table.tsx +149 -0
- package/src/theme/components/openapi/request-body.tsx +90 -0
- package/src/theme/components/openapi/response-list.tsx +112 -0
- package/src/theme/components/openapi/schema-viewer.tsx +277 -0
- package/src/theme/components/openapi/security-badges.tsx +63 -0
- package/src/theme/components/openapi/spec-utils.ts +122 -0
- package/src/theme/components/shared/accordion.css +118 -0
- package/src/theme/components/shared/accordion.stories.tsx +96 -0
- package/src/theme/components/shared/accordion.tsx +191 -0
- package/src/theme/components/shared/brand-logo.stories.tsx +49 -0
- package/src/theme/components/shared/brand-mark.stories.tsx +53 -0
- package/src/theme/components/shared/browser-window.css +1 -0
- package/src/theme/components/shared/browser-window.stories.tsx +100 -0
- package/src/theme/components/shared/browser-window.tsx +2 -0
- package/src/theme/components/shared/card.stories.tsx +50 -0
- package/src/theme/components/shared/card.tsx +35 -0
- package/src/theme/components/shared/ciderpress-logo.tsx +93 -0
- package/src/theme/components/shared/ciderpress-mark.tsx +77 -0
- package/src/theme/components/shared/color.css +56 -0
- package/src/theme/components/shared/color.stories.tsx +47 -0
- package/src/theme/components/shared/color.tsx +69 -0
- package/src/theme/components/shared/columns.css +37 -0
- package/src/theme/components/shared/columns.stories.tsx +91 -0
- package/src/theme/components/shared/columns.tsx +50 -0
- package/src/theme/components/shared/desktop-window.css +339 -0
- package/src/theme/components/shared/desktop-window.tsx +535 -0
- package/src/theme/components/shared/field.css +158 -0
- package/src/theme/components/shared/field.stories.tsx +100 -0
- package/src/theme/components/shared/field.tsx +186 -0
- package/src/theme/components/shared/frame.css +39 -0
- package/src/theme/components/shared/frame.stories.tsx +49 -0
- package/src/theme/components/shared/frame.tsx +76 -0
- package/src/theme/components/shared/icon.stories.tsx +90 -0
- package/src/theme/components/shared/icon.tsx +41 -0
- package/src/theme/components/shared/prompt.css +178 -0
- package/src/theme/components/shared/prompt.stories.tsx +57 -0
- package/src/theme/components/shared/prompt.tsx +369 -0
- package/src/theme/components/shared/resolve-card-icon.ts +28 -0
- package/src/theme/components/shared/section-card.stories.tsx +51 -0
- package/src/theme/components/shared/section-card.tsx +44 -0
- package/src/theme/components/shared/section-grid.stories.tsx +46 -0
- package/src/theme/components/shared/section-grid.tsx +15 -0
- package/src/theme/components/shared/status-badge.css +37 -0
- package/src/theme/components/shared/status-badge.stories.tsx +61 -0
- package/src/theme/components/shared/status-badge.tsx +74 -0
- package/src/theme/components/shared/steps.css +88 -0
- package/src/theme/components/shared/steps.stories.tsx +68 -0
- package/src/theme/components/shared/steps.tsx +100 -0
- package/src/theme/components/shared/tech-icon-table.stories.tsx +29 -0
- package/src/theme/components/shared/tech-icon-table.tsx +71 -0
- package/src/theme/components/shared/tech-tag.stories.tsx +40 -0
- package/src/theme/components/shared/tech-tag.tsx +31 -0
- package/src/theme/components/shared/theme-color-palette.css +80 -0
- package/src/theme/components/shared/theme-color-palette.stories.tsx +52 -0
- package/src/theme/components/shared/theme-color-palette.tsx +275 -0
- package/src/theme/components/shared/tooltip.css +69 -0
- package/src/theme/components/shared/tooltip.stories.tsx +72 -0
- package/src/theme/components/shared/tooltip.tsx +77 -0
- package/src/theme/components/sidebar/framework-picker.css +77 -0
- package/src/theme/components/sidebar/framework-picker.tsx +78 -0
- package/src/theme/components/sidebar/sidebar-filter.test.ts +140 -0
- package/src/theme/components/sidebar/sidebar-filter.ts +79 -0
- package/src/theme/components/sidebar/sidebar-links.css +102 -0
- package/src/theme/components/sidebar/sidebar-links.tsx +122 -0
- package/src/theme/components/sidebar/sidebar-promo.css +42 -0
- package/src/theme/components/sidebar/sidebar-promo.tsx +52 -0
- package/src/theme/components/sidebar/sidebar-scope.tsx +151 -0
- package/src/theme/components/sidebar/sidebar-toggle.css +181 -0
- package/src/theme/components/sidebar/sidebar-toggle.tsx +127 -0
- package/src/theme/components/theme-provider.tsx +637 -0
- package/src/theme/components/workspaces/card.css +151 -0
- package/src/theme/components/workspaces/card.tsx +166 -0
- package/src/theme/components/workspaces/grid.tsx +62 -0
- package/src/theme/css.d.ts +1 -0
- package/src/theme/env.d.ts +12 -0
- package/src/theme/fonts/GeistMono-Variable.woff2 +0 -0
- package/src/theme/fonts/GeistPixel-Square.woff2 +0 -0
- package/src/theme/fonts/GeistSans-Variable.woff2 +0 -0
- package/src/theme/hooks/use-ciderpress.ts +61 -0
- package/src/theme/hooks/use-nav-items.ts +76 -0
- package/src/theme/icons/index.ts +2 -0
- package/src/theme/icons/tech-map.ts +228 -0
- package/src/theme/index.tsx +180 -0
- package/src/theme/lib/read-social-links.ts +27 -0
- package/src/theme/lib/route-link.tsx +126 -0
- package/src/theme/lib/safe-url.test.ts +0 -0
- package/src/theme/lib/safe-url.ts +68 -0
- package/src/theme/lib/theme-favicon.ts +125 -0
- package/src/theme/lib/user-config-stub.ts +12 -0
- package/src/theme/styles/layers.css +32 -0
- package/src/theme/styles/overrides/badge.css +26 -0
- package/src/theme/styles/overrides/content-footer.css +80 -0
- package/src/theme/styles/overrides/details.css +61 -0
- package/src/theme/styles/overrides/fonts.css +32 -0
- package/src/theme/styles/overrides/home-card.css +133 -0
- package/src/theme/styles/overrides/home.css +243 -0
- package/src/theme/styles/overrides/rail.css +337 -0
- package/src/theme/styles/overrides/rspress.css +62 -0
- package/src/theme/styles/overrides/scrollbar.css +25 -0
- package/src/theme/styles/overrides/section-card.css +114 -0
- package/src/theme/styles/overrides/sidebar.css +144 -0
- package/src/theme/styles/overrides/tokens.css +288 -0
- package/src/theme/styles/overrides/vscode.css +88 -0
- package/src/theme/styles/themes/amber.css +545 -0
- package/src/theme/styles/themes/arcade-fx.css +366 -0
- package/src/theme/styles/themes/arcade.css +273 -0
- package/src/theme/styles/themes/grannysmith.css +545 -0
- package/src/theme/styles/themes/honeycrisp.css +545 -0
- package/src/theme/styles/themes/midnight.css +273 -0
- package/src/theme/styles/themes/mulled.css +817 -0
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import { match, P } from 'massaman/match'
|
|
2
|
+
import type React from 'react'
|
|
3
|
+
|
|
4
|
+
import { TECH_ICONS } from '../../icons/index.ts'
|
|
5
|
+
import { Icon } from './icon'
|
|
6
|
+
|
|
7
|
+
export interface TechTagProps {
|
|
8
|
+
readonly name: string
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
/**
|
|
12
|
+
* Technology tag — resolves a tech name to icon + label using the tech map.
|
|
13
|
+
* Falls back to raw name string if not in map.
|
|
14
|
+
*
|
|
15
|
+
* @param props - Props with the technology name to resolve
|
|
16
|
+
* @returns React element with icon and label, or the raw name as fallback
|
|
17
|
+
*/
|
|
18
|
+
export function TechTag({ name }: TechTagProps): React.ReactElement {
|
|
19
|
+
const entry = (TECH_ICONS as Record<string, { readonly icon: string; readonly label: string }>)[
|
|
20
|
+
name
|
|
21
|
+
]
|
|
22
|
+
|
|
23
|
+
return match(entry)
|
|
24
|
+
.with(P.nonNullable, (e) => (
|
|
25
|
+
<span className="cp-tag">
|
|
26
|
+
<Icon icon={e.icon} />
|
|
27
|
+
{` ${e.label}`}
|
|
28
|
+
</span>
|
|
29
|
+
))
|
|
30
|
+
.otherwise(() => <span className="cp-tag">{name}</span>)
|
|
31
|
+
}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* ThemeColorPalette — grouped swatch grid rendered inside an Accordion.
|
|
3
|
+
*/
|
|
4
|
+
|
|
5
|
+
.cp-theme-color-palette {
|
|
6
|
+
display: flex;
|
|
7
|
+
flex-direction: column;
|
|
8
|
+
gap: var(--cp-s-16);
|
|
9
|
+
padding-top: var(--cp-s-4);
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
.cp-theme-color-palette__variants {
|
|
13
|
+
display: inline-flex;
|
|
14
|
+
align-self: flex-start;
|
|
15
|
+
padding: var(--cp-s-4);
|
|
16
|
+
border: 1px solid var(--cp-c-border);
|
|
17
|
+
border-radius: var(--rp-radius);
|
|
18
|
+
background: var(--cp-c-bg);
|
|
19
|
+
gap: var(--cp-s-4);
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
.cp-theme-color-palette__variant {
|
|
23
|
+
display: inline-flex;
|
|
24
|
+
align-items: center;
|
|
25
|
+
gap: var(--cp-s-6);
|
|
26
|
+
padding: var(--cp-s-4) var(--cp-s-10);
|
|
27
|
+
border: none;
|
|
28
|
+
border-radius: var(--rp-radius);
|
|
29
|
+
background: transparent;
|
|
30
|
+
color: var(--cp-c-text-2);
|
|
31
|
+
font-family: var(--cp-font-family-base);
|
|
32
|
+
font-size: var(--cp-fs-color-name);
|
|
33
|
+
font-weight: 600;
|
|
34
|
+
cursor: pointer;
|
|
35
|
+
transition:
|
|
36
|
+
background var(--cp-duration-base),
|
|
37
|
+
color var(--cp-duration-base);
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
.cp-theme-color-palette__variant:hover {
|
|
41
|
+
color: var(--cp-c-text-1);
|
|
42
|
+
background: var(--cp-c-bg-soft);
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
.cp-theme-color-palette__variant:focus-visible {
|
|
46
|
+
outline: var(--cp-size-focus-ring) solid var(--cp-c-brand-1);
|
|
47
|
+
outline-offset: var(--cp-size-focus-ring-offset);
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
.cp-theme-color-palette__variant[data-active='true'] {
|
|
51
|
+
background: var(--cp-c-brand-soft);
|
|
52
|
+
color: var(--cp-c-brand-1);
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
.cp-theme-color-palette__variant svg {
|
|
56
|
+
display: block;
|
|
57
|
+
width: 14px;
|
|
58
|
+
height: 14px;
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
.cp-theme-color-palette__group {
|
|
62
|
+
display: flex;
|
|
63
|
+
flex-direction: column;
|
|
64
|
+
gap: var(--cp-s-8);
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
.cp-theme-color-palette__heading {
|
|
68
|
+
margin: 0;
|
|
69
|
+
font-size: var(--cp-fs-color-name);
|
|
70
|
+
font-weight: 600;
|
|
71
|
+
text-transform: uppercase;
|
|
72
|
+
letter-spacing: 0.06em;
|
|
73
|
+
color: var(--cp-c-text-3);
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
.cp-theme-color-palette__grid {
|
|
77
|
+
display: grid;
|
|
78
|
+
grid-template-columns: repeat(auto-fit, minmax(180px, 1fr));
|
|
79
|
+
gap: var(--cp-s-8);
|
|
80
|
+
}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import type { Story } from '@ladle/react'
|
|
2
|
+
|
|
3
|
+
import { ThemeColorPalette } from './theme-color-palette.tsx'
|
|
4
|
+
|
|
5
|
+
const meta = {
|
|
6
|
+
title: 'Data Display / Theme Color Palette',
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
export default meta
|
|
10
|
+
|
|
11
|
+
/**
|
|
12
|
+
* Single palette — collapsed by default.
|
|
13
|
+
*
|
|
14
|
+
* @returns Mulled dark palette inside the accordion
|
|
15
|
+
*/
|
|
16
|
+
// oxlint-disable-next-line func-style -- Ladle stories use `export const`
|
|
17
|
+
export const Default: Story = () => <ThemeColorPalette theme="mulled" />
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* Palette pinned open on mount.
|
|
21
|
+
*
|
|
22
|
+
* @returns Honeycrisp dark palette, expanded
|
|
23
|
+
*/
|
|
24
|
+
// oxlint-disable-next-line func-style -- Ladle stories use `export const`
|
|
25
|
+
export const InitiallyOpen: Story = () => <ThemeColorPalette theme="honeycrisp" defaultOpen />
|
|
26
|
+
|
|
27
|
+
/**
|
|
28
|
+
* Explicit variant — light token tree for a multi-variant theme.
|
|
29
|
+
*
|
|
30
|
+
* @returns Honeycrisp light palette
|
|
31
|
+
*/
|
|
32
|
+
// oxlint-disable-next-line func-style -- Ladle stories use `export const`
|
|
33
|
+
export const LightVariant: Story = () => (
|
|
34
|
+
<ThemeColorPalette theme="honeycrisp" variant="light" defaultOpen />
|
|
35
|
+
)
|
|
36
|
+
|
|
37
|
+
/**
|
|
38
|
+
* All six built-in themes stacked, default variants, all expanded.
|
|
39
|
+
*
|
|
40
|
+
* @returns Stack of palette accordions
|
|
41
|
+
*/
|
|
42
|
+
// oxlint-disable-next-line func-style -- Ladle stories use `export const`
|
|
43
|
+
export const AllBuiltIns: Story = () => (
|
|
44
|
+
<div style={{ display: 'flex', flexDirection: 'column', gap: 8 }}>
|
|
45
|
+
<ThemeColorPalette theme="mulled" defaultOpen />
|
|
46
|
+
<ThemeColorPalette theme="honeycrisp" />
|
|
47
|
+
<ThemeColorPalette theme="grannysmith" />
|
|
48
|
+
<ThemeColorPalette theme="amber" />
|
|
49
|
+
<ThemeColorPalette theme="midnight" />
|
|
50
|
+
<ThemeColorPalette theme="arcade" />
|
|
51
|
+
</div>
|
|
52
|
+
)
|
|
@@ -0,0 +1,275 @@
|
|
|
1
|
+
import {
|
|
2
|
+
BUILT_IN_THEMES,
|
|
3
|
+
isBuiltInTheme,
|
|
4
|
+
resolveDefaultVariant,
|
|
5
|
+
resolveThemeVariants,
|
|
6
|
+
} from '@ciderpress/theme'
|
|
7
|
+
import type { BuiltInThemeName, ThemeVariant } from '@ciderpress/theme'
|
|
8
|
+
import { match, P } from 'massaman/match'
|
|
9
|
+
import { useState } from 'react'
|
|
10
|
+
import type React from 'react'
|
|
11
|
+
|
|
12
|
+
import { Accordion } from './accordion.tsx'
|
|
13
|
+
import { Color } from './color.tsx'
|
|
14
|
+
import { Icon } from './icon.tsx'
|
|
15
|
+
|
|
16
|
+
export interface ThemeColorPaletteProps {
|
|
17
|
+
/**
|
|
18
|
+
* Built-in theme to render. Accepts any name in `BUILT_IN_THEMES`.
|
|
19
|
+
*/
|
|
20
|
+
readonly theme: BuiltInThemeName
|
|
21
|
+
/**
|
|
22
|
+
* Initial variant to render. Defaults to the theme's `defaultVariant`.
|
|
23
|
+
* If the requested variant is not declared by the theme, falls back to
|
|
24
|
+
* the default.
|
|
25
|
+
*/
|
|
26
|
+
readonly variant?: ThemeVariant
|
|
27
|
+
/**
|
|
28
|
+
* Title shown on the accordion trigger. Defaults to the theme name.
|
|
29
|
+
*/
|
|
30
|
+
readonly title?: string
|
|
31
|
+
/**
|
|
32
|
+
* Description shown below the trigger title.
|
|
33
|
+
*/
|
|
34
|
+
readonly description?: string
|
|
35
|
+
/**
|
|
36
|
+
* Whether the palette accordion starts expanded.
|
|
37
|
+
*/
|
|
38
|
+
readonly defaultOpen?: boolean
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
interface ColorEntry {
|
|
42
|
+
readonly name: string
|
|
43
|
+
readonly value: string
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
interface ColorGroup {
|
|
47
|
+
readonly heading: string
|
|
48
|
+
readonly colors: readonly ColorEntry[]
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
const VARIANT_LABEL: Readonly<Record<ThemeVariant, string>> = Object.freeze({
|
|
52
|
+
dark: 'Dark',
|
|
53
|
+
light: 'Light',
|
|
54
|
+
})
|
|
55
|
+
|
|
56
|
+
const VARIANT_ICON: Readonly<Record<ThemeVariant, string>> = Object.freeze({
|
|
57
|
+
dark: 'pixelarticons:moon',
|
|
58
|
+
light: 'pixelarticons:sun',
|
|
59
|
+
})
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* Collapsible palette display for a built-in theme. Renders every brand,
|
|
63
|
+
* surface, text, border, and semantic color token as a copy-on-click
|
|
64
|
+
* {@link Color} swatch, grouped under a single {@link Accordion}. When the
|
|
65
|
+
* theme declares both `dark` and `light` variants, a sun/moon segmented
|
|
66
|
+
* control inside the panel switches between them in place.
|
|
67
|
+
*
|
|
68
|
+
* @param props - Theme palette configuration
|
|
69
|
+
* @returns React element with the collapsible palette
|
|
70
|
+
*/
|
|
71
|
+
export function ThemeColorPalette({
|
|
72
|
+
theme,
|
|
73
|
+
variant,
|
|
74
|
+
title,
|
|
75
|
+
description,
|
|
76
|
+
defaultOpen = false,
|
|
77
|
+
}: ThemeColorPaletteProps): React.ReactElement | null {
|
|
78
|
+
const themeEntry = match(isBuiltInTheme(theme))
|
|
79
|
+
.with(true, () => BUILT_IN_THEMES[theme])
|
|
80
|
+
.otherwise(() => null)
|
|
81
|
+
if (themeEntry === null) {
|
|
82
|
+
return null
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
const variants = resolveThemeVariants(theme)
|
|
86
|
+
const initialVariant = resolveVariant(theme, variant)
|
|
87
|
+
const [activeVariant, setActiveVariant] = useState<ThemeVariant>(initialVariant)
|
|
88
|
+
|
|
89
|
+
const tokens = themeEntry.variants[activeVariant]
|
|
90
|
+
if (tokens === undefined) {
|
|
91
|
+
return null
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
const groups = buildGroups(tokens)
|
|
95
|
+
const headingText = title ?? theme
|
|
96
|
+
const subtitle =
|
|
97
|
+
description ?? `Brand, surface, text, border, and semantic tokens for the ${theme} theme.`
|
|
98
|
+
|
|
99
|
+
const showToggle = variants.length > 1
|
|
100
|
+
|
|
101
|
+
return (
|
|
102
|
+
<Accordion
|
|
103
|
+
id={`theme-palette-${theme}`}
|
|
104
|
+
title={headingText}
|
|
105
|
+
description={subtitle}
|
|
106
|
+
icon="pixelarticons:eyedropper"
|
|
107
|
+
defaultOpen={defaultOpen}
|
|
108
|
+
>
|
|
109
|
+
<div className="cp-theme-color-palette">
|
|
110
|
+
{match(showToggle)
|
|
111
|
+
.with(true, () => (
|
|
112
|
+
<div
|
|
113
|
+
className="cp-theme-color-palette__variants"
|
|
114
|
+
role="radiogroup"
|
|
115
|
+
aria-label="Variant"
|
|
116
|
+
>
|
|
117
|
+
{variants.map((v) => {
|
|
118
|
+
const selected = v === activeVariant
|
|
119
|
+
return (
|
|
120
|
+
<button
|
|
121
|
+
key={v}
|
|
122
|
+
type="button"
|
|
123
|
+
role="radio"
|
|
124
|
+
aria-checked={selected}
|
|
125
|
+
className="cp-theme-color-palette__variant"
|
|
126
|
+
data-active={selected}
|
|
127
|
+
onClick={() => setActiveVariant(v)}
|
|
128
|
+
>
|
|
129
|
+
<Icon icon={VARIANT_ICON[v]} />
|
|
130
|
+
<span>{VARIANT_LABEL[v]}</span>
|
|
131
|
+
</button>
|
|
132
|
+
)
|
|
133
|
+
})}
|
|
134
|
+
</div>
|
|
135
|
+
))
|
|
136
|
+
.otherwise(() => null)}
|
|
137
|
+
{groups.map((group) => (
|
|
138
|
+
<section key={group.heading} className="cp-theme-color-palette__group">
|
|
139
|
+
<h4 className="cp-theme-color-palette__heading">{group.heading}</h4>
|
|
140
|
+
<div className="cp-theme-color-palette__grid">
|
|
141
|
+
{group.colors.map((c) => (
|
|
142
|
+
<Color key={c.name} value={c.value} name={c.name} />
|
|
143
|
+
))}
|
|
144
|
+
</div>
|
|
145
|
+
</section>
|
|
146
|
+
))}
|
|
147
|
+
</div>
|
|
148
|
+
</Accordion>
|
|
149
|
+
)
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
/**
|
|
153
|
+
* Resolve a variant for the requested theme — falls back to the theme's
|
|
154
|
+
* default when the requested variant is unavailable.
|
|
155
|
+
*
|
|
156
|
+
* @private
|
|
157
|
+
* @param theme - Built-in theme identifier
|
|
158
|
+
* @param requested - Variant supplied by the caller (optional)
|
|
159
|
+
* @returns Variant guaranteed to exist on the theme
|
|
160
|
+
*/
|
|
161
|
+
function resolveVariant(
|
|
162
|
+
theme: BuiltInThemeName,
|
|
163
|
+
requested: ThemeVariant | undefined
|
|
164
|
+
): ThemeVariant {
|
|
165
|
+
const fallback = resolveDefaultVariant(theme)
|
|
166
|
+
return match(requested)
|
|
167
|
+
.with(P.nullish, () => fallback)
|
|
168
|
+
.with(P.string, (v) => {
|
|
169
|
+
const exists = BUILT_IN_THEMES[theme].variants[v] !== undefined
|
|
170
|
+
return match(exists)
|
|
171
|
+
.with(true, () => v)
|
|
172
|
+
.otherwise(() => fallback)
|
|
173
|
+
})
|
|
174
|
+
.exhaustive()
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
/**
|
|
178
|
+
* Project a parsed token tree into the grouped layout rendered by the
|
|
179
|
+
* palette accordion.
|
|
180
|
+
*
|
|
181
|
+
* @private
|
|
182
|
+
* @param tokens - Token tree from `BUILT_IN_THEMES[theme].variants[variant]`
|
|
183
|
+
* @returns Ordered list of groups suitable for the swatch grid
|
|
184
|
+
*/
|
|
185
|
+
function buildGroups(tokens: {
|
|
186
|
+
readonly colors: {
|
|
187
|
+
readonly brand: {
|
|
188
|
+
readonly primary: string
|
|
189
|
+
readonly hover: string
|
|
190
|
+
readonly active: string
|
|
191
|
+
readonly soft: string
|
|
192
|
+
readonly fg: string
|
|
193
|
+
readonly light: string
|
|
194
|
+
readonly lighter: string
|
|
195
|
+
}
|
|
196
|
+
readonly surface: {
|
|
197
|
+
readonly bg: string
|
|
198
|
+
readonly bgAlt: string
|
|
199
|
+
readonly bgElv: string
|
|
200
|
+
readonly bgSoft: string
|
|
201
|
+
readonly homeBg: string
|
|
202
|
+
readonly gutter: string
|
|
203
|
+
readonly codeBlockBg: string
|
|
204
|
+
}
|
|
205
|
+
readonly text: {
|
|
206
|
+
readonly text1: string
|
|
207
|
+
readonly text2: string
|
|
208
|
+
readonly text3: string
|
|
209
|
+
}
|
|
210
|
+
readonly border: {
|
|
211
|
+
readonly border: string
|
|
212
|
+
readonly divider: string
|
|
213
|
+
}
|
|
214
|
+
readonly semantic: {
|
|
215
|
+
readonly success: string
|
|
216
|
+
readonly error: string
|
|
217
|
+
readonly warn: string
|
|
218
|
+
readonly info: string
|
|
219
|
+
readonly muted: string
|
|
220
|
+
}
|
|
221
|
+
}
|
|
222
|
+
}): readonly ColorGroup[] {
|
|
223
|
+
const { brand, surface, text, border, semantic } = tokens.colors
|
|
224
|
+
return [
|
|
225
|
+
{
|
|
226
|
+
heading: 'Brand',
|
|
227
|
+
colors: [
|
|
228
|
+
{ name: 'primary', value: brand.primary },
|
|
229
|
+
{ name: 'hover', value: brand.hover },
|
|
230
|
+
{ name: 'active', value: brand.active },
|
|
231
|
+
{ name: 'soft', value: brand.soft },
|
|
232
|
+
{ name: 'fg (on-brand)', value: brand.fg },
|
|
233
|
+
{ name: 'light', value: brand.light },
|
|
234
|
+
{ name: 'lighter', value: brand.lighter },
|
|
235
|
+
],
|
|
236
|
+
},
|
|
237
|
+
{
|
|
238
|
+
heading: 'Surface',
|
|
239
|
+
colors: [
|
|
240
|
+
{ name: 'bg', value: surface.bg },
|
|
241
|
+
{ name: 'bgAlt', value: surface.bgAlt },
|
|
242
|
+
{ name: 'bgElv', value: surface.bgElv },
|
|
243
|
+
{ name: 'bgSoft', value: surface.bgSoft },
|
|
244
|
+
{ name: 'homeBg', value: surface.homeBg },
|
|
245
|
+
{ name: 'gutter', value: surface.gutter },
|
|
246
|
+
{ name: 'codeBlockBg', value: surface.codeBlockBg },
|
|
247
|
+
],
|
|
248
|
+
},
|
|
249
|
+
{
|
|
250
|
+
heading: 'Text',
|
|
251
|
+
colors: [
|
|
252
|
+
{ name: 'text1', value: text.text1 },
|
|
253
|
+
{ name: 'text2', value: text.text2 },
|
|
254
|
+
{ name: 'text3', value: text.text3 },
|
|
255
|
+
],
|
|
256
|
+
},
|
|
257
|
+
{
|
|
258
|
+
heading: 'Border',
|
|
259
|
+
colors: [
|
|
260
|
+
{ name: 'border', value: border.border },
|
|
261
|
+
{ name: 'divider', value: border.divider },
|
|
262
|
+
],
|
|
263
|
+
},
|
|
264
|
+
{
|
|
265
|
+
heading: 'Semantic',
|
|
266
|
+
colors: [
|
|
267
|
+
{ name: 'success', value: semantic.success },
|
|
268
|
+
{ name: 'error', value: semantic.error },
|
|
269
|
+
{ name: 'warn', value: semantic.warn },
|
|
270
|
+
{ name: 'info', value: semantic.info },
|
|
271
|
+
{ name: 'muted', value: semantic.muted },
|
|
272
|
+
],
|
|
273
|
+
},
|
|
274
|
+
]
|
|
275
|
+
}
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Tooltip — hover-to-reveal definitions.
|
|
3
|
+
*/
|
|
4
|
+
|
|
5
|
+
.cp-tooltip__trigger {
|
|
6
|
+
display: inline;
|
|
7
|
+
padding: 0;
|
|
8
|
+
border: none;
|
|
9
|
+
background: none;
|
|
10
|
+
color: inherit;
|
|
11
|
+
font: inherit;
|
|
12
|
+
cursor: help;
|
|
13
|
+
text-decoration: underline;
|
|
14
|
+
text-decoration-style: dotted;
|
|
15
|
+
text-decoration-color: var(--cp-c-text-3);
|
|
16
|
+
text-underline-offset: var(--cp-s-3);
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
.cp-tooltip__trigger:focus-visible {
|
|
20
|
+
outline: var(--cp-size-focus-ring) solid var(--cp-c-brand-1);
|
|
21
|
+
outline-offset: var(--cp-size-focus-ring-offset);
|
|
22
|
+
border-radius: var(--cp-radius-xs);
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
.cp-tooltip__overlay {
|
|
26
|
+
max-width: var(--cp-size-tooltip-max);
|
|
27
|
+
padding: var(--cp-s-10) var(--cp-s-14);
|
|
28
|
+
background: var(--cp-c-bg-elv);
|
|
29
|
+
border: 1px solid var(--cp-c-border);
|
|
30
|
+
border-radius: var(--rp-radius-large);
|
|
31
|
+
box-shadow: var(--cp-shadow-tooltip);
|
|
32
|
+
font-size: var(--cp-fs-tooltip);
|
|
33
|
+
line-height: var(--cp-lh-base);
|
|
34
|
+
color: var(--cp-c-text-1);
|
|
35
|
+
z-index: var(--cp-z-tooltip);
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
.cp-tooltip__arrow svg {
|
|
39
|
+
display: block;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
.cp-tooltip__body {
|
|
43
|
+
display: flex;
|
|
44
|
+
flex-direction: column;
|
|
45
|
+
gap: var(--cp-s-4);
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
.cp-tooltip__headline {
|
|
49
|
+
font-size: var(--cp-fs-tooltip-headline);
|
|
50
|
+
font-weight: 600;
|
|
51
|
+
color: var(--cp-c-text-1);
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
.cp-tooltip__tip {
|
|
55
|
+
color: var(--cp-c-text-2);
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
.cp-tooltip__cta {
|
|
59
|
+
display: inline-block;
|
|
60
|
+
margin-top: var(--cp-s-4);
|
|
61
|
+
font-size: var(--cp-fs-tooltip-cta);
|
|
62
|
+
font-weight: 500;
|
|
63
|
+
color: var(--cp-c-brand-1);
|
|
64
|
+
text-decoration: none;
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
.cp-tooltip__cta:hover {
|
|
68
|
+
text-decoration: underline;
|
|
69
|
+
}
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
import type { Story } from '@ladle/react'
|
|
2
|
+
|
|
3
|
+
import { Tooltip } from './tooltip.tsx'
|
|
4
|
+
|
|
5
|
+
const meta = {
|
|
6
|
+
title: 'Disclosure / Tooltip',
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
export default meta
|
|
10
|
+
|
|
11
|
+
/**
|
|
12
|
+
* Bare tooltip — hover the trigger to reveal a tip with no headline
|
|
13
|
+
* or call to action.
|
|
14
|
+
*
|
|
15
|
+
* @returns Sentence with an inline tooltip trigger
|
|
16
|
+
*/
|
|
17
|
+
// oxlint-disable-next-line func-style -- Ladle stories use `export const`
|
|
18
|
+
export const Default: Story = () => (
|
|
19
|
+
<p style={{ lineHeight: 2 }}>
|
|
20
|
+
Hover{' '}
|
|
21
|
+
<Tooltip tip="A small package of design tokens applied as CSS custom properties to <html>.">
|
|
22
|
+
<span style={{ borderBottom: '1px dashed var(--cp-c-brand-1)', cursor: 'help' }}>
|
|
23
|
+
the theme cascade
|
|
24
|
+
</span>
|
|
25
|
+
</Tooltip>{' '}
|
|
26
|
+
to see the explanation pop in.
|
|
27
|
+
</p>
|
|
28
|
+
)
|
|
29
|
+
|
|
30
|
+
/**
|
|
31
|
+
* Tooltip with a bold headline above the tip.
|
|
32
|
+
*
|
|
33
|
+
* @returns Tooltip with headline + tip
|
|
34
|
+
*/
|
|
35
|
+
// oxlint-disable-next-line func-style -- Ladle stories use `export const`
|
|
36
|
+
export const WithHeadline: Story = () => (
|
|
37
|
+
<p style={{ lineHeight: 2 }}>
|
|
38
|
+
Read about the{' '}
|
|
39
|
+
<Tooltip
|
|
40
|
+
headline="Sync engine"
|
|
41
|
+
tip="Watches your source markdown and mirrors structure into Rspress's expected layout."
|
|
42
|
+
>
|
|
43
|
+
<span style={{ borderBottom: '1px dashed var(--cp-c-brand-1)', cursor: 'help' }}>
|
|
44
|
+
sync engine
|
|
45
|
+
</span>
|
|
46
|
+
</Tooltip>{' '}
|
|
47
|
+
in the architecture docs.
|
|
48
|
+
</p>
|
|
49
|
+
)
|
|
50
|
+
|
|
51
|
+
/**
|
|
52
|
+
* Tooltip with a call-to-action link in the overlay — routed through
|
|
53
|
+
* the stubbed Rspress `<Link>` so external/internal handling matches
|
|
54
|
+
* production.
|
|
55
|
+
*
|
|
56
|
+
* @returns Tooltip with headline, tip, and CTA
|
|
57
|
+
*/
|
|
58
|
+
// oxlint-disable-next-line func-style -- Ladle stories use `export const`
|
|
59
|
+
export const WithCta: Story = () => (
|
|
60
|
+
<p style={{ lineHeight: 2 }}>
|
|
61
|
+
Try the{' '}
|
|
62
|
+
<Tooltip
|
|
63
|
+
headline="Mulled palette"
|
|
64
|
+
tip="The default Ciderpress palette — deep red brand on near-black surfaces."
|
|
65
|
+
cta="See the full palette →"
|
|
66
|
+
href="/guides/themes/mulled"
|
|
67
|
+
>
|
|
68
|
+
<span style={{ borderBottom: '1px dashed var(--cp-c-brand-1)', cursor: 'help' }}>Mulled</span>
|
|
69
|
+
</Tooltip>{' '}
|
|
70
|
+
palette.
|
|
71
|
+
</p>
|
|
72
|
+
)
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
import { match, P } from 'massaman/match'
|
|
2
|
+
import type React from 'react'
|
|
3
|
+
import { Button, OverlayArrow, Tooltip as AriaTooltip, TooltipTrigger } from 'react-aria-components'
|
|
4
|
+
|
|
5
|
+
import { RouteLink } from '../../lib/route-link.tsx'
|
|
6
|
+
import { safeUrl } from '../../lib/safe-url.ts'
|
|
7
|
+
|
|
8
|
+
export interface TooltipProps {
|
|
9
|
+
/**
|
|
10
|
+
* Main tooltip text displayed on hover.
|
|
11
|
+
*/
|
|
12
|
+
readonly tip: string
|
|
13
|
+
/**
|
|
14
|
+
* Optional bold headline displayed above the tip.
|
|
15
|
+
*/
|
|
16
|
+
readonly headline?: string
|
|
17
|
+
/**
|
|
18
|
+
* Optional call-to-action link label.
|
|
19
|
+
*/
|
|
20
|
+
readonly cta?: string
|
|
21
|
+
/**
|
|
22
|
+
* URL for the call-to-action link. Required when `cta` is provided.
|
|
23
|
+
*/
|
|
24
|
+
readonly href?: string
|
|
25
|
+
/**
|
|
26
|
+
* Inline content that triggers the tooltip on hover.
|
|
27
|
+
*/
|
|
28
|
+
readonly children: React.ReactNode
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
/**
|
|
32
|
+
* Hover-to-reveal tooltip for definitions, glossary terms,
|
|
33
|
+
* and inline contextual help.
|
|
34
|
+
*
|
|
35
|
+
* Built on react-aria-components for full accessibility,
|
|
36
|
+
* keyboard support, and automatic repositioning.
|
|
37
|
+
*
|
|
38
|
+
* @param props - Tooltip configuration with tip text and optional CTA
|
|
39
|
+
* @returns React element with tooltip trigger and overlay
|
|
40
|
+
*/
|
|
41
|
+
export function Tooltip({ tip, headline, cta, href, children }: TooltipProps): React.ReactElement {
|
|
42
|
+
const headlineEl = match(headline)
|
|
43
|
+
.with(P.nonNullable, (h) => <strong className="cp-tooltip__headline">{h}</strong>)
|
|
44
|
+
.otherwise(() => null)
|
|
45
|
+
|
|
46
|
+
const ctaEl = match({ cta, href })
|
|
47
|
+
.with({ cta: P.nonNullable, href: P.nonNullable }, ({ cta: label, href: url }) => {
|
|
48
|
+
const safeHref = safeUrl(url)
|
|
49
|
+
if (safeHref === null) {
|
|
50
|
+
return null
|
|
51
|
+
}
|
|
52
|
+
return (
|
|
53
|
+
<RouteLink className="cp-tooltip__cta" href={safeHref}>
|
|
54
|
+
{label}
|
|
55
|
+
</RouteLink>
|
|
56
|
+
)
|
|
57
|
+
})
|
|
58
|
+
.otherwise(() => null)
|
|
59
|
+
|
|
60
|
+
return (
|
|
61
|
+
<TooltipTrigger delay={300}>
|
|
62
|
+
<Button className="cp-tooltip__trigger">{children}</Button>
|
|
63
|
+
<AriaTooltip className="cp-tooltip__overlay" offset={8}>
|
|
64
|
+
<OverlayArrow className="cp-tooltip__arrow">
|
|
65
|
+
<svg width="12" height="6" viewBox="0 0 12 6">
|
|
66
|
+
<path d="M0 6L6 0L12 6" fill="var(--cp-c-bg-elv)" stroke="var(--cp-c-border)" />
|
|
67
|
+
</svg>
|
|
68
|
+
</OverlayArrow>
|
|
69
|
+
<div className="cp-tooltip__body">
|
|
70
|
+
{headlineEl}
|
|
71
|
+
<span className="cp-tooltip__tip">{tip}</span>
|
|
72
|
+
{ctaEl}
|
|
73
|
+
</div>
|
|
74
|
+
</AriaTooltip>
|
|
75
|
+
</TooltipTrigger>
|
|
76
|
+
)
|
|
77
|
+
}
|