@moderneinc/neo-styled-components 2.5.0-next.3268eb → 2.5.0-next.3773dc

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.
@@ -20,8 +20,9 @@ export interface NeoAvatarProps extends Omit<AvatarProps, 'variant'> {
20
20
  *
21
21
  * Figma Props Mapping:
22
22
  * - Figma Type "Initials" → variant="initials", size="small" (20px)
23
- * - Figma Type "Small" → variant="circular", size="small" (20px with image)
23
+ * - Figma Type "Small" → variant="circular", size="small" (32px with image)
24
24
  * - Figma Type "Medium" → variant="circular", size="medium" (44px white container with image)
25
+ * - State: Focus → CSS :focus-visible ring (2px white inner + 4px blue outer)
25
26
  * - State: Hover (tooltip) → Wrap component with MUI Tooltip
26
27
  *
27
28
  * Usage:
@@ -1,5 +1,5 @@
1
- import { type ButtonBaseProps } from '@mui/material/ButtonBase';
2
- import type { ReactNode } from 'react';
1
+ import ButtonBase from '@mui/material/ButtonBase';
2
+ import React, { type ElementType, type ReactNode } from 'react';
3
3
  declare module '@mui/material/ButtonBase' {
4
4
  interface ButtonBasePropsVariantOverrides {
5
5
  primary: true;
@@ -7,11 +7,12 @@ declare module '@mui/material/ButtonBase' {
7
7
  destructive: true;
8
8
  link: true;
9
9
  linkColor: true;
10
+ tertiary: true;
10
11
  }
11
12
  }
12
- type ButtonVariant = 'primary' | 'secondary' | 'destructive' | 'link' | 'linkColor';
13
+ type ButtonVariant = 'primary' | 'secondary' | 'destructive' | 'link' | 'linkColor' | 'tertiary';
13
14
  type ButtonSize = 'small' | 'medium';
14
- export interface NeoButtonProps extends Omit<ButtonBaseProps, 'children'> {
15
+ type NeoButtonOwnProps = {
15
16
  /**
16
17
  * The visual variant of the button
17
18
  * @default "primary"
@@ -41,14 +42,25 @@ export interface NeoButtonProps extends Omit<ButtonBaseProps, 'children'> {
41
42
  * URL to link to. When provided, the button renders as a link element.
42
43
  */
43
44
  href?: string;
44
- }
45
+ /**
46
+ * Icon placed before the button label
47
+ */
48
+ startIcon?: ReactNode;
49
+ /**
50
+ * Icon placed after the button label
51
+ */
52
+ endIcon?: ReactNode;
53
+ };
54
+ export type NeoButtonProps<C extends ElementType = typeof ButtonBase> = NeoButtonOwnProps & Omit<React.ComponentPropsWithoutRef<C>, keyof NeoButtonOwnProps> & {
55
+ component?: C;
56
+ };
45
57
  /**
46
58
  * NeoButton - Text button component based on MUI ButtonBase
47
59
  *
48
60
  * @figma https://www.figma.com/design/fQTkGSFbYyE7LiHuQJsENC/Neo---Moderne-Design-system---2025?node-id=4086-7590
49
61
  *
50
62
  * Figma Props Mapping:
51
- * - Hierarchy (Primary|Secondary|Destructive|Link|Link Color) → variant prop
63
+ * - Hierarchy (Primary|Secondary|Destructive|Link|Link Color|Tertiary) → variant prop
52
64
  * - Size (Small|Medium) → size prop
53
65
  * - State=Disabled → disabled prop
54
66
  * - State=Loading → loading prop
@@ -56,8 +68,8 @@ export interface NeoButtonProps extends Omit<ButtonBaseProps, 'children'> {
56
68
  * - State=Pressed → CSS :active
57
69
  * - State=Focused → CSS :focus-visible
58
70
  */
59
- export declare const NeoButton: {
60
- ({ variant, size, loading, children, disabled, ...props }: NeoButtonProps): import("react/jsx-runtime").JSX.Element;
61
- displayName: string;
62
- };
71
+ export declare function NeoButton<C extends ElementType = typeof ButtonBase>({ variant, size, loading, children, disabled, startIcon, endIcon, ...rest }: NeoButtonProps<C>): import("react/jsx-runtime").JSX.Element;
72
+ export declare namespace NeoButton {
73
+ var displayName: string;
74
+ }
63
75
  export {};
@@ -0,0 +1,19 @@
1
+ import { type InputBaseProps } from '@mui/material/InputBase';
2
+ export interface NeoSearchChipProps extends Omit<InputBaseProps, 'startAdornment' | 'endAdornment' | 'type'> {
3
+ /**
4
+ * Handler for clearing the search value (shows X icon when provided and value is non-empty)
5
+ */
6
+ onClear?: () => void;
7
+ }
8
+ /**
9
+ * NeoSearchChip - Pill-shaped search input for inline search functionality.
10
+ *
11
+ * @example
12
+ * <NeoSearchChip placeholder="Search titles" value={query} onChange={handleChange} onClear={handleClear} />
13
+ *
14
+ * @figma https://www.figma.com/design/fQTkGSFbYyE7LiHuQJsENC?node-id=8542-921
15
+ */
16
+ export declare const NeoSearchChip: {
17
+ ({ onClear, value, ...props }: NeoSearchChipProps): import("react/jsx-runtime").JSX.Element;
18
+ displayName: string;
19
+ };
package/dist/index.d.ts CHANGED
@@ -6,8 +6,8 @@ import { AvatarProps } from '@mui/material/Avatar';
6
6
  import { ChipProps } from '@mui/material/Chip';
7
7
  import { AlertProps } from '@mui/material/Alert';
8
8
  import { LinkProps } from '@mui/material/Link';
9
- import * as _mui_material_ButtonBase from '@mui/material/ButtonBase';
10
- import { ButtonBaseProps } from '@mui/material/ButtonBase';
9
+ import * as ButtonBase from '@mui/material/ButtonBase';
10
+ import ButtonBase__default, { ButtonBaseProps } from '@mui/material/ButtonBase';
11
11
  import { ButtonGroupProps } from '@mui/material/ButtonGroup';
12
12
  import { CheckboxProps } from '@mui/material/Checkbox';
13
13
  import { GridDensity as GridDensity$1, DataGridProProps, GridSlots, ToolbarProps, GridColumnsPanelProps } from '@mui/x-data-grid-pro';
@@ -302,8 +302,9 @@ interface NeoAvatarProps extends Omit<AvatarProps, 'variant'> {
302
302
  *
303
303
  * Figma Props Mapping:
304
304
  * - Figma Type "Initials" → variant="initials", size="small" (20px)
305
- * - Figma Type "Small" → variant="circular", size="small" (20px with image)
305
+ * - Figma Type "Small" → variant="circular", size="small" (32px with image)
306
306
  * - Figma Type "Medium" → variant="circular", size="medium" (44px white container with image)
307
+ * - State: Focus → CSS :focus-visible ring (2px white inner + 4px blue outer)
307
308
  * - State: Hover (tooltip) → Wrap component with MUI Tooltip
308
309
  *
309
310
  * Usage:
@@ -488,11 +489,12 @@ declare module '@mui/material/ButtonBase' {
488
489
  destructive: true;
489
490
  link: true;
490
491
  linkColor: true;
492
+ tertiary: true;
491
493
  }
492
494
  }
493
- type ButtonVariant = 'primary' | 'secondary' | 'destructive' | 'link' | 'linkColor';
495
+ type ButtonVariant = 'primary' | 'secondary' | 'destructive' | 'link' | 'linkColor' | 'tertiary';
494
496
  type ButtonSize = 'small' | 'medium';
495
- interface NeoButtonProps extends Omit<ButtonBaseProps, 'children'> {
497
+ type NeoButtonOwnProps = {
496
498
  /**
497
499
  * The visual variant of the button
498
500
  * @default "primary"
@@ -522,14 +524,25 @@ interface NeoButtonProps extends Omit<ButtonBaseProps, 'children'> {
522
524
  * URL to link to. When provided, the button renders as a link element.
523
525
  */
524
526
  href?: string;
525
- }
527
+ /**
528
+ * Icon placed before the button label
529
+ */
530
+ startIcon?: ReactNode;
531
+ /**
532
+ * Icon placed after the button label
533
+ */
534
+ endIcon?: ReactNode;
535
+ };
536
+ type NeoButtonProps<C extends ElementType = typeof ButtonBase__default> = NeoButtonOwnProps & Omit<React__default.ComponentPropsWithoutRef<C>, keyof NeoButtonOwnProps> & {
537
+ component?: C;
538
+ };
526
539
  /**
527
540
  * NeoButton - Text button component based on MUI ButtonBase
528
541
  *
529
542
  * @figma https://www.figma.com/design/fQTkGSFbYyE7LiHuQJsENC/Neo---Moderne-Design-system---2025?node-id=4086-7590
530
543
  *
531
544
  * Figma Props Mapping:
532
- * - Hierarchy (Primary|Secondary|Destructive|Link|Link Color) → variant prop
545
+ * - Hierarchy (Primary|Secondary|Destructive|Link|Link Color|Tertiary) → variant prop
533
546
  * - Size (Small|Medium) → size prop
534
547
  * - State=Disabled → disabled prop
535
548
  * - State=Loading → loading prop
@@ -537,10 +550,10 @@ interface NeoButtonProps extends Omit<ButtonBaseProps, 'children'> {
537
550
  * - State=Pressed → CSS :active
538
551
  * - State=Focused → CSS :focus-visible
539
552
  */
540
- declare const NeoButton: {
541
- ({ variant, size, loading, children, disabled, ...props }: NeoButtonProps): react_jsx_runtime.JSX.Element;
542
- displayName: string;
543
- };
553
+ declare function NeoButton<C extends ElementType = typeof ButtonBase__default>({ variant, size, loading, children, disabled, startIcon, endIcon, ...rest }: NeoButtonProps<C>): react_jsx_runtime.JSX.Element;
554
+ declare namespace NeoButton {
555
+ var displayName: string;
556
+ }
544
557
 
545
558
  type ButtonGroupSize = 'small' | 'medium';
546
559
  interface NeoButtonGroupProps extends Omit<ButtonGroupProps, 'size' | 'variant'> {
@@ -1646,6 +1659,41 @@ declare const NeoModalFooter: {
1646
1659
  displayName: string;
1647
1660
  };
1648
1661
 
1662
+ interface NeoNavigationItemProps extends Omit<ButtonBaseProps, 'children'> {
1663
+ /**
1664
+ * Icon element to display
1665
+ */
1666
+ icon?: ReactNode;
1667
+ /**
1668
+ * Text label below the icon
1669
+ */
1670
+ label?: string;
1671
+ /**
1672
+ * Whether the item is selected/active
1673
+ * @figma State (Selected)
1674
+ * @default false
1675
+ */
1676
+ selected?: boolean;
1677
+ /**
1678
+ * Optional tag badge content (e.g., count)
1679
+ * @figma Tag
1680
+ */
1681
+ tag?: string;
1682
+ /**
1683
+ * Additional content
1684
+ */
1685
+ children?: ReactNode;
1686
+ }
1687
+ /**
1688
+ * NeoNavigationItem - Vertical navigation item with icon, label, and optional tag
1689
+ *
1690
+ * @figma https://www.figma.com/design/fQTkGSFbYyE7LiHuQJsENC/Neo---Moderne-Design-system---2025?node-id=8455-6120
1691
+ */
1692
+ declare const NeoNavigationItem: {
1693
+ ({ icon, label, selected, tag, children, ...props }: NeoNavigationItemProps): react_jsx_runtime.JSX.Element;
1694
+ displayName: string;
1695
+ };
1696
+
1649
1697
  /**
1650
1698
  * Breadcrumb item configuration
1651
1699
  */
@@ -1962,6 +2010,25 @@ declare const NeoRadio: {
1962
2010
  displayName: string;
1963
2011
  };
1964
2012
 
2013
+ interface NeoSearchChipProps extends Omit<InputBaseProps, 'startAdornment' | 'endAdornment' | 'type'> {
2014
+ /**
2015
+ * Handler for clearing the search value (shows X icon when provided and value is non-empty)
2016
+ */
2017
+ onClear?: () => void;
2018
+ }
2019
+ /**
2020
+ * NeoSearchChip - Pill-shaped search input for inline search functionality.
2021
+ *
2022
+ * @example
2023
+ * <NeoSearchChip placeholder="Search titles" value={query} onChange={handleChange} onClear={handleClear} />
2024
+ *
2025
+ * @figma https://www.figma.com/design/fQTkGSFbYyE7LiHuQJsENC?node-id=8542-921
2026
+ */
2027
+ declare const NeoSearchChip: {
2028
+ ({ onClear, value, ...props }: NeoSearchChipProps): react_jsx_runtime.JSX.Element;
2029
+ displayName: string;
2030
+ };
2031
+
1965
2032
  /**
1966
2033
  * Extended props for NeoSkeleton component
1967
2034
  */
@@ -2544,7 +2611,7 @@ declare const NeoTooltip: {
2544
2611
  displayName: string;
2545
2612
  };
2546
2613
 
2547
- declare const StyledToggleButton: StyledComponent<_mui_material_ToggleButton.ToggleButtonOwnProps & Omit<_mui_material_ButtonBase.ButtonBaseOwnProps, "classes"> & _mui_material_OverridableComponent.CommonProps & Omit<React$1.DetailedHTMLProps<React$1.ButtonHTMLAttributes<HTMLButtonElement>, HTMLButtonElement>, "style" | "color" | "size" | "children" | "sx" | "className" | "tabIndex" | "onChange" | "onClick" | "classes" | "action" | "centerRipple" | "disabled" | "disableRipple" | "disableTouchRipple" | "focusRipple" | "focusVisibleClassName" | "LinkComponent" | "onFocusVisible" | "TouchRippleProps" | "touchRippleRef" | "disableFocusRipple" | "value" | "fullWidth" | "selected"> & _mui_system.MUIStyledCommonProps<_mui_material_styles.Theme>, {}, {}>;
2614
+ declare const StyledToggleButton: StyledComponent<_mui_material_ToggleButton.ToggleButtonOwnProps & Omit<ButtonBase.ButtonBaseOwnProps, "classes"> & _mui_material_OverridableComponent.CommonProps & Omit<React$1.DetailedHTMLProps<React$1.ButtonHTMLAttributes<HTMLButtonElement>, HTMLButtonElement>, "style" | "color" | "size" | "children" | "sx" | "className" | "tabIndex" | "onChange" | "onClick" | "classes" | "action" | "centerRipple" | "disabled" | "disableRipple" | "disableTouchRipple" | "focusRipple" | "focusVisibleClassName" | "LinkComponent" | "onFocusVisible" | "TouchRippleProps" | "touchRippleRef" | "disableFocusRipple" | "value" | "fullWidth" | "selected"> & _mui_system.MUIStyledCommonProps<_mui_material_styles.Theme>, {}, {}>;
2548
2615
  interface NeoTypologyControlProps extends Omit<ToggleButtonGroupProps, 'orientation'> {
2549
2616
  }
2550
2617
  /**
@@ -2804,5 +2871,5 @@ declare module '@mui/x-data-grid-pro' {
2804
2871
 
2805
2872
  declare const version: string
2806
2873
 
2807
- export { ActivityScene, CIRCLE_RADIUS, NeoActivityHeader, NeoActivityIndicatorCell, NeoAvatar, NeoBadge, NeoBanner, NeoBreadcrumbLink, NeoBreadcrumbs, NeoButton, NeoButtonGroup, NeoCheckbox, NeoCodeSnippet, NeoDataGrid, NeoDataGridCellContent, NeoDataGridColumnsButton, NeoDataGridColumnsPanel, NeoDataGridFilterPanel, NeoDataGridFilterPanelAddIcon, NeoDataGridFilterPanelDeleteIcon, NeoDataGridFilterPanelRemoveAllIcon, NeoDataGridFiltersButton, NeoDataGridHeaderLabel, NeoSelect as NeoDataGridSelect, NeoDatePicker, NeoDivider, NeoDot, NeoFilterChip, NeoFooter, NeoIconButton, NeoInfiniteScrollGrid, NeoInputField, NeoListItem, NeoListItemButton, NeoLoadingSpinner, NeoMarketplaceCard, NeoMenu, NeoMenuItem, NeoModal, NeoModalContent, NeoModalFooter, NeoModalHeader, NeoMultiBadgesCell, NeoPageContent, NeoPaginatedGrid, NeoProgressbar, NeoQuickFilter, NeoRadio, NeoSelect, NeoMenuItem as NeoSelectOption, NeoSkeleton, NeoStatusBadgeCell, NeoStatusBanner, NeoTab, NeoTabs, NeoTag, NeoToast, NeoToastButton, NeoToggle, NeoToolbar, NeoTooltip, StyledToggleButton as NeoTypologyButton, NeoTypologyControl, NeoUserAvatarCell, SortedAscendingIcon, SortedDescendingIcon, UnsortedIcon, getDataGridHeaderStyles, version };
2808
- export type { ActivityColor, ActivityEvent, ActivityHeaderSize, BreadcrumbItem, DataGridSize, NeoActivityHeaderProps, NeoActivityIndicatorCellProps, NeoAvatarProps, NeoBadgeProps, NeoBannerProps, NeoBreadcrumbLinkProps, NeoBreadcrumbsProps, NeoButtonGroupProps, NeoButtonProps, NeoCheckboxProps, NeoCodeSnippetProps, NeoDataGridCellContentProps, NeoDataGridHeaderLabelProps, NeoDataGridProps, NeoDatePickerProps, NeoDividerProps, NeoDotProps, NeoFilterChipProps, NeoFooterProps, NeoIconButtonProps, NeoInfiniteScrollGridProps, NeoInputFieldProps, NeoListItemButtonProps, NeoListItemProps, NeoLoadingSpinnerProps, NeoMarketplaceCardProps, NeoMenuItemProps, NeoMenuProps, NeoModalContentProps, NeoModalFooterProps, NeoModalHeaderProps, NeoModalProps, NeoMultiBadgesCellProps, NeoPageContentProps, NeoPaginatedGridProps, NeoProgressbarProps, NeoQuickFilterProps, NeoRadioProps, NeoSelectProps, NeoSkeletonProps, NeoStatusBadgeCellProps, NeoStatusBannerProps, NeoTabProps, NeoTagProps, NeoToastProps, NeoToggleProps, NeoToolbarProps, NeoTooltipProps, NeoTypologyControlProps, NeoUserAvatarCellProps };
2874
+ export { ActivityScene, CIRCLE_RADIUS, NeoActivityHeader, NeoActivityIndicatorCell, NeoAvatar, NeoBadge, NeoBanner, NeoBreadcrumbLink, NeoBreadcrumbs, NeoButton, NeoButtonGroup, NeoCheckbox, NeoCodeSnippet, NeoDataGrid, NeoDataGridCellContent, NeoDataGridColumnsButton, NeoDataGridColumnsPanel, NeoDataGridFilterPanel, NeoDataGridFilterPanelAddIcon, NeoDataGridFilterPanelDeleteIcon, NeoDataGridFilterPanelRemoveAllIcon, NeoDataGridFiltersButton, NeoDataGridHeaderLabel, NeoSelect as NeoDataGridSelect, NeoDatePicker, NeoDivider, NeoDot, NeoFilterChip, NeoFooter, NeoIconButton, NeoInfiniteScrollGrid, NeoInputField, NeoListItem, NeoListItemButton, NeoLoadingSpinner, NeoMarketplaceCard, NeoMenu, NeoMenuItem, NeoModal, NeoModalContent, NeoModalFooter, NeoModalHeader, NeoMultiBadgesCell, NeoNavigationItem, NeoPageContent, NeoPaginatedGrid, NeoProgressbar, NeoQuickFilter, NeoRadio, NeoSearchChip, NeoSelect, NeoMenuItem as NeoSelectOption, NeoSkeleton, NeoStatusBadgeCell, NeoStatusBanner, NeoTab, NeoTabs, NeoTag, NeoToast, NeoToastButton, NeoToggle, NeoToolbar, NeoTooltip, StyledToggleButton as NeoTypologyButton, NeoTypologyControl, NeoUserAvatarCell, SortedAscendingIcon, SortedDescendingIcon, UnsortedIcon, getDataGridHeaderStyles, version };
2875
+ export type { ActivityColor, ActivityEvent, ActivityHeaderSize, BreadcrumbItem, DataGridSize, NeoActivityHeaderProps, NeoActivityIndicatorCellProps, NeoAvatarProps, NeoBadgeProps, NeoBannerProps, NeoBreadcrumbLinkProps, NeoBreadcrumbsProps, NeoButtonGroupProps, NeoButtonProps, NeoCheckboxProps, NeoCodeSnippetProps, NeoDataGridCellContentProps, NeoDataGridHeaderLabelProps, NeoDataGridProps, NeoDatePickerProps, NeoDividerProps, NeoDotProps, NeoFilterChipProps, NeoFooterProps, NeoIconButtonProps, NeoInfiniteScrollGridProps, NeoInputFieldProps, NeoListItemButtonProps, NeoListItemProps, NeoLoadingSpinnerProps, NeoMarketplaceCardProps, NeoMenuItemProps, NeoMenuProps, NeoModalContentProps, NeoModalFooterProps, NeoModalHeaderProps, NeoModalProps, NeoMultiBadgesCellProps, NeoNavigationItemProps, NeoPageContentProps, NeoPaginatedGridProps, NeoProgressbarProps, NeoQuickFilterProps, NeoRadioProps, NeoSearchChipProps, NeoSelectProps, NeoSkeletonProps, NeoStatusBadgeCellProps, NeoStatusBannerProps, NeoTabProps, NeoTagProps, NeoToastProps, NeoToggleProps, NeoToolbarProps, NeoTooltipProps, NeoTypologyControlProps, NeoUserAvatarCellProps };
package/dist/index.esm.js CHANGED
@@ -1,5 +1,5 @@
1
1
  import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
2
- import { semanticColors, colors, spacing, typography, borderRadius, shadows } from '@moderneinc/neo-design';
2
+ import { shadows, semanticColors, colors, spacing, typography, borderRadius } from '@moderneinc/neo-design';
3
3
  import Box from '@mui/material/Box';
4
4
  import { styled, alpha } from '@mui/material/styles';
5
5
  import Avatar from '@mui/material/Avatar';
@@ -7,7 +7,7 @@ import Chip, { chipClasses } from '@mui/material/Chip';
7
7
  import SvgIcon, { svgIconClasses } from '@mui/material/SvgIcon';
8
8
  import Alert, { alertClasses } from '@mui/material/Alert';
9
9
  import IconButton, { iconButtonClasses } from '@mui/material/IconButton';
10
- import { forwardRef, createElement, useState, useMemo, useRef, useEffect } from 'react';
10
+ import React, { forwardRef, createElement, useState, useMemo, useRef, useEffect } from 'react';
11
11
  import Breadcrumbs, { breadcrumbsClasses } from '@mui/material/Breadcrumbs';
12
12
  import Link from '@mui/material/Link';
13
13
  import ButtonBase, { buttonBaseClasses } from '@mui/material/ButtonBase';
@@ -60,21 +60,39 @@ import Switch, { switchClasses } from '@mui/material/Switch';
60
60
  import ToggleButton, { toggleButtonClasses } from '@mui/material/ToggleButton';
61
61
  import ToggleButtonGroup, { toggleButtonGroupClasses } from '@mui/material/ToggleButtonGroup';
62
62
 
63
+ const focusRingShadow$2 = `${shadows.focusWhite1.x}px ${shadows.focusWhite1.y}px ${shadows.focusWhite1.blur}px ${shadows.focusWhite1.spread}px ${shadows.focusWhite1.shadow}, ${shadows.focusBlue2.x}px ${shadows.focusBlue2.y}px ${shadows.focusBlue2.blur}px ${shadows.focusBlue2.spread}px ${shadows.focusBlue2.shadow}`;
63
64
  // biome-ignore lint/suspicious/noExplicitAny: Type cast required to override MUI Avatar variant type without global augmentation
64
65
  const StyledAvatar = styled(Avatar, {
65
66
  shouldForwardProp: prop => prop !== 'size' && prop !== 'variant',
66
67
  })(({ theme, size = 'medium', variant = 'circular' }) => ({
68
+ boxSizing: 'border-box',
67
69
  borderRadius: borderRadius.full,
68
70
  fontSize: theme.typography.pxToRem(typography.fontSize.xs),
69
71
  fontWeight: typography.fontWeight.regular,
70
72
  lineHeight: 1.5,
71
- // Size variants
72
- ...(size === 'small' && {
73
+ // Size variants — dimensions match Figma bounding boxes (border-box)
74
+ ...(size === 'small' &&
75
+ variant === 'circular' && {
76
+ width: spacing.spacing_4,
77
+ height: spacing.spacing_4,
78
+ fontSize: theme.typography.pxToRem(typography.fontSize.xs),
79
+ }),
80
+ ...(size === 'small' &&
81
+ variant === 'initials' && {
73
82
  width: spacing.spacing_2_1_2,
74
83
  height: spacing.spacing_2_1_2,
75
84
  fontSize: theme.typography.pxToRem(typography.fontSize.xs),
76
85
  }),
77
- ...(size === 'medium' && {
86
+ // Medium circular fills its AvatarContainer (container owns the 44px dimension)
87
+ ...(size === 'medium' &&
88
+ variant === 'circular' && {
89
+ width: '100%',
90
+ height: '100%',
91
+ fontSize: theme.typography.pxToRem(typography.fontSize.sm),
92
+ }),
93
+ // Medium initials has no container, so it owns its 44px dimension
94
+ ...(size === 'medium' &&
95
+ variant === 'initials' && {
78
96
  width: spacing.spacing_5_1_2,
79
97
  height: spacing.spacing_5_1_2,
80
98
  fontSize: theme.typography.pxToRem(typography.fontSize.sm),
@@ -90,20 +108,29 @@ const StyledAvatar = styled(Avatar, {
90
108
  backgroundColor: 'transparent',
91
109
  border: `2px solid ${semanticColors.surfaces.white}`,
92
110
  }),
111
+ '&:focus-visible': {
112
+ outline: 'none',
113
+ boxShadow: focusRingShadow$2,
114
+ },
93
115
  }));
94
116
  const AvatarContainer = styled(Box)(({ size = 'medium' }) => ({
117
+ boxSizing: 'border-box',
95
118
  ...(size === 'medium' && {
96
119
  width: spacing.spacing_5_1_2,
97
120
  height: spacing.spacing_5_1_2,
98
121
  backgroundColor: semanticColors.surfaces.white,
99
122
  borderRadius: borderRadius.full,
100
- padding: spacing.spacing_1_2,
123
+ padding: spacing.spacing_1_4,
101
124
  display: 'flex',
102
125
  alignItems: 'center',
103
126
  justifyContent: 'center',
104
127
  overflow: 'hidden',
105
128
  boxShadow: `${shadows.neutralSmall.x}px ${shadows.neutralSmall.y}px ${shadows.neutralSmall.blur}px ${shadows.neutralSmall.spread}px ${shadows.neutralSmall.shadow}`,
106
129
  }),
130
+ '&:focus-within': {
131
+ outline: 'none',
132
+ boxShadow: focusRingShadow$2,
133
+ },
107
134
  }));
108
135
  /**
109
136
  * NeoAvatar - User avatar component based on MUI Avatar
@@ -112,8 +139,9 @@ const AvatarContainer = styled(Box)(({ size = 'medium' }) => ({
112
139
  *
113
140
  * Figma Props Mapping:
114
141
  * - Figma Type "Initials" → variant="initials", size="small" (20px)
115
- * - Figma Type "Small" → variant="circular", size="small" (20px with image)
142
+ * - Figma Type "Small" → variant="circular", size="small" (32px with image)
116
143
  * - Figma Type "Medium" → variant="circular", size="medium" (44px white container with image)
144
+ * - State: Focus → CSS :focus-visible ring (2px white inner + 4px blue outer)
117
145
  * - State: Hover (tooltip) → Wrap component with MUI Tooltip
118
146
  *
119
147
  * Usage:
@@ -1262,6 +1290,28 @@ const StyledButtonBase$1 = styled(ButtonBase, {
1262
1290
  },
1263
1291
  }),
1264
1292
  },
1293
+ tertiary: {
1294
+ backgroundColor: 'transparent',
1295
+ color: semanticColors.typography.input.default,
1296
+ border: 'none',
1297
+ padding: 0,
1298
+ lineHeight: 1,
1299
+ '&:hover': {
1300
+ backgroundColor: 'transparent',
1301
+ color: semanticColors.buttons.tertiary.hover,
1302
+ },
1303
+ '&:active': {
1304
+ color: semanticColors.buttons.tertiary.pressed,
1305
+ },
1306
+ ...(loading
1307
+ ? {}
1308
+ : {
1309
+ [`&.${buttonBaseClasses.disabled}`]: {
1310
+ backgroundColor: 'transparent',
1311
+ color: semanticColors.buttons.tertiary.disabled,
1312
+ },
1313
+ }),
1314
+ },
1265
1315
  };
1266
1316
  return {
1267
1317
  ...baseStyles,
@@ -1276,6 +1326,7 @@ const LoadingSpinner = styled(CircularProgress)(({ theme, $variant }) => {
1276
1326
  destructive: theme.palette.common.white,
1277
1327
  link: semanticColors.buttons.primary.default,
1278
1328
  linkColor: semanticColors.buttons.primary.default,
1329
+ tertiary: semanticColors.buttons.tertiary.default,
1279
1330
  };
1280
1331
  return {
1281
1332
  color: spinnerColors[$variant],
@@ -1287,7 +1338,7 @@ const LoadingSpinner = styled(CircularProgress)(({ theme, $variant }) => {
1287
1338
  * @figma https://www.figma.com/design/fQTkGSFbYyE7LiHuQJsENC/Neo---Moderne-Design-system---2025?node-id=4086-7590
1288
1339
  *
1289
1340
  * Figma Props Mapping:
1290
- * - Hierarchy (Primary|Secondary|Destructive|Link|Link Color) → variant prop
1341
+ * - Hierarchy (Primary|Secondary|Destructive|Link|Link Color|Tertiary) → variant prop
1291
1342
  * - Size (Small|Medium) → size prop
1292
1343
  * - State=Disabled → disabled prop
1293
1344
  * - State=Loading → loading prop
@@ -1295,9 +1346,9 @@ const LoadingSpinner = styled(CircularProgress)(({ theme, $variant }) => {
1295
1346
  * - State=Pressed → CSS :active
1296
1347
  * - State=Focused → CSS :focus-visible
1297
1348
  */
1298
- const NeoButton = ({ variant = 'primary', size = 'medium', loading = false, children, disabled, ...props }) => {
1299
- return (jsx(StyledButtonBase$1, { variant: variant, size: size, loading: loading, disabled: disabled || loading, ...props, children: loading ? jsx(LoadingSpinner, { "$variant": variant, size: size === 'small' ? 16 : 20 }) : children }));
1300
- };
1349
+ function NeoButton({ variant = 'primary', size = 'medium', loading = false, children, disabled, startIcon, endIcon, ...rest }) {
1350
+ return (jsx(StyledButtonBase$1, { variant: variant, size: size, loading: loading, disabled: disabled || loading, ...rest, children: loading ? (jsx(LoadingSpinner, { "$variant": variant, size: size === 'small' ? 16 : 20 })) : (jsxs(React.Fragment, { children: [startIcon, children, endIcon] })) }));
1351
+ }
1301
1352
  NeoButton.displayName = 'NeoButton';
1302
1353
 
1303
1354
  /**
@@ -1457,6 +1508,8 @@ const HelperText$2 = styled('span')(({ theme, size = 'medium' }) => ({
1457
1508
  lineHeight: size === 'xs' ? 1.5 : size === 'small' ? 1.4 : 1.5,
1458
1509
  color: semanticColors.typography.bodySecondary,
1459
1510
  }));
1511
+ // Figma-exact border radius for xs checkbox — no matching design token
1512
+ const FIGMA_XS_BORDER_RADIUS = 1;
1460
1513
  const StyledCheckbox = styled(Checkbox, {
1461
1514
  shouldForwardProp: prop => prop !== 'size',
1462
1515
  })(({ size = 'medium' }) => {
@@ -1464,8 +1517,7 @@ const StyledCheckbox = styled(Checkbox, {
1464
1517
  const sizeConfig = {
1465
1518
  xs: {
1466
1519
  size: 12,
1467
- // biome-ignore plugin: Figma-exact 1px for xs — no matching token
1468
- borderRadius: 1, // From Figma: 1px for xs
1520
+ borderRadius: FIGMA_XS_BORDER_RADIUS,
1469
1521
  },
1470
1522
  small: {
1471
1523
  size: 16,
@@ -1758,13 +1810,14 @@ const ColumnItemContainer = styled(Box)(({ theme }) => ({
1758
1810
  paddingLeft: theme.spacing(0.75),
1759
1811
  paddingRight: theme.spacing(0.75),
1760
1812
  }));
1813
+ // Figma-exact border radius for menu items — no matching design token
1814
+ const MENU_ITEM_BORDER_RADIUS = 6;
1761
1815
  const MenuItemContent$1 = styled('div')(({ theme }) => ({
1762
1816
  display: 'flex',
1763
1817
  alignItems: 'center',
1764
1818
  gap: theme.spacing(1),
1765
1819
  padding: theme.spacing(1),
1766
- // biome-ignore plugin: no exact token for 6px
1767
- borderRadius: 6,
1820
+ borderRadius: MENU_ITEM_BORDER_RADIUS,
1768
1821
  width: '100%',
1769
1822
  '&:hover': {
1770
1823
  backgroundColor: semanticColors.surfaces.listHover,
@@ -3532,7 +3585,7 @@ const NeoDot = ({ size = 'medium', variant = 'solid', color = 'neutral', ...prop
3532
3585
  };
3533
3586
  NeoDot.displayName = 'NeoDot';
3534
3587
 
3535
- const focusRing = `${shadows.focusWhite1.x}px ${shadows.focusWhite1.y}px ${shadows.focusWhite1.blur}px ${shadows.focusWhite1.spread}px ${shadows.focusWhite1.shadow}, ${shadows.focusBlue2.x}px ${shadows.focusBlue2.y}px ${shadows.focusBlue2.blur}px ${shadows.focusBlue2.spread}px ${shadows.focusBlue2.shadow}`;
3588
+ const focusRing$1 = `${shadows.focusWhite1.x}px ${shadows.focusWhite1.y}px ${shadows.focusWhite1.blur}px ${shadows.focusWhite1.spread}px ${shadows.focusWhite1.shadow}, ${shadows.focusBlue2.x}px ${shadows.focusBlue2.y}px ${shadows.focusBlue2.blur}px ${shadows.focusBlue2.spread}px ${shadows.focusBlue2.shadow}`;
3536
3589
  const filterChipOnlyProps = ['selected', 'expanded', 'selectedLabel', 'count', 'onClear'];
3537
3590
  const StyledChip = styled(Chip, {
3538
3591
  shouldForwardProp: prop => !filterChipOnlyProps.includes(prop),
@@ -3569,7 +3622,7 @@ const StyledChip = styled(Chip, {
3569
3622
  backgroundColor: semanticColors.buttons.secondary.hoverBackground,
3570
3623
  },
3571
3624
  [`&.${chipClasses.focusVisible}`]: {
3572
- boxShadow: focusRing,
3625
+ boxShadow: focusRing$1,
3573
3626
  backgroundColor: selected
3574
3627
  ? semanticColors.buttons.secondary.pressedBackground
3575
3628
  : semanticColors.surfaces.white,
@@ -4740,7 +4793,7 @@ const HeaderTitle = styled('span', {
4740
4793
  shouldForwardProp: prop => prop !== 'cardTheme',
4741
4794
  })(({ cardTheme = 'light' }) => ({
4742
4795
  fontFamily: `${typography.fontFamily.heading}, sans-serif`,
4743
- fontWeight: 600,
4796
+ fontWeight: typography.fontWeight.semiBold,
4744
4797
  fontSize: typography.fontSize.h6,
4745
4798
  lineHeight: 1.4,
4746
4799
  color: cardTheme === 'light' ? colors.grey[800] : semanticColors.surfaces.white,
@@ -4750,7 +4803,7 @@ const Description = styled('p', {
4750
4803
  shouldForwardProp: prop => prop !== 'cardTheme',
4751
4804
  })(({ cardTheme = 'light' }) => ({
4752
4805
  fontFamily: `${typography.fontFamily.body}, sans-serif`,
4753
- fontWeight: 400,
4806
+ fontWeight: typography.fontWeight.regular,
4754
4807
  fontSize: typography.fontSize.xs,
4755
4808
  lineHeight: 1.5,
4756
4809
  color: cardTheme === 'light' ? colors.grey[800] : semanticColors.surfaces.white,
@@ -5653,6 +5706,72 @@ const NeoRadio = ({ size = 'medium', label, helperText, disabled, ...props }) =>
5653
5706
  };
5654
5707
  NeoRadio.displayName = 'NeoRadio';
5655
5708
 
5709
+ const focusRing = `${shadows.focusWhite1.x}px ${shadows.focusWhite1.y}px ${shadows.focusWhite1.blur}px ${shadows.focusWhite1.spread}px ${shadows.focusWhite1.shadow}, ${shadows.focusBlue2.x}px ${shadows.focusBlue2.y}px ${shadows.focusBlue2.blur}px ${shadows.focusBlue2.spread}px ${shadows.focusBlue2.shadow}`;
5710
+ const StyledSearchChip = styled(InputBase)(({ theme }) => ({
5711
+ borderRadius: borderRadius.full,
5712
+ border: `1px solid ${semanticColors.buttons.secondary.defaultBorder}`,
5713
+ backgroundColor: semanticColors.surfaces.white,
5714
+ height: 40,
5715
+ padding: `0 ${spacing.spacing_1_1_2}px`,
5716
+ gap: spacing.spacing_1_2,
5717
+ fontSize: theme.typography.pxToRem(typography.fontSize.sm),
5718
+ fontWeight: typography.fontWeight.medium,
5719
+ lineHeight: 1,
5720
+ color: semanticColors.typography.input.default,
5721
+ cursor: 'text',
5722
+ boxSizing: 'border-box',
5723
+ [`& .${inputBaseClasses.input}`]: {
5724
+ padding: '0 2px',
5725
+ height: 'auto',
5726
+ lineHeight: 1,
5727
+ '&::placeholder': {
5728
+ color: semanticColors.typography.input.placeholder,
5729
+ opacity: 1,
5730
+ },
5731
+ // Hide native browser clear button for type="search" (we provide our own)
5732
+ '&::-webkit-search-cancel-button': {
5733
+ WebkitAppearance: 'none',
5734
+ },
5735
+ },
5736
+ '&:hover': {
5737
+ backgroundColor: semanticColors.buttons.secondary.hoverBackground,
5738
+ },
5739
+ [`&.${inputBaseClasses.focused}`]: {
5740
+ boxShadow: focusRing,
5741
+ backgroundColor: semanticColors.surfaces.white,
5742
+ },
5743
+ }));
5744
+ const ClearButton = styled(ButtonBase)({
5745
+ display: 'inline-flex',
5746
+ alignItems: 'center',
5747
+ justifyContent: 'center',
5748
+ width: 16,
5749
+ height: 16,
5750
+ padding: 0,
5751
+ border: 'none',
5752
+ backgroundColor: 'transparent',
5753
+ cursor: 'pointer',
5754
+ color: semanticColors.icons.default,
5755
+ flexShrink: 0,
5756
+ borderRadius: borderRadius.full,
5757
+ '&:hover': {
5758
+ backgroundColor: semanticColors.buttons.secondary.hoverBackground,
5759
+ },
5760
+ });
5761
+ /**
5762
+ * NeoSearchChip - Pill-shaped search input for inline search functionality.
5763
+ *
5764
+ * @example
5765
+ * <NeoSearchChip placeholder="Search titles" value={query} onChange={handleChange} onClear={handleClear} />
5766
+ *
5767
+ * @figma https://www.figma.com/design/fQTkGSFbYyE7LiHuQJsENC?node-id=8542-921
5768
+ */
5769
+ const NeoSearchChip = ({ onClear, value, ...props }) => {
5770
+ const hasValue = Boolean(value && String(value).length > 0);
5771
+ return (jsx(StyledSearchChip, { type: "search", value: value, startAdornment: jsx(Search, { size: 16, color: semanticColors.icons.placeholder, style: { flexShrink: 0 } }), endAdornment: hasValue && onClear ? (jsx(ClearButton, { type: "button", onClick: onClear, "aria-label": "Clear search", children: jsx(X, { size: 16 }) })) : undefined, ...props }));
5772
+ };
5773
+ NeoSearchChip.displayName = 'NeoSearchChip';
5774
+
5656
5775
  const StyledSkeleton = styled(Skeleton, {
5657
5776
  shouldForwardProp: prop => prop !== 'colorTheme' && prop !== 'position',
5658
5777
  })(({ theme, colorTheme = 'light', position = 'start' }) => ({
@@ -6415,6 +6534,8 @@ const NeoTooltip = ({ variant = 'light', title, description, children, arrow = f
6415
6534
  };
6416
6535
  NeoTooltip.displayName = 'NeoTooltip';
6417
6536
 
6537
+ // Figma-exact border radius for toggle buttons — no matching design token
6538
+ const TOGGLE_BUTTON_BORDER_RADIUS = 14;
6418
6539
  const StyledToggleButtonGroup = styled(ToggleButtonGroup)(({ theme }) => ({
6419
6540
  backgroundColor: colors.grey[50],
6420
6541
  padding: theme.spacing(0.625, 0.875),
@@ -6422,17 +6543,14 @@ const StyledToggleButtonGroup = styled(ToggleButtonGroup)(({ theme }) => ({
6422
6543
  gap: 0,
6423
6544
  [`& .${toggleButtonGroupClasses.grouped}`]: {
6424
6545
  border: 'none',
6425
- // biome-ignore plugin: no exact token for 14px
6426
- borderRadius: 14,
6546
+ borderRadius: TOGGLE_BUTTON_BORDER_RADIUS,
6427
6547
  margin: 0,
6428
6548
  '&:not(:first-of-type)': {
6429
- // biome-ignore plugin: no exact token for 14px
6430
- borderRadius: 14,
6549
+ borderRadius: TOGGLE_BUTTON_BORDER_RADIUS,
6431
6550
  marginLeft: 0,
6432
6551
  },
6433
6552
  '&:not(:last-of-type)': {
6434
- // biome-ignore plugin: no exact token for 14px
6435
- borderRadius: 14,
6553
+ borderRadius: TOGGLE_BUTTON_BORDER_RADIUS,
6436
6554
  },
6437
6555
  },
6438
6556
  }));
@@ -6485,5 +6603,5 @@ NeoTypologyControl.displayName = 'NeoTypologyControl';
6485
6603
 
6486
6604
  const version = '0.0.0-development';
6487
6605
 
6488
- export { ActivityScene, CIRCLE_RADIUS, NeoActivityHeader, NeoActivityIndicatorCell, NeoAvatar, NeoBadge, NeoBanner, NeoBreadcrumbLink, NeoBreadcrumbs, NeoButton, NeoButtonGroup, NeoCheckbox, NeoCodeSnippet, NeoDataGrid, NeoDataGridCellContent, NeoDataGridColumnsButton, NeoDataGridColumnsPanel, NeoDataGridFilterPanel, NeoDataGridFilterPanelAddIcon, NeoDataGridFilterPanelDeleteIcon, NeoDataGridFilterPanelRemoveAllIcon, NeoDataGridFiltersButton, NeoDataGridHeaderLabel, NeoSelect as NeoDataGridSelect, NeoDatePicker, NeoDivider, NeoDot, NeoFilterChip, NeoFooter, NeoIconButton, NeoIconWrapper, NeoInfiniteScrollGrid, NeoInputField, NeoListItem, NeoListItemButton, NeoLoadingSpinner, NeoMarketplaceCard, NeoMarketplaceLargeCard, NeoMenu, NeoMenuItem, NeoModal, NeoModalContent, NeoModalFooter, NeoModalHeader, NeoMultiBadgesCell, NeoNavigationItem, NeoPageContent, NeoPaginatedGrid, NeoProgressbar, NeoQuickFilter, NeoRadio, NeoSelect, NeoMenuItem as NeoSelectOption, NeoSkeleton, NeoStatusBadgeCell, NeoStatusBanner, NeoTab, NeoTabs, NeoTag, NeoToast, NeoToastButton, NeoToggle, NeoToolbar, NeoTooltip, StyledToggleButton as NeoTypologyButton, NeoTypologyControl, NeoUserAvatarCell, SortedAscendingIcon, SortedDescendingIcon, UnsortedIcon, getDataGridHeaderStyles, neoRowHeights, version };
6606
+ export { ActivityScene, CIRCLE_RADIUS, NeoActivityHeader, NeoActivityIndicatorCell, NeoAvatar, NeoBadge, NeoBanner, NeoBreadcrumbLink, NeoBreadcrumbs, NeoButton, NeoButtonGroup, NeoCheckbox, NeoCodeSnippet, NeoDataGrid, NeoDataGridCellContent, NeoDataGridColumnsButton, NeoDataGridColumnsPanel, NeoDataGridFilterPanel, NeoDataGridFilterPanelAddIcon, NeoDataGridFilterPanelDeleteIcon, NeoDataGridFilterPanelRemoveAllIcon, NeoDataGridFiltersButton, NeoDataGridHeaderLabel, NeoSelect as NeoDataGridSelect, NeoDatePicker, NeoDivider, NeoDot, NeoFilterChip, NeoFooter, NeoIconButton, NeoIconWrapper, NeoInfiniteScrollGrid, NeoInputField, NeoListItem, NeoListItemButton, NeoLoadingSpinner, NeoMarketplaceCard, NeoMarketplaceLargeCard, NeoMenu, NeoMenuItem, NeoModal, NeoModalContent, NeoModalFooter, NeoModalHeader, NeoMultiBadgesCell, NeoNavigationItem, NeoPageContent, NeoPaginatedGrid, NeoProgressbar, NeoQuickFilter, NeoRadio, NeoSearchChip, NeoSelect, NeoMenuItem as NeoSelectOption, NeoSkeleton, NeoStatusBadgeCell, NeoStatusBanner, NeoTab, NeoTabs, NeoTag, NeoToast, NeoToastButton, NeoToggle, NeoToolbar, NeoTooltip, StyledToggleButton as NeoTypologyButton, NeoTypologyControl, NeoUserAvatarCell, SortedAscendingIcon, SortedDescendingIcon, UnsortedIcon, getDataGridHeaderStyles, neoRowHeights, version };
6489
6607
  //# sourceMappingURL=index.esm.js.map