@backstage/ui 0.16.0 → 0.17.0-next.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/CHANGELOG.md +19 -0
- package/dist/components/PluginHeader/PluginHeader.esm.js +16 -1
- package/dist/components/PluginHeader/PluginHeader.esm.js.map +1 -1
- package/dist/components/PluginHeader/PluginHeader.module.css.esm.js +2 -2
- package/dist/components/PluginHeader/PluginHeaderBreadcrumbs.esm.js +106 -0
- package/dist/components/PluginHeader/PluginHeaderBreadcrumbs.esm.js.map +1 -0
- package/dist/components/PluginHeader/definition.esm.js +3 -0
- package/dist/components/PluginHeader/definition.esm.js.map +1 -1
- package/dist/components/PluginHeader/useIsTruncated.esm.js +36 -0
- package/dist/components/PluginHeader/useIsTruncated.esm.js.map +1 -0
- package/dist/components/TextAreaField/TextAreaField.esm.js +61 -0
- package/dist/components/TextAreaField/TextAreaField.esm.js.map +1 -0
- package/dist/components/TextAreaField/TextAreaField.module.css.esm.js +8 -0
- package/dist/components/TextAreaField/TextAreaField.module.css.esm.js.map +1 -0
- package/dist/components/TextAreaField/definition.esm.js +32 -0
- package/dist/components/TextAreaField/definition.esm.js.map +1 -0
- package/dist/index.d.ts +77 -2
- package/dist/index.esm.js +3 -0
- package/dist/index.esm.js.map +1 -1
- package/package.json +4 -4
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,24 @@
|
|
|
1
1
|
# @backstage/ui
|
|
2
2
|
|
|
3
|
+
## 0.17.0-next.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- 503ba32: Added re-exports from `react-aria-components`. The types `Selection`, `SortDirection`, and `Key` are available as type-only exports (use `import type`), while `Focusable` is a runtime export. Consumers can now import these directly from `@backstage/ui` instead of depending on `react-aria-components`, avoiding version mismatches.
|
|
8
|
+
|
|
9
|
+
### Patch Changes
|
|
10
|
+
|
|
11
|
+
- 791703e: Add `breadcrumbs` prop & breadcrumbs to `PluginHeader`. When passed `breadcrumbs`, `PluginHeader` renders a `nav` with breadcrumbs & visually hides the plugin title.
|
|
12
|
+
|
|
13
|
+
These breadcrumbs:
|
|
14
|
+
|
|
15
|
+
- Collapses middle segments if 5 or more segments
|
|
16
|
+
- Shows tooltip if text is truncated
|
|
17
|
+
|
|
18
|
+
**Affected components:** PluginHeader
|
|
19
|
+
|
|
20
|
+
- 066c7ac: Added a new `TextAreaField` component for multi-line text input, following the same conventions as `TextField` with support for a label, secondary label, and description.
|
|
21
|
+
|
|
3
22
|
## 0.16.0
|
|
4
23
|
|
|
5
24
|
### Minor Changes
|
|
@@ -12,6 +12,9 @@ import '../Link/Link.module.css.esm.js';
|
|
|
12
12
|
import { RiShapesLine } from '@remixicon/react';
|
|
13
13
|
import { Text } from '../Text/Text.esm.js';
|
|
14
14
|
import '../Text/Text.module.css.esm.js';
|
|
15
|
+
import { VisuallyHidden } from '../VisuallyHidden/VisuallyHidden.esm.js';
|
|
16
|
+
import '../VisuallyHidden/VisuallyHidden.module.css.esm.js';
|
|
17
|
+
import { PluginHeaderBreadcrumbs } from './PluginHeaderBreadcrumbs.esm.js';
|
|
15
18
|
|
|
16
19
|
const PluginHeader = (props) => {
|
|
17
20
|
const { ownProps } = useDefinition(PluginHeaderDefinition, props);
|
|
@@ -21,10 +24,12 @@ const PluginHeader = (props) => {
|
|
|
21
24
|
icon,
|
|
22
25
|
title,
|
|
23
26
|
titleLink,
|
|
27
|
+
breadcrumbs,
|
|
24
28
|
customActions,
|
|
25
29
|
onTabSelectionChange
|
|
26
30
|
} = ownProps;
|
|
27
31
|
const hasTabs = tabs && tabs.length > 0;
|
|
32
|
+
const hasBreadcrumbs = breadcrumbs && breadcrumbs.length > 0;
|
|
28
33
|
const rootRef = useRef(null);
|
|
29
34
|
const animationFrameRef = useRef(void 0);
|
|
30
35
|
const lastAppliedHeightRef = useRef(void 0);
|
|
@@ -84,7 +89,17 @@ const PluginHeader = (props) => {
|
|
|
84
89
|
/* @__PURE__ */ jsxs("div", { className: classes.toolbar, "data-has-tabs": hasTabs ? "" : void 0, children: [
|
|
85
90
|
/* @__PURE__ */ jsxs("div", { className: classes.toolbarContent, children: [
|
|
86
91
|
/* @__PURE__ */ jsx(Box, { bg: "neutral", className: classes.toolbarIcon, "aria-hidden": "true", children: icon || /* @__PURE__ */ jsx(RiShapesLine, {}) }),
|
|
87
|
-
/* @__PURE__ */
|
|
92
|
+
hasBreadcrumbs ? /* @__PURE__ */ jsxs("div", { className: classes.toolbarName, children: [
|
|
93
|
+
/* @__PURE__ */ jsx(VisuallyHidden, { children: /* @__PURE__ */ jsx("h1", { children: titleText }) }),
|
|
94
|
+
/* @__PURE__ */ jsx(
|
|
95
|
+
PluginHeaderBreadcrumbs,
|
|
96
|
+
{
|
|
97
|
+
entries: breadcrumbs,
|
|
98
|
+
className: classes.breadcrumbs,
|
|
99
|
+
ellipsisClassName: classes.breadcrumbsEllipsis
|
|
100
|
+
}
|
|
101
|
+
)
|
|
102
|
+
] }) : /* @__PURE__ */ jsx("h1", { className: classes.toolbarName, children: titleLink ? /* @__PURE__ */ jsx(Link, { href: titleLink, standalone: true, variant: "body-medium", children: titleText }) : /* @__PURE__ */ jsx(Text, { as: "span", variant: "body-medium", children: titleText }) })
|
|
88
103
|
] }),
|
|
89
104
|
/* @__PURE__ */ jsx("div", { className: classes.toolbarControls, children: actionChildren })
|
|
90
105
|
] }),
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"PluginHeader.esm.js","sources":["../../../src/components/PluginHeader/PluginHeader.tsx"],"sourcesContent":["/*\n * Copyright 2025 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport type { PluginHeaderProps } from './types';\nimport { Tabs, TabList, Tab } from '../Tabs';\nimport { useDefinition } from '../../hooks/useDefinition';\nimport { PluginHeaderDefinition } from './definition';\nimport { type NavigateOptions } from 'react-router-dom';\nimport { Children, useMemo, useRef } from 'react';\nimport { useIsomorphicLayoutEffect } from '../../hooks/useIsomorphicLayoutEffect';\nimport { Box } from '../Box';\nimport { Link } from '../Link';\nimport { RiShapesLine } from '@remixicon/react';\nimport { Text } from '../Text';\n\ndeclare module 'react-aria-components' {\n interface RouterConfig {\n routerOptions: NavigateOptions;\n }\n}\n\n/**\n * Renders a plugin header with icon, title, custom actions, and optional tabs.\n * Always participates in the background context system so descendants (e.g. buttons)\n * get the correct `data-on-bg` styling inside the toolbar and tabs.\n *\n * @public\n */\nexport const PluginHeader = (props: PluginHeaderProps) => {\n const { ownProps } = useDefinition(PluginHeaderDefinition, props);\n const {\n classes,\n tabs,\n icon,\n title,\n titleLink,\n customActions,\n onTabSelectionChange,\n } = ownProps;\n\n const hasTabs = tabs && tabs.length > 0;\n const rootRef = useRef<HTMLDivElement>(null);\n const animationFrameRef = useRef<number | undefined>(undefined);\n const lastAppliedHeightRef = useRef<number | undefined>(undefined);\n\n const actionChildren = useMemo(() => {\n return Children.toArray(customActions);\n }, [customActions]);\n\n useIsomorphicLayoutEffect(() => {\n const el = rootRef.current;\n if (!el) {\n return undefined;\n }\n\n const cancelScheduledUpdate = () => {\n if (animationFrameRef.current === undefined) {\n return;\n }\n\n cancelAnimationFrame(animationFrameRef.current);\n animationFrameRef.current = undefined;\n };\n\n const applyHeight = (height: number) => {\n if (lastAppliedHeightRef.current === height) {\n return;\n }\n\n lastAppliedHeightRef.current = height;\n document.documentElement.style.setProperty(\n '--bui-header-height',\n `${height}px`,\n );\n };\n\n const scheduleHeightUpdate = () => {\n cancelScheduledUpdate();\n animationFrameRef.current = requestAnimationFrame(() => {\n animationFrameRef.current = undefined;\n applyHeight(el.offsetHeight);\n });\n };\n\n // Set height once immediately so the initial layout is correct.\n applyHeight(el.offsetHeight);\n\n // Observe for resize changes if ResizeObserver is available\n // (not present in Jest/jsdom by default)\n if (typeof ResizeObserver === 'undefined') {\n return () => {\n cancelScheduledUpdate();\n lastAppliedHeightRef.current = undefined;\n document.documentElement.style.removeProperty('--bui-header-height');\n };\n }\n\n const observer = new ResizeObserver(() => {\n scheduleHeightUpdate();\n });\n observer.observe(el);\n\n return () => {\n observer.disconnect();\n cancelScheduledUpdate();\n lastAppliedHeightRef.current = undefined;\n document.documentElement.style.removeProperty('--bui-header-height');\n };\n }, []);\n\n const titleText = title || 'Your plugin';\n\n return (\n <div ref={rootRef} className={classes.root}>\n <div className={classes.toolbar} data-has-tabs={hasTabs ? '' : undefined}>\n <div className={classes.toolbarContent}>\n <Box bg=\"neutral\" className={classes.toolbarIcon} aria-hidden=\"true\">\n {icon || <RiShapesLine />}\n </Box>\n <
|
|
1
|
+
{"version":3,"file":"PluginHeader.esm.js","sources":["../../../src/components/PluginHeader/PluginHeader.tsx"],"sourcesContent":["/*\n * Copyright 2025 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport type { PluginHeaderProps } from './types';\nimport { Tabs, TabList, Tab } from '../Tabs';\nimport { useDefinition } from '../../hooks/useDefinition';\nimport { PluginHeaderDefinition } from './definition';\nimport { type NavigateOptions } from 'react-router-dom';\nimport { Children, useMemo, useRef } from 'react';\nimport { useIsomorphicLayoutEffect } from '../../hooks/useIsomorphicLayoutEffect';\nimport { Box } from '../Box';\nimport { Link } from '../Link';\nimport { RiShapesLine } from '@remixicon/react';\nimport { Text } from '../Text';\nimport { VisuallyHidden } from '../VisuallyHidden';\nimport { PluginHeaderBreadcrumbs } from './PluginHeaderBreadcrumbs';\n\ndeclare module 'react-aria-components' {\n interface RouterConfig {\n routerOptions: NavigateOptions;\n }\n}\n\n/**\n * Renders a plugin header with icon, title, custom actions, and optional tabs.\n * Always participates in the background context system so descendants (e.g. buttons)\n * get the correct `data-on-bg` styling inside the toolbar and tabs.\n *\n * @public\n */\nexport const PluginHeader = (props: PluginHeaderProps) => {\n const { ownProps } = useDefinition(PluginHeaderDefinition, props);\n const {\n classes,\n tabs,\n icon,\n title,\n titleLink,\n breadcrumbs,\n customActions,\n onTabSelectionChange,\n } = ownProps;\n\n const hasTabs = tabs && tabs.length > 0;\n const hasBreadcrumbs = breadcrumbs && breadcrumbs.length > 0;\n const rootRef = useRef<HTMLDivElement>(null);\n const animationFrameRef = useRef<number | undefined>(undefined);\n const lastAppliedHeightRef = useRef<number | undefined>(undefined);\n\n const actionChildren = useMemo(() => {\n return Children.toArray(customActions);\n }, [customActions]);\n\n useIsomorphicLayoutEffect(() => {\n const el = rootRef.current;\n if (!el) {\n return undefined;\n }\n\n const cancelScheduledUpdate = () => {\n if (animationFrameRef.current === undefined) {\n return;\n }\n\n cancelAnimationFrame(animationFrameRef.current);\n animationFrameRef.current = undefined;\n };\n\n const applyHeight = (height: number) => {\n if (lastAppliedHeightRef.current === height) {\n return;\n }\n\n lastAppliedHeightRef.current = height;\n document.documentElement.style.setProperty(\n '--bui-header-height',\n `${height}px`,\n );\n };\n\n const scheduleHeightUpdate = () => {\n cancelScheduledUpdate();\n animationFrameRef.current = requestAnimationFrame(() => {\n animationFrameRef.current = undefined;\n applyHeight(el.offsetHeight);\n });\n };\n\n // Set height once immediately so the initial layout is correct.\n applyHeight(el.offsetHeight);\n\n // Observe for resize changes if ResizeObserver is available\n // (not present in Jest/jsdom by default)\n if (typeof ResizeObserver === 'undefined') {\n return () => {\n cancelScheduledUpdate();\n lastAppliedHeightRef.current = undefined;\n document.documentElement.style.removeProperty('--bui-header-height');\n };\n }\n\n const observer = new ResizeObserver(() => {\n scheduleHeightUpdate();\n });\n observer.observe(el);\n\n return () => {\n observer.disconnect();\n cancelScheduledUpdate();\n lastAppliedHeightRef.current = undefined;\n document.documentElement.style.removeProperty('--bui-header-height');\n };\n }, []);\n\n const titleText = title || 'Your plugin';\n\n return (\n <div ref={rootRef} className={classes.root}>\n <div className={classes.toolbar} data-has-tabs={hasTabs ? '' : undefined}>\n <div className={classes.toolbarContent}>\n <Box bg=\"neutral\" className={classes.toolbarIcon} aria-hidden=\"true\">\n {icon || <RiShapesLine />}\n </Box>\n {hasBreadcrumbs ? (\n <div className={classes.toolbarName}>\n <VisuallyHidden>\n <h1>{titleText}</h1>\n </VisuallyHidden>\n <PluginHeaderBreadcrumbs\n entries={breadcrumbs}\n className={classes.breadcrumbs}\n ellipsisClassName={classes.breadcrumbsEllipsis}\n />\n </div>\n ) : (\n <h1 className={classes.toolbarName}>\n {titleLink ? (\n <Link href={titleLink} standalone variant=\"body-medium\">\n {titleText}\n </Link>\n ) : (\n <Text as=\"span\" variant=\"body-medium\">\n {titleText}\n </Text>\n )}\n </h1>\n )}\n </div>\n <div className={classes.toolbarControls}>{actionChildren}</div>\n </div>\n {hasTabs && (\n <div className={classes.tabs}>\n <Tabs onSelectionChange={onTabSelectionChange}>\n <TabList>\n {tabs?.map(tab => (\n <Tab\n key={tab.id}\n id={tab.id}\n href={tab.href}\n matchStrategy={tab.matchStrategy}\n >\n {tab.label}\n </Tab>\n ))}\n </TabList>\n </Tabs>\n </div>\n )}\n </div>\n );\n};\n"],"names":[],"mappings":"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"}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import styleInject from '../../node_modules_dist/style-inject/dist/style-inject.es.esm.js';
|
|
2
2
|
|
|
3
|
-
var css_248z = "/*\n * Copyright 2025 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\n@layer tokens, base, components, utilities;\n\n@layer components {\n .PluginHeader_bui-
|
|
4
|
-
var styles = {"bui-PluginHeader":"PluginHeader_bui-
|
|
3
|
+
var css_248z = "/*\n * Copyright 2025 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\n@layer tokens, base, components, utilities;\n\n@layer components {\n .PluginHeader_bui-PluginHeader__cf3f6a1fa8 {\n --bui-plugin-header-margin-bottom: var(--bui-space-6);\n --bui-plugin-header-toolbar-border-bottom: solid 1px var(--bui-border-1);\n --bui-plugin-header-tabs-border-bottom: 1px solid var(--bui-border-1);\n --bui-plugin-header-toolbar-padding-bottom: var(--bui-space-4);\n --bui-plugin-header-toolbar-tabs-padding-bottom: var(--bui-space-1);\n --bui-plugin-header-background-color: transparent;\n --bui-plugin-header-padding-top: var(--bui-space-4);\n --bui-plugin-header-breadcrumbs-gap: var(--bui-space-3);\n --bui-plugin-header-breadcrumbs-max-width: 165px;\n --bui-plugin-header-breadcrumbs-current-max-width: none;\n\n margin-bottom: var(--bui-plugin-header-margin-bottom);\n padding-inline: var(--bui-space-5);\n padding-top: var(--bui-plugin-header-padding-top);\n background-color: var(--bui-plugin-header-background-color);\n }\n\n .PluginHeader_bui-PluginHeader__cf3f6a1fa8:has(+ .PluginHeader_bui-HeaderTop__cf3f6a1fa8),\n .PluginHeader_bui-PluginHeader__cf3f6a1fa8:has(+ [data-backstage-core-header]),\n .PluginHeader_bui-PluginHeader__cf3f6a1fa8:has(\n + [data-backstage-core-page] [data-backstage-core-header]\n ) {\n --bui-plugin-header-margin-bottom: 0;\n --bui-plugin-header-toolbar-border-bottom: none;\n --bui-plugin-header-tabs-border-bottom: none;\n --bui-plugin-header-toolbar-padding-bottom: var(--bui-space-2);\n --bui-plugin-header-toolbar-tabs-padding-bottom: var(--bui-space-2);\n --bui-plugin-header-background-color: var(--bui-bg-neutral-1);\n --bui-plugin-header-padding-top: var(--bui-space-2);\n }\n\n .PluginHeader_bui-PluginHeader__cf3f6a1fa8:has(+ [data-backstage-core-header])\n .PluginHeader_bui-PluginHeaderToolbarIcon__cf3f6a1fa8,\n .PluginHeader_bui-PluginHeader__cf3f6a1fa8:has(\n + [data-backstage-core-page] [data-backstage-core-header]\n )\n .PluginHeader_bui-PluginHeaderToolbarIcon__cf3f6a1fa8 {\n background-color: var(--bui-bg-neutral-3);\n }\n\n .PluginHeader_bui-PluginHeaderToolbar__cf3f6a1fa8 {\n display: flex;\n flex-direction: row;\n align-items: center;\n justify-content: space-between;\n color: var(--bui-fg-primary);\n border-bottom: var(--bui-plugin-header-toolbar-border-bottom);\n padding-bottom: var(--bui-plugin-header-toolbar-padding-bottom);\n\n &[data-has-tabs] {\n border-bottom: none;\n padding-bottom: var(--bui-plugin-header-toolbar-tabs-padding-bottom);\n }\n }\n\n .PluginHeader_bui-PluginHeaderToolbarContent__cf3f6a1fa8 {\n display: flex;\n flex-direction: row;\n align-items: center;\n gap: var(--bui-space-2);\n min-width: 0;\n padding: var(--bui-space-1) 0;\n }\n\n .PluginHeader_bui-PluginHeaderToolbarName__cf3f6a1fa8 {\n display: flex;\n flex-direction: row;\n align-items: center;\n gap: var(--bui-space-2);\n margin: 0;\n min-width: 0;\n }\n\n .PluginHeader_bui-PluginHeaderToolbarName__cf3f6a1fa8:not(:has(.PluginHeader_bui-PluginHeaderBreadcrumbs__cf3f6a1fa8)) {\n flex-shrink: 0;\n }\n\n .PluginHeader_bui-PluginHeaderBreadcrumbs__cf3f6a1fa8 {\n min-width: 0;\n }\n\n .PluginHeader_bui-PluginHeaderBreadcrumbs__cf3f6a1fa8 ol {\n display: flex;\n flex-direction: row;\n list-style: none;\n margin: 0;\n padding: 0;\n gap: var(--bui-plugin-header-breadcrumbs-gap);\n min-width: 0;\n }\n\n .PluginHeader_bui-PluginHeaderBreadcrumbs__cf3f6a1fa8 ol li {\n display: flex;\n flex-direction: row;\n align-items: center;\n gap: var(--bui-plugin-header-breadcrumbs-gap);\n max-width: var(--bui-plugin-header-breadcrumbs-max-width);\n\n & svg {\n flex-shrink: 0;\n }\n\n &[data-current] {\n flex: 1;\n min-width: 0;\n max-width: var(--bui-plugin-header-breadcrumbs-current-max-width);\n }\n\n & a[data-focus-visible] {\n border-radius: var(--bui-radius-1);\n outline: 2px solid var(--bui-ring);\n outline-offset: 2px;\n }\n }\n\n .PluginHeader_bui-PluginHeaderBreadcrumbsEllipsis__cf3f6a1fa8 {\n all: unset;\n cursor: pointer;\n font: inherit;\n color: inherit;\n line-height: 1;\n letter-spacing: 0.1em;\n\n &[data-hovered] {\n text-decoration-line: underline;\n text-decoration-style: solid;\n text-decoration-thickness: 1px;\n text-underline-offset: 2px;\n text-decoration-color: color-mix(in srgb, currentColor 30%, transparent);\n }\n\n &[data-focus-visible] {\n border-radius: var(--bui-radius-1);\n outline: 2px solid var(--bui-ring);\n outline-offset: 2px;\n }\n }\n\n .PluginHeader_bui-PluginHeader__cf3f6a1fa8 .PluginHeader_bui-PluginHeaderToolbarIcon__cf3f6a1fa8 {\n display: flex;\n align-items: center;\n justify-content: center;\n flex-shrink: 0;\n width: 2rem;\n height: 2rem;\n border-radius: var(--bui-radius-2);\n color: var(--bui-fg-primary);\n\n & svg {\n width: 1rem;\n height: 1rem;\n }\n }\n\n .PluginHeader_bui-PluginHeaderToolbarControls__cf3f6a1fa8 {\n display: flex;\n flex-direction: row;\n align-items: center;\n gap: var(--bui-space-2);\n }\n\n .PluginHeader_bui-PluginHeaderTabsWrapper__cf3f6a1fa8 {\n border-bottom: var(--bui-plugin-header-tabs-border-bottom);\n }\n}\n";
|
|
4
|
+
var styles = {"bui-PluginHeader":"PluginHeader_bui-PluginHeader__cf3f6a1fa8","bui-HeaderTop":"PluginHeader_bui-HeaderTop__cf3f6a1fa8","bui-PluginHeaderToolbarIcon":"PluginHeader_bui-PluginHeaderToolbarIcon__cf3f6a1fa8","bui-PluginHeaderToolbar":"PluginHeader_bui-PluginHeaderToolbar__cf3f6a1fa8","bui-PluginHeaderToolbarContent":"PluginHeader_bui-PluginHeaderToolbarContent__cf3f6a1fa8","bui-PluginHeaderToolbarName":"PluginHeader_bui-PluginHeaderToolbarName__cf3f6a1fa8","bui-PluginHeaderBreadcrumbs":"PluginHeader_bui-PluginHeaderBreadcrumbs__cf3f6a1fa8","bui-PluginHeaderBreadcrumbsEllipsis":"PluginHeader_bui-PluginHeaderBreadcrumbsEllipsis__cf3f6a1fa8","bui-PluginHeaderToolbarControls":"PluginHeader_bui-PluginHeaderToolbarControls__cf3f6a1fa8","bui-PluginHeaderTabsWrapper":"PluginHeader_bui-PluginHeaderTabsWrapper__cf3f6a1fa8"};
|
|
5
5
|
styleInject(css_248z);
|
|
6
6
|
|
|
7
7
|
export { styles as default };
|
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
import { jsxs, Fragment, jsx } from 'react/jsx-runtime';
|
|
2
|
+
import { Link } from '../Link/Link.esm.js';
|
|
3
|
+
import 'clsx';
|
|
4
|
+
import '../../hooks/useBreakpoint.esm.js';
|
|
5
|
+
import '../../hooks/useBg.esm.js';
|
|
6
|
+
import '../../hooks/useDefinition/helpers.esm.js';
|
|
7
|
+
import '../../analytics/useAnalytics.esm.js';
|
|
8
|
+
import 'react-router-dom';
|
|
9
|
+
import '../Link/Link.module.css.esm.js';
|
|
10
|
+
import { Text } from '../Text/Text.esm.js';
|
|
11
|
+
import '../Text/Text.module.css.esm.js';
|
|
12
|
+
import { MenuTrigger, Menu, MenuItem } from '../Menu/Menu.esm.js';
|
|
13
|
+
import '../Menu/definition.esm.js';
|
|
14
|
+
import { RiArrowRightSLine } from '@remixicon/react';
|
|
15
|
+
import { Breadcrumbs, Breadcrumb, Button, Focusable } from 'react-aria-components';
|
|
16
|
+
import { useIsTruncated } from './useIsTruncated.esm.js';
|
|
17
|
+
import { TooltipTrigger, Tooltip } from '../Tooltip/Tooltip.esm.js';
|
|
18
|
+
import '../Tooltip/Tooltip.module.css.esm.js';
|
|
19
|
+
|
|
20
|
+
const COLLAPSE_THRESHOLD = 5;
|
|
21
|
+
const ROOT_ITEMS = 1;
|
|
22
|
+
function BreadcrumbSeparator() {
|
|
23
|
+
return /* @__PURE__ */ jsx("span", { "aria-hidden": "true", children: /* @__PURE__ */ jsx(RiArrowRightSLine, { size: 16 }) });
|
|
24
|
+
}
|
|
25
|
+
function BreadcrumbTooltipWrapper(props) {
|
|
26
|
+
const { showTooltip, label, children } = props;
|
|
27
|
+
return /* @__PURE__ */ jsxs(TooltipTrigger, { delay: 300, isDisabled: !showTooltip, children: [
|
|
28
|
+
children,
|
|
29
|
+
/* @__PURE__ */ jsx(Tooltip, { children: label })
|
|
30
|
+
] });
|
|
31
|
+
}
|
|
32
|
+
function BreadcrumbLink(props) {
|
|
33
|
+
const { entry } = props;
|
|
34
|
+
const { ref, truncated } = useIsTruncated();
|
|
35
|
+
return /* @__PURE__ */ jsx(BreadcrumbTooltipWrapper, { label: entry.label, showTooltip: truncated, children: /* @__PURE__ */ jsx(
|
|
36
|
+
Link,
|
|
37
|
+
{
|
|
38
|
+
href: entry.href,
|
|
39
|
+
standalone: true,
|
|
40
|
+
variant: "body-medium",
|
|
41
|
+
truncate: true,
|
|
42
|
+
ref,
|
|
43
|
+
children: entry.label
|
|
44
|
+
}
|
|
45
|
+
) });
|
|
46
|
+
}
|
|
47
|
+
function BreadcrumbText(props) {
|
|
48
|
+
const { entry } = props;
|
|
49
|
+
const { ref, truncated } = useIsTruncated();
|
|
50
|
+
return /* @__PURE__ */ jsx(BreadcrumbTooltipWrapper, { label: entry.label, showTooltip: truncated, children: /* @__PURE__ */ jsx(Focusable, { excludeFromTabOrder: !truncated, children: /* @__PURE__ */ jsx(Text, { variant: "body-medium", truncate: true, ref, children: entry.label }) }) });
|
|
51
|
+
}
|
|
52
|
+
function CollapsedSegment(props) {
|
|
53
|
+
const { items, ellipsisClassName } = props;
|
|
54
|
+
const ariaLabel = "Show more breadcrumbs";
|
|
55
|
+
return /* @__PURE__ */ jsxs(Breadcrumb, { children: [
|
|
56
|
+
/* @__PURE__ */ jsxs(MenuTrigger, { children: [
|
|
57
|
+
/* @__PURE__ */ jsx(Button, { "aria-label": ariaLabel, className: ellipsisClassName, children: /* @__PURE__ */ jsx(Text, { as: "span", variant: "body-medium", children: "\u2026" }) }),
|
|
58
|
+
/* @__PURE__ */ jsx(Menu, { children: items.map((item) => /* @__PURE__ */ jsx(MenuItem, { href: item.href, children: item.label }, item.href)) })
|
|
59
|
+
] }),
|
|
60
|
+
/* @__PURE__ */ jsx(BreadcrumbSeparator, {})
|
|
61
|
+
] }, "collapsed");
|
|
62
|
+
}
|
|
63
|
+
function AncestorSegment(props) {
|
|
64
|
+
const { entry } = props;
|
|
65
|
+
return /* @__PURE__ */ jsxs(Breadcrumb, { children: [
|
|
66
|
+
/* @__PURE__ */ jsx(BreadcrumbLink, { entry }),
|
|
67
|
+
/* @__PURE__ */ jsx(BreadcrumbSeparator, {})
|
|
68
|
+
] }, entry.href);
|
|
69
|
+
}
|
|
70
|
+
function CurrentSegment(props) {
|
|
71
|
+
const { entry, isSingleEntry } = props;
|
|
72
|
+
return /* @__PURE__ */ jsx(Breadcrumb, { children: isSingleEntry ? /* @__PURE__ */ jsx(BreadcrumbLink, { entry }) : /* @__PURE__ */ jsx(BreadcrumbText, { entry }) }, entry.href);
|
|
73
|
+
}
|
|
74
|
+
function PluginHeaderBreadcrumbs(props) {
|
|
75
|
+
const { entries, className, ellipsisClassName } = props;
|
|
76
|
+
if (entries.length === 0) return null;
|
|
77
|
+
const isSingleEntry = entries.length === 1;
|
|
78
|
+
const current = entries[entries.length - 1];
|
|
79
|
+
const rest = entries.slice(0, -1);
|
|
80
|
+
let ancestorItems = null;
|
|
81
|
+
if (entries.length >= COLLAPSE_THRESHOLD) {
|
|
82
|
+
const root = rest.slice(0, ROOT_ITEMS);
|
|
83
|
+
const leading = rest.slice(-1);
|
|
84
|
+
const collapsed = rest.slice(ROOT_ITEMS, -1);
|
|
85
|
+
ancestorItems = /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
86
|
+
root.map((entry) => /* @__PURE__ */ jsx(AncestorSegment, { entry }, entry.href)),
|
|
87
|
+
/* @__PURE__ */ jsx(
|
|
88
|
+
CollapsedSegment,
|
|
89
|
+
{
|
|
90
|
+
items: collapsed,
|
|
91
|
+
ellipsisClassName
|
|
92
|
+
}
|
|
93
|
+
),
|
|
94
|
+
leading.map((entry) => /* @__PURE__ */ jsx(AncestorSegment, { entry }, entry.href))
|
|
95
|
+
] });
|
|
96
|
+
} else {
|
|
97
|
+
ancestorItems = rest.map((entry) => /* @__PURE__ */ jsx(AncestorSegment, { entry }, entry.href));
|
|
98
|
+
}
|
|
99
|
+
return /* @__PURE__ */ jsx("nav", { id: "Breadcrumbs", "aria-label": "Breadcrumbs", className, children: /* @__PURE__ */ jsxs(Breadcrumbs, { children: [
|
|
100
|
+
ancestorItems,
|
|
101
|
+
/* @__PURE__ */ jsx(CurrentSegment, { entry: current, isSingleEntry })
|
|
102
|
+
] }) });
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
export { PluginHeaderBreadcrumbs };
|
|
106
|
+
//# sourceMappingURL=PluginHeaderBreadcrumbs.esm.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"PluginHeaderBreadcrumbs.esm.js","sources":["../../../src/components/PluginHeader/PluginHeaderBreadcrumbs.tsx"],"sourcesContent":["/*\n * Copyright 2026 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport type { PluginHeaderBreadcrumbEntry } from './types';\nimport { Link } from '../Link';\nimport { Text } from '../Text';\nimport { MenuTrigger, Menu, MenuItem } from '../Menu';\nimport { RiArrowRightSLine } from '@remixicon/react';\nimport {\n Focusable,\n Breadcrumb as RACBreadcrumb,\n Breadcrumbs as RACBreadcrumbs,\n Button as RACButton,\n} from 'react-aria-components';\nimport { useIsTruncated } from './useIsTruncated';\nimport { Tooltip, TooltipTrigger } from '../Tooltip';\n\nconst COLLAPSE_THRESHOLD = 5;\nconst ROOT_ITEMS = 1;\nconst LEADING_ITEMS = 1;\n\n/** Separator icon that appears after non-current segments */\nfunction BreadcrumbSeparator() {\n return (\n <span aria-hidden=\"true\">\n <RiArrowRightSLine size={16} />\n </span>\n );\n}\n\n/** Wraps children in a tooltip that shows on hover when the label is truncated. */\nfunction BreadcrumbTooltipWrapper(props: {\n showTooltip: boolean;\n label: string;\n children: React.ReactNode;\n}) {\n const { showTooltip, label, children } = props;\n\n return (\n <TooltipTrigger delay={300} isDisabled={!showTooltip}>\n {children}\n <Tooltip>{label}</Tooltip>\n </TooltipTrigger>\n );\n}\n\n/** Renders a link in the breadcrumbs trail */\nfunction BreadcrumbLink(props: { entry: PluginHeaderBreadcrumbEntry }) {\n const { entry } = props;\n const { ref, truncated } = useIsTruncated<HTMLAnchorElement>();\n return (\n <BreadcrumbTooltipWrapper label={entry.label} showTooltip={truncated}>\n <Link\n href={entry.href}\n standalone\n variant=\"body-medium\"\n truncate\n ref={ref}\n >\n {entry.label}\n </Link>\n </BreadcrumbTooltipWrapper>\n );\n}\n\n/**\n * Renders a text in the breadcrumbs trail.\n * If it is truncated, it becomes focusable (requirement for the tooltip to work)\n */\nfunction BreadcrumbText(props: { entry: PluginHeaderBreadcrumbEntry }) {\n const { entry } = props;\n const { ref, truncated } = useIsTruncated<HTMLParagraphElement>();\n\n return (\n <BreadcrumbTooltipWrapper label={entry.label} showTooltip={truncated}>\n <Focusable excludeFromTabOrder={!truncated}>\n <Text variant=\"body-medium\" truncate ref={ref}>\n {entry.label}\n </Text>\n </Focusable>\n </BreadcrumbTooltipWrapper>\n );\n}\n\n/** Renders an ellipsis button that opens a menu with the collapsed breadcrumb items. */\nfunction CollapsedSegment(props: {\n items: PluginHeaderBreadcrumbEntry[];\n ellipsisClassName?: string;\n}) {\n const { items, ellipsisClassName } = props;\n const ariaLabel = 'Show more breadcrumbs';\n return (\n <RACBreadcrumb key=\"collapsed\">\n <MenuTrigger>\n <RACButton aria-label={ariaLabel} className={ellipsisClassName}>\n <Text as=\"span\" variant=\"body-medium\">\n …\n </Text>\n </RACButton>\n <Menu>\n {items.map(item => (\n <MenuItem key={item.href} href={item.href}>\n {item.label}\n </MenuItem>\n ))}\n </Menu>\n </MenuTrigger>\n <BreadcrumbSeparator />\n </RACBreadcrumb>\n );\n}\n\n/** Renders a non-current breadcrumb segment as a link with a trailing separator. */\nfunction AncestorSegment(props: { entry: PluginHeaderBreadcrumbEntry }) {\n const { entry } = props;\n return (\n <RACBreadcrumb key={entry.href}>\n <BreadcrumbLink entry={entry} />\n <BreadcrumbSeparator />\n </RACBreadcrumb>\n );\n}\n\n/**\n * Renders the current page in the breadcrumbs trail\n * - RAC Breadcrumbs will attach `data-current` to this segment\n * - If it's the only entry (eg. we are on the root page of the Plugin), it will render as a link\n * - Otherwise renders as text\n * - If truncated, will be focusable and show a breadcrumb\n */\nfunction CurrentSegment(props: {\n entry: PluginHeaderBreadcrumbEntry;\n isSingleEntry: boolean;\n}) {\n const { entry, isSingleEntry } = props;\n return (\n <RACBreadcrumb key={entry.href}>\n {isSingleEntry ? (\n <BreadcrumbLink entry={entry} />\n ) : (\n <BreadcrumbText entry={entry} />\n )}\n </RACBreadcrumb>\n );\n}\n\n/**\n * Renders a breadcrumb navigation trail from an ordered list of entries.\n *\n * - Uses RAC Breadcrumb and Breadcrumbs internally for a11y utils\n * - A single entry renders as a clickable link (plugin root page).\n * - Multiple entries render ancestors as links and the last entry as plain text.\n * - When there are {@link COLLAPSE_THRESHOLD} or more entries, middle items\n * collapse behind an ellipsis menu, keeping the root and leading items visible.\n *\n * @internal\n */\nexport function PluginHeaderBreadcrumbs(props: {\n entries: PluginHeaderBreadcrumbEntry[];\n className?: string;\n ellipsisClassName?: string;\n}) {\n const { entries, className, ellipsisClassName } = props;\n\n if (entries.length === 0) return null;\n\n const isSingleEntry = entries.length === 1;\n const current = entries[entries.length - 1];\n const rest = entries.slice(0, -1);\n\n let ancestorItems: React.ReactNode = null;\n\n if (entries.length >= COLLAPSE_THRESHOLD) {\n const root = rest.slice(0, ROOT_ITEMS);\n const leading = rest.slice(-LEADING_ITEMS);\n const collapsed = rest.slice(ROOT_ITEMS, -LEADING_ITEMS);\n\n ancestorItems = (\n <>\n {root.map(entry => (\n <AncestorSegment key={entry.href} entry={entry} />\n ))}\n <CollapsedSegment\n items={collapsed}\n ellipsisClassName={ellipsisClassName}\n />\n {leading.map(entry => (\n <AncestorSegment key={entry.href} entry={entry} />\n ))}\n </>\n );\n } else {\n ancestorItems = rest.map(entry => (\n <AncestorSegment key={entry.href} entry={entry} />\n ));\n }\n\n return (\n <nav id=\"Breadcrumbs\" aria-label=\"Breadcrumbs\" className={className}>\n <RACBreadcrumbs>\n {ancestorItems}\n <CurrentSegment entry={current} isSingleEntry={isSingleEntry} />\n </RACBreadcrumbs>\n </nav>\n );\n}\n"],"names":["RACBreadcrumb","RACButton","RACBreadcrumbs"],"mappings":"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"}
|
|
@@ -17,12 +17,15 @@ const PluginHeaderDefinition = defineComponent()({
|
|
|
17
17
|
toolbarControls: "bui-PluginHeaderToolbarControls",
|
|
18
18
|
toolbarIcon: "bui-PluginHeaderToolbarIcon",
|
|
19
19
|
toolbarName: "bui-PluginHeaderToolbarName",
|
|
20
|
+
breadcrumbs: "bui-PluginHeaderBreadcrumbs",
|
|
21
|
+
breadcrumbsEllipsis: "bui-PluginHeaderBreadcrumbsEllipsis",
|
|
20
22
|
tabs: "bui-PluginHeaderTabsWrapper"
|
|
21
23
|
},
|
|
22
24
|
propDefs: {
|
|
23
25
|
icon: {},
|
|
24
26
|
title: {},
|
|
25
27
|
titleLink: {},
|
|
28
|
+
breadcrumbs: {},
|
|
26
29
|
customActions: {},
|
|
27
30
|
tabs: {},
|
|
28
31
|
onTabSelectionChange: {},
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"definition.esm.js","sources":["../../../src/components/PluginHeader/definition.ts"],"sourcesContent":["/*\n * Copyright 2024 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport { defineComponent } from '../../hooks/useDefinition';\nimport type { PluginHeaderOwnProps } from './types';\nimport styles from './PluginHeader.module.css';\n\n/**\n * Component definition for PluginHeader\n * @public\n */\nexport const PluginHeaderDefinition = defineComponent<PluginHeaderOwnProps>()({\n styles,\n classNames: {\n root: 'bui-PluginHeader',\n toolbar: 'bui-PluginHeaderToolbar',\n toolbarContent: 'bui-PluginHeaderToolbarContent',\n toolbarControls: 'bui-PluginHeaderToolbarControls',\n toolbarIcon: 'bui-PluginHeaderToolbarIcon',\n toolbarName: 'bui-PluginHeaderToolbarName',\n tabs: 'bui-PluginHeaderTabsWrapper',\n },\n propDefs: {\n icon: {},\n title: {},\n titleLink: {},\n customActions: {},\n tabs: {},\n onTabSelectionChange: {},\n className: {},\n },\n});\n"],"names":[],"mappings":";;;;;;;;;;AAwBO,MAAM,sBAAA,GAAyB,iBAAsC,CAAE;AAAA,EAC5E,MAAA;AAAA,EACA,UAAA,EAAY;AAAA,IACV,IAAA,EAAM,kBAAA;AAAA,IACN,OAAA,EAAS,yBAAA;AAAA,IACT,cAAA,EAAgB,gCAAA;AAAA,IAChB,eAAA,EAAiB,iCAAA;AAAA,IACjB,WAAA,EAAa,6BAAA;AAAA,IACb,WAAA,EAAa,6BAAA;AAAA,IACb,IAAA,EAAM;AAAA,GACR;AAAA,EACA,QAAA,EAAU;AAAA,IACR,MAAM,EAAC;AAAA,IACP,OAAO,EAAC;AAAA,IACR,WAAW,EAAC;AAAA,IACZ,eAAe,EAAC;AAAA,IAChB,MAAM,EAAC;AAAA,IACP,sBAAsB,EAAC;AAAA,IACvB,WAAW;AAAC;AAEhB,CAAC;;;;"}
|
|
1
|
+
{"version":3,"file":"definition.esm.js","sources":["../../../src/components/PluginHeader/definition.ts"],"sourcesContent":["/*\n * Copyright 2024 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport { defineComponent } from '../../hooks/useDefinition';\nimport type { PluginHeaderOwnProps } from './types';\nimport styles from './PluginHeader.module.css';\n\n/**\n * Component definition for PluginHeader\n * @public\n */\nexport const PluginHeaderDefinition = defineComponent<PluginHeaderOwnProps>()({\n styles,\n classNames: {\n root: 'bui-PluginHeader',\n toolbar: 'bui-PluginHeaderToolbar',\n toolbarContent: 'bui-PluginHeaderToolbarContent',\n toolbarControls: 'bui-PluginHeaderToolbarControls',\n toolbarIcon: 'bui-PluginHeaderToolbarIcon',\n toolbarName: 'bui-PluginHeaderToolbarName',\n breadcrumbs: 'bui-PluginHeaderBreadcrumbs',\n breadcrumbsEllipsis: 'bui-PluginHeaderBreadcrumbsEllipsis',\n tabs: 'bui-PluginHeaderTabsWrapper',\n },\n propDefs: {\n icon: {},\n title: {},\n titleLink: {},\n breadcrumbs: {},\n customActions: {},\n tabs: {},\n onTabSelectionChange: {},\n className: {},\n },\n});\n"],"names":[],"mappings":";;;;;;;;;;AAwBO,MAAM,sBAAA,GAAyB,iBAAsC,CAAE;AAAA,EAC5E,MAAA;AAAA,EACA,UAAA,EAAY;AAAA,IACV,IAAA,EAAM,kBAAA;AAAA,IACN,OAAA,EAAS,yBAAA;AAAA,IACT,cAAA,EAAgB,gCAAA;AAAA,IAChB,eAAA,EAAiB,iCAAA;AAAA,IACjB,WAAA,EAAa,6BAAA;AAAA,IACb,WAAA,EAAa,6BAAA;AAAA,IACb,WAAA,EAAa,6BAAA;AAAA,IACb,mBAAA,EAAqB,qCAAA;AAAA,IACrB,IAAA,EAAM;AAAA,GACR;AAAA,EACA,QAAA,EAAU;AAAA,IACR,MAAM,EAAC;AAAA,IACP,OAAO,EAAC;AAAA,IACR,WAAW,EAAC;AAAA,IACZ,aAAa,EAAC;AAAA,IACd,eAAe,EAAC;AAAA,IAChB,MAAM,EAAC;AAAA,IACP,sBAAsB,EAAC;AAAA,IACvB,WAAW;AAAC;AAEhB,CAAC;;;;"}
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import { useRef, useState } from 'react';
|
|
2
|
+
import { useIsomorphicLayoutEffect } from '../../hooks/useIsomorphicLayoutEffect.esm.js';
|
|
3
|
+
|
|
4
|
+
const DEBOUNCE_MS = 150;
|
|
5
|
+
function observeResize(el, callback) {
|
|
6
|
+
if (typeof ResizeObserver === "undefined") return void 0;
|
|
7
|
+
let timerId;
|
|
8
|
+
const observer = new ResizeObserver(() => {
|
|
9
|
+
clearTimeout(timerId);
|
|
10
|
+
timerId = setTimeout(callback, DEBOUNCE_MS);
|
|
11
|
+
});
|
|
12
|
+
observer.observe(el);
|
|
13
|
+
return () => {
|
|
14
|
+
clearTimeout(timerId);
|
|
15
|
+
observer.disconnect();
|
|
16
|
+
};
|
|
17
|
+
}
|
|
18
|
+
function useIsTruncated() {
|
|
19
|
+
const ref = useRef(null);
|
|
20
|
+
const [truncated, setTruncated] = useState(false);
|
|
21
|
+
useIsomorphicLayoutEffect(() => {
|
|
22
|
+
const el = ref.current;
|
|
23
|
+
if (!el) return;
|
|
24
|
+
setTruncated(el.scrollWidth > el.clientWidth);
|
|
25
|
+
});
|
|
26
|
+
useIsomorphicLayoutEffect(() => {
|
|
27
|
+
const el = ref.current;
|
|
28
|
+
if (!el) return void 0;
|
|
29
|
+
const check = () => setTruncated(el.scrollWidth > el.clientWidth);
|
|
30
|
+
return observeResize(el, check);
|
|
31
|
+
}, []);
|
|
32
|
+
return { ref, truncated };
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
export { useIsTruncated };
|
|
36
|
+
//# sourceMappingURL=useIsTruncated.esm.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"useIsTruncated.esm.js","sources":["../../../src/components/PluginHeader/useIsTruncated.ts"],"sourcesContent":["/*\n * Copyright 2026 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport { useRef, useState } from 'react';\nimport { useIsomorphicLayoutEffect } from '../../hooks/useIsomorphicLayoutEffect';\n\nconst DEBOUNCE_MS = 150;\n\nfunction observeResize(\n el: HTMLElement,\n callback: () => void,\n): (() => void) | undefined {\n if (typeof ResizeObserver === 'undefined') return undefined; // ResizeObserver isn't available in all runtimes (e.g. older browsers, SSR, Jest/jsdom)\n\n let timerId: ReturnType<typeof setTimeout> | undefined;\n const observer = new ResizeObserver(() => {\n clearTimeout(timerId);\n timerId = setTimeout(callback, DEBOUNCE_MS);\n });\n observer.observe(el);\n return () => {\n clearTimeout(timerId);\n observer.disconnect();\n };\n}\n\n/**\n * Tracks whether a text element is overflowing its container via CSS truncation.\n * Useful for conditionally showing a tooltip only when text is truncated.\n *\n * Checks on every render and whenever the element resizes (via ResizeObserver, debounced).\n *\n * @example\n * ```tsx\n * const { ref, truncated } = useIsTruncated();\n *\n * <TooltipTrigger isDisabled={!truncated}>\n * <span ref={ref}>\n * {label}\n * </span>\n * <Tooltip>{label}</Tooltip>\n * </TooltipTrigger>\n * ```\n *\n * @internal\n */\nexport function useIsTruncated<T extends HTMLElement = HTMLElement>(): {\n ref: React.RefObject<T>;\n truncated: boolean;\n} {\n const ref = useRef<T>(null);\n const [truncated, setTruncated] = useState(false);\n\n // Re-check after each render in case the content changes without a resize event.\n useIsomorphicLayoutEffect(() => {\n const el = ref.current;\n if (!el) return;\n setTruncated(el.scrollWidth > el.clientWidth);\n });\n\n // Also keep it up-to-date when the element resizes.\n useIsomorphicLayoutEffect(() => {\n const el = ref.current;\n if (!el) return undefined;\n\n const check = () => setTruncated(el.scrollWidth > el.clientWidth);\n\n return observeResize(el, check);\n }, []);\n\n return { ref, truncated };\n}\n"],"names":[],"mappings":";;;AAmBA,MAAM,WAAA,GAAc,GAAA;AAEpB,SAAS,aAAA,CACP,IACA,QAAA,EAC0B;AAC1B,EAAA,IAAI,OAAO,cAAA,KAAmB,WAAA,EAAa,OAAO,MAAA;AAElD,EAAA,IAAI,OAAA;AACJ,EAAA,MAAM,QAAA,GAAW,IAAI,cAAA,CAAe,MAAM;AACxC,IAAA,YAAA,CAAa,OAAO,CAAA;AACpB,IAAA,OAAA,GAAU,UAAA,CAAW,UAAU,WAAW,CAAA;AAAA,EAC5C,CAAC,CAAA;AACD,EAAA,QAAA,CAAS,QAAQ,EAAE,CAAA;AACnB,EAAA,OAAO,MAAM;AACX,IAAA,YAAA,CAAa,OAAO,CAAA;AACpB,IAAA,QAAA,CAAS,UAAA,EAAW;AAAA,EACtB,CAAA;AACF;AAsBO,SAAS,cAAA,GAGd;AACA,EAAA,MAAM,GAAA,GAAM,OAAU,IAAI,CAAA;AAC1B,EAAA,MAAM,CAAC,SAAA,EAAW,YAAY,CAAA,GAAI,SAAS,KAAK,CAAA;AAGhD,EAAA,yBAAA,CAA0B,MAAM;AAC9B,IAAA,MAAM,KAAK,GAAA,CAAI,OAAA;AACf,IAAA,IAAI,CAAC,EAAA,EAAI;AACT,IAAA,YAAA,CAAa,EAAA,CAAG,WAAA,GAAc,EAAA,CAAG,WAAW,CAAA;AAAA,EAC9C,CAAC,CAAA;AAGD,EAAA,yBAAA,CAA0B,MAAM;AAC9B,IAAA,MAAM,KAAK,GAAA,CAAI,OAAA;AACf,IAAA,IAAI,CAAC,IAAI,OAAO,MAAA;AAEhB,IAAA,MAAM,QAAQ,MAAM,YAAA,CAAa,EAAA,CAAG,WAAA,GAAc,GAAG,WAAW,CAAA;AAEhE,IAAA,OAAO,aAAA,CAAc,IAAI,KAAK,CAAA;AAAA,EAChC,CAAA,EAAG,EAAE,CAAA;AAEL,EAAA,OAAO,EAAE,KAAK,SAAA,EAAU;AAC1B;;;;"}
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
import { jsxs, jsx } from 'react/jsx-runtime';
|
|
2
|
+
import { forwardRef, useEffect } from 'react';
|
|
3
|
+
import { TextField, TextArea } from 'react-aria-components';
|
|
4
|
+
import { FieldLabel } from '../FieldLabel/FieldLabel.esm.js';
|
|
5
|
+
import { useDefinition } from '../../hooks/useDefinition/useDefinition.esm.js';
|
|
6
|
+
import '../FieldLabel/FieldLabel.module.css.esm.js';
|
|
7
|
+
import { FieldError } from '../FieldError/FieldError.esm.js';
|
|
8
|
+
import '../FieldError/FieldError.module.css.esm.js';
|
|
9
|
+
import { TextAreaFieldDefinition } from './definition.esm.js';
|
|
10
|
+
|
|
11
|
+
const TextAreaField = forwardRef(
|
|
12
|
+
(props, ref) => {
|
|
13
|
+
const { ownProps, restProps, dataAttributes } = useDefinition(
|
|
14
|
+
TextAreaFieldDefinition,
|
|
15
|
+
props
|
|
16
|
+
);
|
|
17
|
+
const { classes, label, secondaryLabel, placeholder, description, rows } = ownProps;
|
|
18
|
+
useEffect(() => {
|
|
19
|
+
if (!label && !restProps["aria-label"] && !restProps["aria-labelledby"]) {
|
|
20
|
+
console.warn(
|
|
21
|
+
"TextAreaField requires either a visible label, aria-label, or aria-labelledby for accessibility"
|
|
22
|
+
);
|
|
23
|
+
}
|
|
24
|
+
}, [label, restProps["aria-label"], restProps["aria-labelledby"]]);
|
|
25
|
+
const secondaryLabelText = secondaryLabel || (restProps.isRequired ? "Required" : null);
|
|
26
|
+
return /* @__PURE__ */ jsxs(
|
|
27
|
+
TextField,
|
|
28
|
+
{
|
|
29
|
+
className: classes.root,
|
|
30
|
+
...dataAttributes,
|
|
31
|
+
...restProps,
|
|
32
|
+
ref,
|
|
33
|
+
children: [
|
|
34
|
+
/* @__PURE__ */ jsx(
|
|
35
|
+
FieldLabel,
|
|
36
|
+
{
|
|
37
|
+
label,
|
|
38
|
+
secondaryLabel: secondaryLabelText,
|
|
39
|
+
description,
|
|
40
|
+
descriptionSlot: "description"
|
|
41
|
+
}
|
|
42
|
+
),
|
|
43
|
+
/* @__PURE__ */ jsx(
|
|
44
|
+
TextArea,
|
|
45
|
+
{
|
|
46
|
+
className: classes.textArea,
|
|
47
|
+
"data-size": dataAttributes["data-size"],
|
|
48
|
+
placeholder,
|
|
49
|
+
rows
|
|
50
|
+
}
|
|
51
|
+
),
|
|
52
|
+
/* @__PURE__ */ jsx(FieldError, {})
|
|
53
|
+
]
|
|
54
|
+
}
|
|
55
|
+
);
|
|
56
|
+
}
|
|
57
|
+
);
|
|
58
|
+
TextAreaField.displayName = "TextAreaField";
|
|
59
|
+
|
|
60
|
+
export { TextAreaField };
|
|
61
|
+
//# sourceMappingURL=TextAreaField.esm.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TextAreaField.esm.js","sources":["../../../src/components/TextAreaField/TextAreaField.tsx"],"sourcesContent":["/*\n * Copyright 2024 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport { forwardRef, useEffect } from 'react';\nimport { TextArea, TextField as AriaTextField } from 'react-aria-components';\nimport { FieldLabel } from '../FieldLabel';\nimport { FieldError } from '../FieldError';\nimport type { TextAreaFieldProps } from './types';\nimport { useDefinition } from '../../hooks/useDefinition';\nimport { TextAreaFieldDefinition } from './definition';\n\n/**\n * A multi-line text input with an integrated label and inline error display.\n *\n * @public\n */\nexport const TextAreaField = forwardRef<HTMLDivElement, TextAreaFieldProps>(\n (props, ref) => {\n const { ownProps, restProps, dataAttributes } = useDefinition(\n TextAreaFieldDefinition,\n props,\n );\n const { classes, label, secondaryLabel, placeholder, description, rows } =\n ownProps;\n\n useEffect(() => {\n if (!label && !restProps['aria-label'] && !restProps['aria-labelledby']) {\n console.warn(\n 'TextAreaField requires either a visible label, aria-label, or aria-labelledby for accessibility',\n );\n }\n }, [label, restProps['aria-label'], restProps['aria-labelledby']]);\n\n // If a secondary label is provided, use it. Otherwise, use 'Required' if the field is required.\n const secondaryLabelText =\n secondaryLabel || (restProps.isRequired ? 'Required' : null);\n\n return (\n <AriaTextField\n className={classes.root}\n {...dataAttributes}\n {...restProps}\n ref={ref}\n >\n <FieldLabel\n label={label}\n secondaryLabel={secondaryLabelText}\n description={description}\n descriptionSlot=\"description\"\n />\n <TextArea\n className={classes.textArea}\n data-size={dataAttributes['data-size']}\n placeholder={placeholder}\n rows={rows}\n />\n <FieldError />\n </AriaTextField>\n );\n },\n);\n\nTextAreaField.displayName = 'TextAreaField';\n"],"names":["AriaTextField"],"mappings":";;;;;;;;;;AA6BO,MAAM,aAAA,GAAgB,UAAA;AAAA,EAC3B,CAAC,OAAO,GAAA,KAAQ;AACd,IAAA,MAAM,EAAE,QAAA,EAAU,SAAA,EAAW,cAAA,EAAe,GAAI,aAAA;AAAA,MAC9C,uBAAA;AAAA,MACA;AAAA,KACF;AACA,IAAA,MAAM,EAAE,OAAA,EAAS,KAAA,EAAO,gBAAgB,WAAA,EAAa,WAAA,EAAa,MAAK,GACrE,QAAA;AAEF,IAAA,SAAA,CAAU,MAAM;AACd,MAAA,IAAI,CAAC,SAAS,CAAC,SAAA,CAAU,YAAY,CAAA,IAAK,CAAC,SAAA,CAAU,iBAAiB,CAAA,EAAG;AACvE,QAAA,OAAA,CAAQ,IAAA;AAAA,UACN;AAAA,SACF;AAAA,MACF;AAAA,IACF,CAAA,EAAG,CAAC,KAAA,EAAO,SAAA,CAAU,YAAY,CAAA,EAAG,SAAA,CAAU,iBAAiB,CAAC,CAAC,CAAA;AAGjE,IAAA,MAAM,kBAAA,GACJ,cAAA,KAAmB,SAAA,CAAU,UAAA,GAAa,UAAA,GAAa,IAAA,CAAA;AAEzD,IAAA,uBACE,IAAA;AAAA,MAACA,SAAA;AAAA,MAAA;AAAA,QACC,WAAW,OAAA,CAAQ,IAAA;AAAA,QAClB,GAAG,cAAA;AAAA,QACH,GAAG,SAAA;AAAA,QACJ,GAAA;AAAA,QAEA,QAAA,EAAA;AAAA,0BAAA,GAAA;AAAA,YAAC,UAAA;AAAA,YAAA;AAAA,cACC,KAAA;AAAA,cACA,cAAA,EAAgB,kBAAA;AAAA,cAChB,WAAA;AAAA,cACA,eAAA,EAAgB;AAAA;AAAA,WAClB;AAAA,0BACA,GAAA;AAAA,YAAC,QAAA;AAAA,YAAA;AAAA,cACC,WAAW,OAAA,CAAQ,QAAA;AAAA,cACnB,WAAA,EAAW,eAAe,WAAW,CAAA;AAAA,cACrC,WAAA;AAAA,cACA;AAAA;AAAA,WACF;AAAA,8BACC,UAAA,EAAA,EAAW;AAAA;AAAA;AAAA,KACd;AAAA,EAEJ;AACF;AAEA,aAAA,CAAc,WAAA,GAAc,eAAA;;;;"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import styleInject from '../../node_modules_dist/style-inject/dist/style-inject.es.esm.js';
|
|
2
|
+
|
|
3
|
+
var css_248z = "/*\n * Copyright 2025 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\n@layer tokens, base, components, utilities;\n\n@layer components {\n .TextAreaField_bui-TextAreaField__dceec51086 {\n display: flex;\n flex-direction: column;\n font-family: var(--bui-font-regular);\n width: 100%;\n flex: 1;\n }\n\n .TextAreaField_bui-TextArea__dceec51086 {\n display: block;\n padding: var(--bui-space-2) var(--bui-space-3);\n border-radius: var(--bui-radius-2);\n border: none;\n background-color: var(--bui-bg-neutral-1);\n font-size: var(--bui-font-size-3);\n font-family: var(--bui-font-regular);\n font-weight: var(--bui-font-weight-regular);\n line-height: 140%;\n color: var(--bui-fg-primary);\n transition: box-shadow 0.2s ease-in-out;\n width: 100%;\n /* Keep the manual resize handle so users can expand the field. */\n resize: vertical;\n overflow-y: auto;\n\n .TextAreaField_bui-TextAreaField__dceec51086[data-on-bg='neutral-1'] & {\n background-color: var(--bui-bg-neutral-2);\n }\n\n .TextAreaField_bui-TextAreaField__dceec51086[data-on-bg='neutral-2'] & {\n background-color: var(--bui-bg-neutral-3);\n }\n\n .TextAreaField_bui-TextAreaField__dceec51086[data-on-bg='neutral-3'] & {\n background-color: var(--bui-bg-neutral-4);\n }\n\n &[data-focused] {\n outline: none;\n box-shadow: inset 0 0 0 1px var(--bui-ring);\n }\n\n &::placeholder {\n color: var(--bui-fg-secondary);\n }\n\n &[data-invalid] {\n box-shadow: inset 0 0 0 1px var(--bui-border-danger);\n }\n\n &[data-disabled] {\n opacity: 0.5;\n cursor: not-allowed;\n }\n\n &[data-size='small'] {\n padding: var(--bui-space-1_5) var(--bui-space-3);\n }\n\n &[data-size='medium'] {\n padding: var(--bui-space-2) var(--bui-space-3);\n }\n }\n}\n";
|
|
4
|
+
var styles = {"bui-TextAreaField":"TextAreaField_bui-TextAreaField__dceec51086","bui-TextArea":"TextAreaField_bui-TextArea__dceec51086"};
|
|
5
|
+
styleInject(css_248z);
|
|
6
|
+
|
|
7
|
+
export { styles as default };
|
|
8
|
+
//# sourceMappingURL=TextAreaField.module.css.esm.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TextAreaField.module.css.esm.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;"}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import 'react/jsx-runtime';
|
|
2
|
+
import 'clsx';
|
|
3
|
+
import '../../hooks/useBreakpoint.esm.js';
|
|
4
|
+
import '../../hooks/useBg.esm.js';
|
|
5
|
+
import '../../hooks/useDefinition/helpers.esm.js';
|
|
6
|
+
import '../../analytics/useAnalytics.esm.js';
|
|
7
|
+
import 'react-router-dom';
|
|
8
|
+
import { defineComponent } from '../../hooks/useDefinition/defineComponent.esm.js';
|
|
9
|
+
import styles from './TextAreaField.module.css.esm.js';
|
|
10
|
+
|
|
11
|
+
const TextAreaFieldDefinition = defineComponent()(
|
|
12
|
+
{
|
|
13
|
+
styles,
|
|
14
|
+
classNames: {
|
|
15
|
+
root: "bui-TextAreaField",
|
|
16
|
+
textArea: "bui-TextArea"
|
|
17
|
+
},
|
|
18
|
+
bg: "consumer",
|
|
19
|
+
propDefs: {
|
|
20
|
+
size: { dataAttribute: true, default: "small" },
|
|
21
|
+
className: {},
|
|
22
|
+
placeholder: {},
|
|
23
|
+
rows: { default: 3 },
|
|
24
|
+
label: {},
|
|
25
|
+
description: {},
|
|
26
|
+
secondaryLabel: {}
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
);
|
|
30
|
+
|
|
31
|
+
export { TextAreaFieldDefinition };
|
|
32
|
+
//# sourceMappingURL=definition.esm.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"definition.esm.js","sources":["../../../src/components/TextAreaField/definition.ts"],"sourcesContent":["/*\n * Copyright 2024 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport { defineComponent } from '../../hooks/useDefinition';\nimport type { TextAreaFieldOwnProps } from './types';\nimport styles from './TextAreaField.module.css';\n\n/**\n * Component definition for TextAreaField\n * @public\n */\nexport const TextAreaFieldDefinition = defineComponent<TextAreaFieldOwnProps>()(\n {\n styles,\n classNames: {\n root: 'bui-TextAreaField',\n textArea: 'bui-TextArea',\n },\n bg: 'consumer',\n propDefs: {\n size: { dataAttribute: true, default: 'small' },\n className: {},\n placeholder: {},\n rows: { default: 3 },\n label: {},\n description: {},\n secondaryLabel: {},\n },\n },\n);\n"],"names":[],"mappings":";;;;;;;;;;AAwBO,MAAM,0BAA0B,eAAA,EAAuC;AAAA,EAC5E;AAAA,IACE,MAAA;AAAA,IACA,UAAA,EAAY;AAAA,MACV,IAAA,EAAM,mBAAA;AAAA,MACN,QAAA,EAAU;AAAA,KACZ;AAAA,IACA,EAAA,EAAI,UAAA;AAAA,IACJ,QAAA,EAAU;AAAA,MACR,IAAA,EAAM,EAAE,aAAA,EAAe,IAAA,EAAM,SAAS,OAAA,EAAQ;AAAA,MAC9C,WAAW,EAAC;AAAA,MACZ,aAAa,EAAC;AAAA,MACd,IAAA,EAAM,EAAE,OAAA,EAAS,CAAA,EAAE;AAAA,MACnB,OAAO,EAAC;AAAA,MACR,aAAa,EAAC;AAAA,MACd,gBAAgB;AAAC;AACnB;AAEJ;;;;"}
|
package/dist/index.d.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import * as react from 'react';
|
|
2
2
|
import { CSSProperties, ReactNode, HTMLAttributes, ComponentPropsWithoutRef, ReactElement, ElementType, ComponentPropsWithRef, ComponentProps } from 'react';
|
|
3
3
|
import { DisclosureProps, DisclosureGroupProps, DisclosurePanelProps, HeadingProps, ButtonProps as ButtonProps$1, DatePickerProps as DatePickerProps$1, DateRangePickerProps as DateRangePickerProps$1, ModalOverlayProps, DialogTriggerProps as DialogTriggerProps$1, TabProps as TabProps$1, TabListProps as TabListProps$1, TabPanelProps as TabPanelProps$1, TabsProps as TabsProps$1, LinkProps as LinkProps$1, CheckboxProps as CheckboxProps$1, CheckboxGroupProps as CheckboxGroupProps$1, Key, ComboBoxProps, ListBoxItemRenderProps, ListBoxItemProps, RadioProps as RadioProps$1, RadioGroupProps as RadioGroupProps$1, SliderProps as SliderProps$1, CellProps as CellProps$1, ColumnProps as ColumnProps$1, RowProps as RowProps$1, TableProps as TableProps$1, TableBodyProps as TableBodyProps$1, TableHeaderProps as TableHeaderProps$1, TagProps as TagProps$1, TagListProps, TagGroupProps as TagGroupProps$1, TextFieldProps as TextFieldProps$1, NumberFieldProps as NumberFieldProps$1, TooltipProps as TooltipProps$1, TooltipTriggerComponentProps, PopoverProps as PopoverProps$1, MenuProps as MenuProps$1, ListBoxProps, MenuItemProps as MenuItemProps$1, MenuSectionProps as MenuSectionProps$1, SeparatorProps, MenuTriggerProps as MenuTriggerProps$1, SubmenuTriggerProps as SubmenuTriggerProps$1, SearchFieldProps as SearchFieldProps$1, GridListProps, GridListItemProps, SelectProps as SelectProps$1, SwitchProps as SwitchProps$1, ToggleButtonProps as ToggleButtonProps$1, ToggleButtonGroupProps as ToggleButtonGroupProps$1 } from 'react-aria-components';
|
|
4
|
+
export { Focusable, Key, Selection, SortDirection } from 'react-aria-components';
|
|
4
5
|
import { DateValue } from '@internationalized/date';
|
|
5
6
|
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
6
7
|
import { NavigateOptions } from 'react-router-dom';
|
|
@@ -1559,6 +1560,7 @@ interface PluginHeaderOwnProps {
|
|
|
1559
1560
|
icon?: React.ReactNode;
|
|
1560
1561
|
title?: string;
|
|
1561
1562
|
titleLink?: string;
|
|
1563
|
+
breadcrumbs?: PluginHeaderBreadcrumbEntry[];
|
|
1562
1564
|
customActions?: React.ReactNode;
|
|
1563
1565
|
tabs?: HeaderTab[];
|
|
1564
1566
|
onTabSelectionChange?: TabsProps$1['onSelectionChange'];
|
|
@@ -1587,6 +1589,15 @@ interface HeaderTab {
|
|
|
1587
1589
|
*/
|
|
1588
1590
|
matchStrategy?: TabMatchStrategy;
|
|
1589
1591
|
}
|
|
1592
|
+
/**
|
|
1593
|
+
* Represents a breadcrumb item in the PluginHeader Breadcrumbs
|
|
1594
|
+
*
|
|
1595
|
+
* @public
|
|
1596
|
+
*/
|
|
1597
|
+
interface PluginHeaderBreadcrumbEntry {
|
|
1598
|
+
href: string;
|
|
1599
|
+
label: string;
|
|
1600
|
+
}
|
|
1590
1601
|
|
|
1591
1602
|
declare module 'react-aria-components' {
|
|
1592
1603
|
interface RouterConfig {
|
|
@@ -1617,12 +1628,15 @@ declare const PluginHeaderDefinition: {
|
|
|
1617
1628
|
readonly toolbarControls: "bui-PluginHeaderToolbarControls";
|
|
1618
1629
|
readonly toolbarIcon: "bui-PluginHeaderToolbarIcon";
|
|
1619
1630
|
readonly toolbarName: "bui-PluginHeaderToolbarName";
|
|
1631
|
+
readonly breadcrumbs: "bui-PluginHeaderBreadcrumbs";
|
|
1632
|
+
readonly breadcrumbsEllipsis: "bui-PluginHeaderBreadcrumbsEllipsis";
|
|
1620
1633
|
readonly tabs: "bui-PluginHeaderTabsWrapper";
|
|
1621
1634
|
};
|
|
1622
1635
|
readonly propDefs: {
|
|
1623
1636
|
readonly icon: {};
|
|
1624
1637
|
readonly title: {};
|
|
1625
1638
|
readonly titleLink: {};
|
|
1639
|
+
readonly breadcrumbs: {};
|
|
1626
1640
|
readonly customActions: {};
|
|
1627
1641
|
readonly tabs: {};
|
|
1628
1642
|
readonly onTabSelectionChange: {};
|
|
@@ -3445,6 +3459,67 @@ declare const TextFieldDefinition: {
|
|
|
3445
3459
|
};
|
|
3446
3460
|
};
|
|
3447
3461
|
|
|
3462
|
+
/** @public */
|
|
3463
|
+
type TextAreaFieldOwnProps = {
|
|
3464
|
+
/**
|
|
3465
|
+
* The size of the text area field
|
|
3466
|
+
* @defaultValue 'small'
|
|
3467
|
+
*/
|
|
3468
|
+
size?: 'small' | 'medium' | Partial<Record<Breakpoint, 'small' | 'medium'>>;
|
|
3469
|
+
className?: string;
|
|
3470
|
+
/**
|
|
3471
|
+
* Text to display in the text area when it has no value
|
|
3472
|
+
*/
|
|
3473
|
+
placeholder?: string;
|
|
3474
|
+
/**
|
|
3475
|
+
* The number of visible text lines, controlling the initial and minimum height
|
|
3476
|
+
* @defaultValue 3
|
|
3477
|
+
*/
|
|
3478
|
+
rows?: number;
|
|
3479
|
+
label?: FieldLabelProps['label'];
|
|
3480
|
+
description?: FieldLabelProps['description'];
|
|
3481
|
+
secondaryLabel?: FieldLabelProps['secondaryLabel'];
|
|
3482
|
+
};
|
|
3483
|
+
/** @public */
|
|
3484
|
+
interface TextAreaFieldProps extends Omit<TextFieldProps$1, 'className' | 'description'>, TextAreaFieldOwnProps {
|
|
3485
|
+
}
|
|
3486
|
+
|
|
3487
|
+
/**
|
|
3488
|
+
* A multi-line text input with an integrated label and inline error display.
|
|
3489
|
+
*
|
|
3490
|
+
* @public
|
|
3491
|
+
*/
|
|
3492
|
+
declare const TextAreaField: react.ForwardRefExoticComponent<TextAreaFieldProps & react.RefAttributes<HTMLDivElement>>;
|
|
3493
|
+
|
|
3494
|
+
/**
|
|
3495
|
+
* Component definition for TextAreaField
|
|
3496
|
+
* @public
|
|
3497
|
+
*/
|
|
3498
|
+
declare const TextAreaFieldDefinition: {
|
|
3499
|
+
readonly styles: {
|
|
3500
|
+
readonly [key: string]: string;
|
|
3501
|
+
};
|
|
3502
|
+
readonly classNames: {
|
|
3503
|
+
readonly root: "bui-TextAreaField";
|
|
3504
|
+
readonly textArea: "bui-TextArea";
|
|
3505
|
+
};
|
|
3506
|
+
readonly bg: "consumer";
|
|
3507
|
+
readonly propDefs: {
|
|
3508
|
+
readonly size: {
|
|
3509
|
+
readonly dataAttribute: true;
|
|
3510
|
+
readonly default: "small";
|
|
3511
|
+
};
|
|
3512
|
+
readonly className: {};
|
|
3513
|
+
readonly placeholder: {};
|
|
3514
|
+
readonly rows: {
|
|
3515
|
+
readonly default: 3;
|
|
3516
|
+
};
|
|
3517
|
+
readonly label: {};
|
|
3518
|
+
readonly description: {};
|
|
3519
|
+
readonly secondaryLabel: {};
|
|
3520
|
+
};
|
|
3521
|
+
};
|
|
3522
|
+
|
|
3448
3523
|
/** @public */
|
|
3449
3524
|
type NumberFieldOwnProps = {
|
|
3450
3525
|
/**
|
|
@@ -4934,5 +5009,5 @@ declare function useAnalytics(): AnalyticsTracker;
|
|
|
4934
5009
|
*/
|
|
4935
5010
|
declare function getNodeText(node: ReactNode | ((...args: any[]) => ReactNode)): string | undefined;
|
|
4936
5011
|
|
|
4937
|
-
export { Accordion, AccordionDefinition, AccordionGroup, AccordionGroupDefinition, AccordionPanel, AccordionPanelDefinition, AccordionTrigger, AccordionTriggerDefinition, Alert, AlertDefinition, Avatar, AvatarDefinition, BUIProvider, Badge, BadgeDefinition, BgProvider, Box, BoxDefinition, Button, ButtonDefinition, ButtonIcon, ButtonIconDefinition, ButtonLink, ButtonLinkDefinition, Card, CardBody, CardBodyDefinition, CardDefinition, CardFooter, CardFooterDefinition, CardHeader, CardHeaderDefinition, Cell, CellProfile, CellText, Checkbox, CheckboxDefinition, CheckboxGroup, CheckboxGroupDefinition, Column, Combobox, ComboboxDefinition, ComboboxInputDefinition, ComboboxItem, ComboboxItemDefinition, ComboboxItemProfile, ComboboxItemProfileDefinition, ComboboxItemText, ComboboxItemTextDefinition, ComboboxListBoxDefinition, ComboboxListBoxItemDefinition, ComboboxSectionDefinition, Container, ContainerDefinition, DatePicker, DatePickerCalendarDefinition, DatePickerDefinition, DatePickerGroupDefinition, DateRangePicker, DateRangePickerDefinition, Dialog, DialogBody, DialogBodyDefinition, DialogDefinition, DialogFooter, DialogFooterDefinition, DialogHeader, DialogHeaderDefinition, DialogTrigger, FieldLabel, FieldLabelDefinition, Flex, FlexDefinition, FullPage, FullPageDefinition, Grid, GridDefinition, GridItemDefinition, Header, HeaderDefinition, HeaderMetadataStatus, HeaderMetadataUsers, HeaderNavDefinition, HeaderNavGroupDefinition, HeaderNavItemDefinition, HeaderPage, HeaderPageDefinition, Link, LinkDefinition, List, ListDefinition, ListRow, ListRowDefinition, Menu, MenuAutocomplete, MenuAutocompleteListbox, MenuDefinition, MenuItem, MenuListBox, MenuListBoxItem, MenuSection, MenuSeparator, MenuTrigger, NumberField, NumberFieldDefinition, PasswordField, PasswordFieldDefinition, PluginHeader, PluginHeaderDefinition, Popover, PopoverDefinition, Radio, RadioDefinition, RadioGroup, RadioGroupDefinition, Row, SearchAutocomplete, SearchAutocompleteDefinition, SearchAutocompleteItem, SearchField, SearchFieldDefinition, Select, SelectContentDefinition, SelectDefinition, SelectItem, SelectItemDefinition, SelectItemProfile, SelectItemProfileDefinition, SelectItemText, SelectItemTextDefinition, SelectListBoxDefinition, SelectListBoxItemDefinition, SelectSectionDefinition, SelectTriggerDefinition, Skeleton, SkeletonDefinition, Slider, SliderDefinition, SubmenuTrigger, Switch, SwitchDefinition, Tab, TabList, TabPanel, Table, TableBody, TableBodySkeleton, TableDefinition, TableHeader, TablePagination, TablePaginationDefinition, TableRoot, Tabs, TabsDefinition, Tag, TagGroup, TagGroupDefinition, Text, TextDefinition, TextField, TextFieldDefinition, ToggleButton, ToggleButtonDefinition, ToggleButtonGroup, ToggleButtonGroupDefinition, Tooltip, TooltipDefinition, TooltipTrigger, VisuallyHidden, VisuallyHiddenDefinition, getNodeText, useAnalytics, useBgConsumer, useBgProvider, useBreakpoint, useTable };
|
|
4938
|
-
export type { AccordionGroupOwnProps, AccordionGroupProps, AccordionOwnProps, AccordionPanelOwnProps, AccordionPanelProps, AccordionProps, AccordionTriggerOwnProps, AccordionTriggerProps, AlertOwnProps, AlertProps, AlignItems, AnalyticsEventAttributes, AnalyticsTracker, AsyncListSource, AvatarOwnProps, AvatarProps, BUIProviderProps, BadgeOwnProps, BadgeProps, BgContextValue, BgProviderProps, Border, BorderRadius, BoxOwnProps, BoxProps, BoxUtilityProps, Breakpoint, ButtonIconOwnProps, ButtonIconProps, ButtonLinkOwnProps, ButtonLinkProps, ButtonOwnProps, ButtonProps, CardBaseProps, CardBodyOwnProps, CardBodyProps, CardButtonVariant, CardFooterOwnProps, CardFooterProps, CardHeaderOwnProps, CardHeaderProps, CardLinkVariant, CardOwnProps, CardProps, CardStaticVariant, CellOwnProps, CellProfileOwnProps, CellProfileProps, CellProps, CellTextOwnProps, CellTextProps, CheckboxGroupOwnProps, CheckboxGroupProps, CheckboxOwnProps, CheckboxProps, ColumnConfig, ColumnOwnProps, ColumnProps, Columns, ComboboxAsyncItemsProps, ComboboxAsyncOptionsProps, ComboboxAsyncSearch, ComboboxBaseOwnProps, ComboboxCommonProps, ComboboxItemOwnProps, ComboboxItemProfileOwnProps, ComboboxItemProfileProps, ComboboxItemProps, ComboboxItemSelectionProps, ComboboxItemTextOwnProps, ComboboxItemTextProps, ComboboxItemsProps, ComboboxKeySelectionProps, ComboboxOptionsProps, ComboboxOwnProps, ComboboxProps, ComboboxSearch, ComboboxServerItem, ComboboxServerItemsProps, ComboboxServerOptionsProps, ComboboxStaticProps, ComboboxStaticSearch, CompletePaginationOptions, ContainerBg, ContainerOwnProps, ContainerProps, CursorParams, CursorResponse, DatePickerOwnProps, DatePickerProps, DateRangePickerOwnProps, DateRangePickerProps, DialogBodyOwnProps, DialogBodyProps, DialogFooterOwnProps, DialogFooterProps, DialogHeaderOwnProps, DialogHeaderProps, DialogOwnProps, DialogProps, DialogTriggerProps, Display, FieldLabelOwnProps, FieldLabelProps, FilterState, FlexDirection, FlexItemProps, FlexOwnProps, FlexProps, FlexWrap, FullPageOwnProps, FullPageProps, GridItemOwnProps, GridItemProps, GridOwnProps, GridProps, HeaderBreadcrumb, HeaderMetadataItem, HeaderMetadataStatusProps, HeaderMetadataUser, HeaderNavTab, HeaderNavTabGroup, HeaderNavTabItem, HeaderOwnProps, HeaderPageBreadcrumb, HeaderPageOwnProps, HeaderPageProps, HeaderProps, HeaderTab, HeaderTag, IdentifiedOption, JustifyContent, LegacyOption, LinkOwnProps, LinkProps, ListOwnProps, ListProps, ListRowOwnProps, ListRowProps, LoadingConfig, LoadingState, MarginProps, MenuAutocompleteListBoxOwnProps, MenuAutocompleteListBoxProps, MenuAutocompleteOwnProps, MenuAutocompleteProps, MenuItemOwnProps, MenuItemProps, MenuListBoxItemOwnProps, MenuListBoxItemProps, MenuListBoxOwnProps, MenuListBoxProps, MenuOwnProps, MenuPopoverOwnProps, MenuProps, MenuSectionOwnProps, MenuSectionProps, MenuSeparatorOwnProps, MenuSeparatorProps, MenuTriggerProps, NoPagination, NormalizedOption, NumberFieldOwnProps, NumberFieldProps, OffsetParams, OffsetResponse, Option, OptionSection, PaddingProps, PagePagination, PageSizeOption, PaginationOptions, PasswordFieldOwnProps, PasswordFieldProps, PluginHeaderOwnProps, PluginHeaderProps, PopoverOwnProps, PopoverProps, ProviderBg, QueryOptions, RadioGroupOwnProps, RadioGroupProps, RadioOwnProps, RadioProps, Responsive, RowConfig, RowOwnProps, RowProps, RowRenderFn, SearchAutocompleteItemOwnProps, SearchAutocompleteItemProps, SearchAutocompleteOwnProps, SearchAutocompleteProps, SearchFieldOwnProps, SearchFieldProps, SearchState, SelectAsyncItemsProps, SelectAsyncOptionsProps, SelectAsyncSearch, SelectBaseOwnProps, SelectCommonProps, SelectItemOwnProps, SelectItemProfileOwnProps, SelectItemProfileProps, SelectItemProps, SelectItemTextOwnProps, SelectItemTextProps, SelectItemsProps, SelectOptionsProps, SelectOwnProps, SelectProps, SelectSearch, SelectStaticProps, SelectStaticSearch, SkeletonOwnProps, SkeletonProps, SliderOwnProps, SliderProps, SortDescriptor, SortState, Space, SpaceProps, SubmenuTriggerProps, SwitchOwnProps, SwitchProps, TabListOwnProps, TabListProps, TabMatchStrategy, TabOwnProps, TabPanelOwnProps, TabPanelProps, TabProps, TableBodyOwnProps, TableBodyProps, TableHeaderOwnProps, TableHeaderProps, TableItem, TablePaginationOwnProps, TablePaginationProps, TablePaginationType, TableProps, TableRootOwnProps, TableRootProps, TableSelection, TabsOwnProps, TabsProps, TagGroupOwnProps, TagGroupProps, TagOwnProps, TagProps, TextColorStatus, TextColors, TextFieldOwnProps, TextFieldProps, TextOwnProps, TextProps, TextVariants, TextWeights, ToggleButtonGroupOwnProps, ToggleButtonGroupProps, ToggleButtonOwnProps, ToggleButtonProps, TooltipOwnProps, TooltipProps, UseAnalyticsFn, UseTableCompleteOptions, UseTableCursorOptions, UseTableOffsetOptions, UseTableOptions, UseTableResult, UtilityProps, VirtualizedProp, VisuallyHiddenOwnProps, VisuallyHiddenProps };
|
|
5012
|
+
export { Accordion, AccordionDefinition, AccordionGroup, AccordionGroupDefinition, AccordionPanel, AccordionPanelDefinition, AccordionTrigger, AccordionTriggerDefinition, Alert, AlertDefinition, Avatar, AvatarDefinition, BUIProvider, Badge, BadgeDefinition, BgProvider, Box, BoxDefinition, Button, ButtonDefinition, ButtonIcon, ButtonIconDefinition, ButtonLink, ButtonLinkDefinition, Card, CardBody, CardBodyDefinition, CardDefinition, CardFooter, CardFooterDefinition, CardHeader, CardHeaderDefinition, Cell, CellProfile, CellText, Checkbox, CheckboxDefinition, CheckboxGroup, CheckboxGroupDefinition, Column, Combobox, ComboboxDefinition, ComboboxInputDefinition, ComboboxItem, ComboboxItemDefinition, ComboboxItemProfile, ComboboxItemProfileDefinition, ComboboxItemText, ComboboxItemTextDefinition, ComboboxListBoxDefinition, ComboboxListBoxItemDefinition, ComboboxSectionDefinition, Container, ContainerDefinition, DatePicker, DatePickerCalendarDefinition, DatePickerDefinition, DatePickerGroupDefinition, DateRangePicker, DateRangePickerDefinition, Dialog, DialogBody, DialogBodyDefinition, DialogDefinition, DialogFooter, DialogFooterDefinition, DialogHeader, DialogHeaderDefinition, DialogTrigger, FieldLabel, FieldLabelDefinition, Flex, FlexDefinition, FullPage, FullPageDefinition, Grid, GridDefinition, GridItemDefinition, Header, HeaderDefinition, HeaderMetadataStatus, HeaderMetadataUsers, HeaderNavDefinition, HeaderNavGroupDefinition, HeaderNavItemDefinition, HeaderPage, HeaderPageDefinition, Link, LinkDefinition, List, ListDefinition, ListRow, ListRowDefinition, Menu, MenuAutocomplete, MenuAutocompleteListbox, MenuDefinition, MenuItem, MenuListBox, MenuListBoxItem, MenuSection, MenuSeparator, MenuTrigger, NumberField, NumberFieldDefinition, PasswordField, PasswordFieldDefinition, PluginHeader, PluginHeaderDefinition, Popover, PopoverDefinition, Radio, RadioDefinition, RadioGroup, RadioGroupDefinition, Row, SearchAutocomplete, SearchAutocompleteDefinition, SearchAutocompleteItem, SearchField, SearchFieldDefinition, Select, SelectContentDefinition, SelectDefinition, SelectItem, SelectItemDefinition, SelectItemProfile, SelectItemProfileDefinition, SelectItemText, SelectItemTextDefinition, SelectListBoxDefinition, SelectListBoxItemDefinition, SelectSectionDefinition, SelectTriggerDefinition, Skeleton, SkeletonDefinition, Slider, SliderDefinition, SubmenuTrigger, Switch, SwitchDefinition, Tab, TabList, TabPanel, Table, TableBody, TableBodySkeleton, TableDefinition, TableHeader, TablePagination, TablePaginationDefinition, TableRoot, Tabs, TabsDefinition, Tag, TagGroup, TagGroupDefinition, Text, TextAreaField, TextAreaFieldDefinition, TextDefinition, TextField, TextFieldDefinition, ToggleButton, ToggleButtonDefinition, ToggleButtonGroup, ToggleButtonGroupDefinition, Tooltip, TooltipDefinition, TooltipTrigger, VisuallyHidden, VisuallyHiddenDefinition, getNodeText, useAnalytics, useBgConsumer, useBgProvider, useBreakpoint, useTable };
|
|
5013
|
+
export type { AccordionGroupOwnProps, AccordionGroupProps, AccordionOwnProps, AccordionPanelOwnProps, AccordionPanelProps, AccordionProps, AccordionTriggerOwnProps, AccordionTriggerProps, AlertOwnProps, AlertProps, AlignItems, AnalyticsEventAttributes, AnalyticsTracker, AsyncListSource, AvatarOwnProps, AvatarProps, BUIProviderProps, BadgeOwnProps, BadgeProps, BgContextValue, BgProviderProps, Border, BorderRadius, BoxOwnProps, BoxProps, BoxUtilityProps, Breakpoint, ButtonIconOwnProps, ButtonIconProps, ButtonLinkOwnProps, ButtonLinkProps, ButtonOwnProps, ButtonProps, CardBaseProps, CardBodyOwnProps, CardBodyProps, CardButtonVariant, CardFooterOwnProps, CardFooterProps, CardHeaderOwnProps, CardHeaderProps, CardLinkVariant, CardOwnProps, CardProps, CardStaticVariant, CellOwnProps, CellProfileOwnProps, CellProfileProps, CellProps, CellTextOwnProps, CellTextProps, CheckboxGroupOwnProps, CheckboxGroupProps, CheckboxOwnProps, CheckboxProps, ColumnConfig, ColumnOwnProps, ColumnProps, Columns, ComboboxAsyncItemsProps, ComboboxAsyncOptionsProps, ComboboxAsyncSearch, ComboboxBaseOwnProps, ComboboxCommonProps, ComboboxItemOwnProps, ComboboxItemProfileOwnProps, ComboboxItemProfileProps, ComboboxItemProps, ComboboxItemSelectionProps, ComboboxItemTextOwnProps, ComboboxItemTextProps, ComboboxItemsProps, ComboboxKeySelectionProps, ComboboxOptionsProps, ComboboxOwnProps, ComboboxProps, ComboboxSearch, ComboboxServerItem, ComboboxServerItemsProps, ComboboxServerOptionsProps, ComboboxStaticProps, ComboboxStaticSearch, CompletePaginationOptions, ContainerBg, ContainerOwnProps, ContainerProps, CursorParams, CursorResponse, DatePickerOwnProps, DatePickerProps, DateRangePickerOwnProps, DateRangePickerProps, DialogBodyOwnProps, DialogBodyProps, DialogFooterOwnProps, DialogFooterProps, DialogHeaderOwnProps, DialogHeaderProps, DialogOwnProps, DialogProps, DialogTriggerProps, Display, FieldLabelOwnProps, FieldLabelProps, FilterState, FlexDirection, FlexItemProps, FlexOwnProps, FlexProps, FlexWrap, FullPageOwnProps, FullPageProps, GridItemOwnProps, GridItemProps, GridOwnProps, GridProps, HeaderBreadcrumb, HeaderMetadataItem, HeaderMetadataStatusProps, HeaderMetadataUser, HeaderNavTab, HeaderNavTabGroup, HeaderNavTabItem, HeaderOwnProps, HeaderPageBreadcrumb, HeaderPageOwnProps, HeaderPageProps, HeaderProps, HeaderTab, HeaderTag, IdentifiedOption, JustifyContent, LegacyOption, LinkOwnProps, LinkProps, ListOwnProps, ListProps, ListRowOwnProps, ListRowProps, LoadingConfig, LoadingState, MarginProps, MenuAutocompleteListBoxOwnProps, MenuAutocompleteListBoxProps, MenuAutocompleteOwnProps, MenuAutocompleteProps, MenuItemOwnProps, MenuItemProps, MenuListBoxItemOwnProps, MenuListBoxItemProps, MenuListBoxOwnProps, MenuListBoxProps, MenuOwnProps, MenuPopoverOwnProps, MenuProps, MenuSectionOwnProps, MenuSectionProps, MenuSeparatorOwnProps, MenuSeparatorProps, MenuTriggerProps, NoPagination, NormalizedOption, NumberFieldOwnProps, NumberFieldProps, OffsetParams, OffsetResponse, Option, OptionSection, PaddingProps, PagePagination, PageSizeOption, PaginationOptions, PasswordFieldOwnProps, PasswordFieldProps, PluginHeaderBreadcrumbEntry, PluginHeaderOwnProps, PluginHeaderProps, PopoverOwnProps, PopoverProps, ProviderBg, QueryOptions, RadioGroupOwnProps, RadioGroupProps, RadioOwnProps, RadioProps, Responsive, RowConfig, RowOwnProps, RowProps, RowRenderFn, SearchAutocompleteItemOwnProps, SearchAutocompleteItemProps, SearchAutocompleteOwnProps, SearchAutocompleteProps, SearchFieldOwnProps, SearchFieldProps, SearchState, SelectAsyncItemsProps, SelectAsyncOptionsProps, SelectAsyncSearch, SelectBaseOwnProps, SelectCommonProps, SelectItemOwnProps, SelectItemProfileOwnProps, SelectItemProfileProps, SelectItemProps, SelectItemTextOwnProps, SelectItemTextProps, SelectItemsProps, SelectOptionsProps, SelectOwnProps, SelectProps, SelectSearch, SelectStaticProps, SelectStaticSearch, SkeletonOwnProps, SkeletonProps, SliderOwnProps, SliderProps, SortDescriptor, SortState, Space, SpaceProps, SubmenuTriggerProps, SwitchOwnProps, SwitchProps, TabListOwnProps, TabListProps, TabMatchStrategy, TabOwnProps, TabPanelOwnProps, TabPanelProps, TabProps, TableBodyOwnProps, TableBodyProps, TableHeaderOwnProps, TableHeaderProps, TableItem, TablePaginationOwnProps, TablePaginationProps, TablePaginationType, TableProps, TableRootOwnProps, TableRootProps, TableSelection, TabsOwnProps, TabsProps, TagGroupOwnProps, TagGroupProps, TagOwnProps, TagProps, TextAreaFieldOwnProps, TextAreaFieldProps, TextColorStatus, TextColors, TextFieldOwnProps, TextFieldProps, TextOwnProps, TextProps, TextVariants, TextWeights, ToggleButtonGroupOwnProps, ToggleButtonGroupProps, ToggleButtonOwnProps, ToggleButtonProps, TooltipOwnProps, TooltipProps, UseAnalyticsFn, UseTableCompleteOptions, UseTableCursorOptions, UseTableOffsetOptions, UseTableOptions, UseTableResult, UtilityProps, VirtualizedProp, VisuallyHiddenOwnProps, VisuallyHiddenProps };
|
package/dist/index.esm.js
CHANGED
|
@@ -72,6 +72,8 @@ export { Text } from './components/Text/Text.esm.js';
|
|
|
72
72
|
export { TextDefinition } from './components/Text/definition.esm.js';
|
|
73
73
|
export { TextField } from './components/TextField/TextField.esm.js';
|
|
74
74
|
export { TextFieldDefinition } from './components/TextField/definition.esm.js';
|
|
75
|
+
export { TextAreaField } from './components/TextAreaField/TextAreaField.esm.js';
|
|
76
|
+
export { TextAreaFieldDefinition } from './components/TextAreaField/definition.esm.js';
|
|
75
77
|
export { NumberField } from './components/NumberField/NumberField.esm.js';
|
|
76
78
|
export { NumberFieldDefinition } from './components/NumberField/definition.esm.js';
|
|
77
79
|
export { PasswordField } from './components/PasswordField/PasswordField.esm.js';
|
|
@@ -103,6 +105,7 @@ export { ToggleButtonGroup } from './components/ToggleButtonGroup/ToggleButtonGr
|
|
|
103
105
|
export { ToggleButtonGroupDefinition } from './components/ToggleButtonGroup/definition.esm.js';
|
|
104
106
|
export { VisuallyHidden } from './components/VisuallyHidden/VisuallyHidden.esm.js';
|
|
105
107
|
export { VisuallyHiddenDefinition } from './components/VisuallyHidden/definition.esm.js';
|
|
108
|
+
export { Focusable } from 'react-aria-components';
|
|
106
109
|
export { useBreakpoint } from './hooks/useBreakpoint.esm.js';
|
|
107
110
|
export { BgProvider, useBgConsumer, useBgProvider } from './hooks/useBg.esm.js';
|
|
108
111
|
export { useAsyncList } from 'react-stately/useAsyncList';
|
package/dist/index.esm.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.esm.js","sources":[],"sourcesContent":[],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"index.esm.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@backstage/ui",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.17.0-next.0",
|
|
4
4
|
"backstage": {
|
|
5
5
|
"role": "web-library"
|
|
6
6
|
},
|
|
@@ -50,7 +50,7 @@
|
|
|
50
50
|
"test": "backstage-cli package test"
|
|
51
51
|
},
|
|
52
52
|
"dependencies": {
|
|
53
|
-
"@backstage/version-bridge": "
|
|
53
|
+
"@backstage/version-bridge": "1.0.12",
|
|
54
54
|
"@braintree/sanitize-url": "^7.1.2",
|
|
55
55
|
"@internationalized/date": "^3.12.0",
|
|
56
56
|
"@remixicon/react": ">=4.6.0 <4.9.0",
|
|
@@ -63,8 +63,8 @@
|
|
|
63
63
|
"use-sync-external-store": "^1.4.0"
|
|
64
64
|
},
|
|
65
65
|
"devDependencies": {
|
|
66
|
-
"@backstage/cli": "
|
|
67
|
-
"@backstage/core-components": "
|
|
66
|
+
"@backstage/cli": "0.36.4-next.0",
|
|
67
|
+
"@backstage/core-components": "0.18.12-next.0",
|
|
68
68
|
"@storybook/react-vite": "^10.4.0",
|
|
69
69
|
"@testing-library/jest-dom": "^6.0.0",
|
|
70
70
|
"@testing-library/react": "^16.0.0",
|