diff --git a/.prettierignore b/.prettierignore
index a796dbf309..e4fb024c62 100644
--- a/.prettierignore
+++ b/.prettierignore
@@ -1,7 +1,7 @@
.yarn
dist
microsite
-microsite-canon
+microsite-canon/.next
coverage
*.hbs
templates
diff --git a/microsite-canon/app/globals.css b/microsite-canon/app/globals.css
index ce79569b3d..adeee8bc02 100644
--- a/microsite-canon/app/globals.css
+++ b/microsite-canon/app/globals.css
@@ -9,3 +9,29 @@ iframe {
border: none;
width: 100%;
}
+
+pre {
+ border-radius: 0.5rem;
+ border: 1px solid var(--canon-border-base);
+ position: relative;
+ padding: 16px 20px;
+ background: transparent;
+ overflow-x: auto;
+ font-family: var(--canon-font-monospace);
+}
+
+pre code span {
+ font-family: var(--canon-font-monospace);
+ font-size: 0.875rem;
+ line-height: 1.7;
+}
+
+[data-theme='dark'] .shiki,
+[data-theme='dark'] .shiki span {
+ color: var(--shiki-dark) !important;
+ background-color: var(--shiki-dark-bg) !important;
+ /* Optional, if you also want font styles */
+ font-style: var(--shiki-dark-font-style) !important;
+ font-weight: var(--shiki-dark-font-weight) !important;
+ text-decoration: var(--shiki-dark-text-decoration) !important;
+}
diff --git a/microsite-canon/content/layout.mdx b/microsite-canon/content/layout.mdx
index 4cbb050c4c..7fdbcbfc57 100644
--- a/microsite-canon/content/layout.mdx
+++ b/microsite-canon/content/layout.mdx
@@ -19,6 +19,16 @@ that will be consistent with the rest of your Backstage instance. These
components are opinionated and use TypeScript to ensure that the props you
provide are the ones coming from the theme.
+```tsx title=boom
+
+ Hello World
+
+ Project 1
+ Project 2
+
+
+```
+
## Layout Helpers
diff --git a/microsite-canon/mdx-components.tsx b/microsite-canon/mdx-components.tsx
index 8b086903bd..21479dc4e6 100644
--- a/microsite-canon/mdx-components.tsx
+++ b/microsite-canon/mdx-components.tsx
@@ -1,6 +1,9 @@
import type { MDXComponents } from 'mdx/types';
import Image, { ImageProps } from 'next/image';
-import { ReactNode } from 'react';
+import { ReactNode, ReactElement } from 'react';
+import type { BundledLanguage } from 'shiki';
+import { codeToHtml } from 'shiki';
+import React from 'react';
// This file allows you to provide custom React components
// to be used in MDX files. You can import and use any
@@ -43,6 +46,10 @@ export function useMDXComponents(components: MDXComponents): MDXComponents {
{children as ReactNode}
),
+ pre: ({ children }) => {
+ console.log(children);
+ return {children as ReactNode};
+ },
img: props => (
;
+}
diff --git a/microsite-canon/package.json b/microsite-canon/package.json
index 7dd094089c..963f219ddf 100644
--- a/microsite-canon/package.json
+++ b/microsite-canon/package.json
@@ -29,6 +29,7 @@
"@types/react-dom": "^19",
"eslint": "^9",
"eslint-config-next": "15.1.3",
+ "shiki": "^1.24.4",
"typescript": "^5"
}
}
diff --git a/microsite-canon/yarn.lock b/microsite-canon/yarn.lock
index 63ca2f4af6..2af0e436e7 100644
--- a/microsite-canon/yarn.lock
+++ b/microsite-canon/yarn.lock
@@ -582,6 +582,58 @@ __metadata:
languageName: node
linkType: hard
+"@shikijs/core@npm:1.24.4":
+ version: 1.24.4
+ resolution: "@shikijs/core@npm:1.24.4"
+ dependencies:
+ "@shikijs/engine-javascript": 1.24.4
+ "@shikijs/engine-oniguruma": 1.24.4
+ "@shikijs/types": 1.24.4
+ "@shikijs/vscode-textmate": ^9.3.1
+ "@types/hast": ^3.0.4
+ hast-util-to-html: ^9.0.4
+ checksum: 33dfa6b183def624812f5d736ae09ebb6e9880839278ddef8498312064d7724316e4d8bd26273c8cad55aa5218d422ddc76f8baf3cf90a993ca8f62761a89db8
+ languageName: node
+ linkType: hard
+
+"@shikijs/engine-javascript@npm:1.24.4":
+ version: 1.24.4
+ resolution: "@shikijs/engine-javascript@npm:1.24.4"
+ dependencies:
+ "@shikijs/types": 1.24.4
+ "@shikijs/vscode-textmate": ^9.3.1
+ oniguruma-to-es: 0.8.1
+ checksum: 528be972df1386bfcd8364d3875db91e561ad480b18bd5dbe36388365eac2856b6564441a4da312d31a579d9267272fa7d13ea54b4d583961492cef831685037
+ languageName: node
+ linkType: hard
+
+"@shikijs/engine-oniguruma@npm:1.24.4":
+ version: 1.24.4
+ resolution: "@shikijs/engine-oniguruma@npm:1.24.4"
+ dependencies:
+ "@shikijs/types": 1.24.4
+ "@shikijs/vscode-textmate": ^9.3.1
+ checksum: 05cd0d82cad1ac9e93aedbd63859feed5d98c14144c263453ece2359c56d26c1e88750fcfccf6a62df716a6fe2b4b6eecf076573b383292cefd180afd639d312
+ languageName: node
+ linkType: hard
+
+"@shikijs/types@npm:1.24.4":
+ version: 1.24.4
+ resolution: "@shikijs/types@npm:1.24.4"
+ dependencies:
+ "@shikijs/vscode-textmate": ^9.3.1
+ "@types/hast": ^3.0.4
+ checksum: 6af64511df37312329f1cc88eb0d5be688cb302be220edaf3cbe332d27b03c16e445655ad7a57a809939dca2f4ac56be45fcf048ed0fef6bfdea8e73f3aa28ac
+ languageName: node
+ linkType: hard
+
+"@shikijs/vscode-textmate@npm:^9.3.1":
+ version: 9.3.1
+ resolution: "@shikijs/vscode-textmate@npm:9.3.1"
+ checksum: 42fc9cba3619eee72d8863def0cb128ce463145cf4b2665f00249481ecbed39dd8e2726e25ade684ab2a020705eebf4d28646121f8bb9aadb350a307a7c04f94
+ languageName: node
+ linkType: hard
+
"@swc/counter@npm:0.1.3":
version: 0.1.3
resolution: "@swc/counter@npm:0.1.3"
@@ -632,7 +684,7 @@ __metadata:
languageName: node
linkType: hard
-"@types/hast@npm:^3.0.0":
+"@types/hast@npm:^3.0.0, @types/hast@npm:^3.0.4":
version: 3.0.4
resolution: "@types/hast@npm:3.0.4"
dependencies:
@@ -1149,6 +1201,7 @@ __metadata:
next: 15.1.3
react: ^19.0.0
react-dom: ^19.0.0
+ shiki: ^1.24.4
typescript: ^5
languageName: unknown
linkType: soft
@@ -1422,6 +1475,13 @@ __metadata:
languageName: node
linkType: hard
+"emoji-regex-xs@npm:^1.0.0":
+ version: 1.0.0
+ resolution: "emoji-regex-xs@npm:1.0.0"
+ checksum: c33be159da769836f83281f2802d90169093ebf3c2c1643d6801d891c53beac5ef785fd8279f9b02fa6dc6c47c367818e076949f1e13bd1b3f921b416de4cbea
+ languageName: node
+ linkType: hard
+
"emoji-regex@npm:^9.2.2":
version: 9.2.2
resolution: "emoji-regex@npm:9.2.2"
@@ -2270,6 +2330,25 @@ __metadata:
languageName: node
linkType: hard
+"hast-util-to-html@npm:^9.0.4":
+ version: 9.0.4
+ resolution: "hast-util-to-html@npm:9.0.4"
+ dependencies:
+ "@types/hast": ^3.0.0
+ "@types/unist": ^3.0.0
+ ccount: ^2.0.0
+ comma-separated-tokens: ^2.0.0
+ hast-util-whitespace: ^3.0.0
+ html-void-elements: ^3.0.0
+ mdast-util-to-hast: ^13.0.0
+ property-information: ^6.0.0
+ space-separated-tokens: ^2.0.0
+ stringify-entities: ^4.0.0
+ zwitch: ^2.0.4
+ checksum: 6b97f641bca4c1de66bd74dd5a965bc5fd5c4b8e09328448c4952226ebd691c107cc990ce4e29ccb1e6bfff0278d8956fc8159533456c167f94ae067b4b42b11
+ languageName: node
+ linkType: hard
+
"hast-util-to-jsx-runtime@npm:^2.0.0":
version: 2.3.2
resolution: "hast-util-to-jsx-runtime@npm:2.3.2"
@@ -2302,6 +2381,13 @@ __metadata:
languageName: node
linkType: hard
+"html-void-elements@npm:^3.0.0":
+ version: 3.0.0
+ resolution: "html-void-elements@npm:3.0.0"
+ checksum: 59be397525465a7489028afa064c55763d9cccd1d7d9f630cca47137317f0e897a9ca26cef7e745e7cff1abc44260cfa407742b243a54261dfacd42230e94fce
+ languageName: node
+ linkType: hard
+
"ignore@npm:^5.2.0, ignore@npm:^5.3.1":
version: 5.3.2
resolution: "ignore@npm:5.3.2"
@@ -3483,6 +3569,17 @@ __metadata:
languageName: node
linkType: hard
+"oniguruma-to-es@npm:0.8.1":
+ version: 0.8.1
+ resolution: "oniguruma-to-es@npm:0.8.1"
+ dependencies:
+ emoji-regex-xs: ^1.0.0
+ regex: ^5.0.2
+ regex-recursion: ^5.0.0
+ checksum: 88e1936ba0ffd09850e6a96fefcb0efc257013b42d139e0076a46b31fe75f2c36ca4152df08765cafd8b52554a739a3b2c4aa4ddc47df12bc3c0fdde40103104
+ languageName: node
+ linkType: hard
+
"optionator@npm:^0.9.3":
version: 0.9.4
resolution: "optionator@npm:0.9.4"
@@ -3727,6 +3824,32 @@ __metadata:
languageName: node
linkType: hard
+"regex-recursion@npm:^5.0.0":
+ version: 5.1.1
+ resolution: "regex-recursion@npm:5.1.1"
+ dependencies:
+ regex: ^5.1.1
+ regex-utilities: ^2.3.0
+ checksum: 4f203ae8f4a2ebf9004f4e4119df5106ba07b39bd3778d7040a83b17f3a82fe22c202661adc3f5586e4eb782fece77e8a01eba8b7033f92147ad7a1e7e1531d7
+ languageName: node
+ linkType: hard
+
+"regex-utilities@npm:^2.3.0":
+ version: 2.3.0
+ resolution: "regex-utilities@npm:2.3.0"
+ checksum: 41408777df45cefe1b276281030213235aa1143809c4c10eb5573d2cc27ff2c4aa746c6f4d4c235e3d2f4830eff76b28906ce82fbe72895beca8e15204c2da51
+ languageName: node
+ linkType: hard
+
+"regex@npm:^5.0.2, regex@npm:^5.1.1":
+ version: 5.1.1
+ resolution: "regex@npm:5.1.1"
+ dependencies:
+ regex-utilities: ^2.3.0
+ checksum: bff664d0c001bf2929c2a5c92399419f719ef5ac9e7198bce653695d37628a3bd21595cea571f93ee13b55c5bbeff7fbab307a9ef569e36b149caf09601d4a31
+ languageName: node
+ linkType: hard
+
"regexp.prototype.flags@npm:^1.5.3":
version: 1.5.3
resolution: "regexp.prototype.flags@npm:1.5.3"
@@ -4027,6 +4150,20 @@ __metadata:
languageName: node
linkType: hard
+"shiki@npm:^1.24.4":
+ version: 1.24.4
+ resolution: "shiki@npm:1.24.4"
+ dependencies:
+ "@shikijs/core": 1.24.4
+ "@shikijs/engine-javascript": 1.24.4
+ "@shikijs/engine-oniguruma": 1.24.4
+ "@shikijs/types": 1.24.4
+ "@shikijs/vscode-textmate": ^9.3.1
+ "@types/hast": ^3.0.4
+ checksum: dee2af812f67e11985882469a82540dd4cd91ea5e966d8dc52854df82471e5f5dad30c971c2512766f1f55ddd88f8033ff3ae472676fcb053297a5f6b8707449
+ languageName: node
+ linkType: hard
+
"side-channel-list@npm:^1.0.0":
version: 1.0.0
resolution: "side-channel-list@npm:1.0.0"
@@ -4634,7 +4771,7 @@ __metadata:
languageName: node
linkType: hard
-"zwitch@npm:^2.0.0":
+"zwitch@npm:^2.0.0, zwitch@npm:^2.0.4":
version: 2.0.4
resolution: "zwitch@npm:2.0.4"
checksum: f22ec5fc2d5f02c423c93d35cdfa83573a3a3bd98c66b927c368ea4d0e7252a500df2a90a6b45522be536a96a73404393c958e945fdba95e6832c200791702b6
diff --git a/packages/canon/report.api.md b/packages/canon/report.api.md
index e725d0ac8b..cc193e1180 100644
--- a/packages/canon/report.api.md
+++ b/packages/canon/report.api.md
@@ -8,6 +8,7 @@
import { ForwardRefExoticComponent } from 'react';
import { default as React_2 } from 'react';
import * as React_3 from 'react';
+import { ReactNode } from 'react';
import { RefAttributes } from 'react';
// @public (undocumented)
@@ -91,6 +92,29 @@ export interface ButtonProps {
| Partial>;
}
+// @public (undocumented)
+export interface CanonContextProps {
+ // (undocumented)
+ breakpoint: Breakpoint;
+ // (undocumented)
+ getResponsiveValue: (
+ value: string | Partial>,
+ ) => string;
+ // (undocumented)
+ icons: IconMap;
+}
+
+// @public (undocumented)
+export const CanonProvider: (props: CanonProviderProps) => React_2.JSX.Element;
+
+// @public (undocumented)
+export interface CanonProviderProps {
+ // (undocumented)
+ children?: ReactNode;
+ // (undocumented)
+ overrides?: Partial>;
+}
+
// @public (undocumented)
export const Checkbox: React_2.ForwardRefExoticComponent<
CheckboxProps & React_2.RefAttributes
@@ -223,7 +247,9 @@ export type IconNames =
| 'chevronUp'
| 'cloud'
| 'heart'
+ | 'moon'
| 'plus'
+ | 'sun'
| 'trash';
// @public (undocumented)
@@ -374,6 +400,9 @@ export const TableRow: React_3.ForwardRefExoticComponent<
React_3.RefAttributes
>;
+// @public (undocumented)
+export const useCanon: () => CanonContextProps;
+
// @public (undocumented)
export interface UtilityProps extends SpaceProps {
// (undocumented)
diff --git a/packages/canon/src/contexts/canon.tsx b/packages/canon/src/contexts/canon.tsx
index a7e9f73bc8..da0b9b420b 100644
--- a/packages/canon/src/contexts/canon.tsx
+++ b/packages/canon/src/contexts/canon.tsx
@@ -22,7 +22,8 @@ import { defaultIcons } from '../components/Icon/icons';
import { useMediaQuery } from '../hooks/useMediaQuery';
import type { Breakpoint } from '../types';
-interface CanonContextProps {
+/** @public */
+export interface CanonContextProps {
icons: IconMap;
breakpoint: Breakpoint;
getResponsiveValue: (
@@ -36,7 +37,8 @@ const CanonContext = createContext({
getResponsiveValue: () => '',
});
-interface CanonProviderProps {
+/** @public */
+export interface CanonProviderProps {
children?: ReactNode;
overrides?: Partial>;
}
diff --git a/packages/canon/src/css/core.css b/packages/canon/src/css/core.css
index 9f8dcfff19..7f0c2f42f7 100644
--- a/packages/canon/src/css/core.css
+++ b/packages/canon/src/css/core.css
@@ -50,7 +50,8 @@
--canon-font-regular: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto,
'Helvetica Neue', Arial, sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji',
'Segoe UI Symbol', 'Noto Color Emoji';
- --canon-font-monospace: 'Monospace', monospace;
+ --canon-font-monospace: ui-monospace, 'Menlo', 'Monaco', 'Consolas',
+ 'Liberation Mono', 'Courier New', monospace;
/* Font weights */
--canon-font-weight-regular: 400;