Skip to content

feat: drawer component#1997

Draft
Adzouz wants to merge 8 commits intomainfrom
feat/drawer
Draft

feat: drawer component#1997
Adzouz wants to merge 8 commits intomainfrom
feat/drawer

Conversation

@Adzouz
Copy link
Copy Markdown
Contributor

@Adzouz Adzouz commented Jan 27, 2026

What does it do?

Adds a Drawer component that can be used for multiple purposes:

  • Actions drawer (used in the Content Manager on mobile)
  • Assets details (in the new Media Library revamp)
  • Upload progress popup (in the new Media Library revamp)

Inspired by https://vaul.emilkowal.ski/

Components.Drawer.Side.Bottom.Storybook.Jan.28.2026.mp4

Why is it needed?

This component will need to be integrated a few places in the CMS.

How to test it?

  • Go to Storybook > Components > Drawer
    -> Play with the settings to change the behaviour

🚀

@changeset-bot
Copy link
Copy Markdown

changeset-bot Bot commented Jan 27, 2026

⚠️ No Changeset found

Latest commit: f2b3e71

Merging this PR will not cause a version bump for any packages. If these changes should not result in a new version, you're good to go. If these changes should result in a version bump, you need to add a changeset.

This PR includes no changesets

When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

Click here to learn what changesets are, and how to add one.

Click here if you're a maintainer who wants to add a changeset to this PR

@vercel
Copy link
Copy Markdown

vercel Bot commented Jan 27, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
design-system Ready Ready Preview, Comment Feb 17, 2026 3:03pm

Request Review

@Adzouz Adzouz self-assigned this Jan 27, 2026
@Adzouz Adzouz added pr: feature This PR adds a new feature source: design-system relates to design-system package labels Jan 27, 2026
fix: update lodash to match cms version
Comment thread packages/design-system/src/components/Drawer/Drawer.tsx
Comment thread packages/design-system/src/components/Drawer/Drawer.tsx Outdated
Comment thread packages/design-system/src/components/Drawer/Drawer.tsx
Comment thread packages/design-system/src/components/Drawer/Drawer.tsx Outdated
Comment thread packages/design-system/src/components/Drawer/Drawer.tsx
Comment thread packages/design-system/src/components/Drawer/Drawer.tsx Outdated
Comment thread packages/design-system/src/styles/motion.ts Outdated
Comment thread packages/design-system/src/components/Drawer/Drawer.test.tsx Outdated
Copy link
Copy Markdown
Contributor

@markkaylor markkaylor left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hey thanks for the time invested in this. I've left a few comments mostly about favoring composition.

I'm wondering though did you consider just using vaul? I just read https://emilkowal.ski/ui/building-a-drawer-component and I feel like it solves a lot of the common problems with drawers (including animations) and already exposes a clean API. So wondering if like we do with radix we could adapt it to our design.

Comment on lines +256 to +275
const Overlay = styled(Dialog.Overlay)<{ $isVisible: boolean }>`
background: ${(props) => setOpacity(props.theme.colors.neutral800, 0.2)};
position: fixed;
inset: 0;
z-index: ${(props) => props.theme.zIndices.overlay};
will-change: opacity;

@media (prefers-reduced-motion: no-preference) {
${({ $isVisible, theme }) =>
$isVisible
? css`
animation: ${ANIMATIONS.fadeIn} ${theme.motion.timings[OPENING_ANIMATION_DURATION]}
${theme.motion.easings.authenticMotion} forwards;
`
: css`
animation: ${ANIMATIONS.fadeOut} ${theme.motion.timings[CLOSING_ANIMATION_DURATION]}
${theme.motion.easings.easeOutQuad} forwards;
`}
}
`;
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Couldn't overlay be a composable component. I think that would also eliminate the need for any sort of isOverlayVisible prop. The consumer either composes with or they don't. That's how Radix UI does it in their example for dialog:

Image

and vaul

Image

Comment on lines +492 to +501
<ToggleButton
withTooltip={false}
label={open ? toggleLabelResolved.collapse : toggleLabelResolved.expand}
onClick={() => onOpenChange(!open)}
aria-expanded={open}
>
<ToggleIconWrapper $expanded={open} aria-hidden>
<CaretDown width="1.2rem" height="1.2rem" />
</ToggleIconWrapper>
</ToggleButton>
Copy link
Copy Markdown
Contributor

@markkaylor markkaylor Jan 29, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This to me looks like consumer code. The API gives me a Trigger and that should be enough for me to compose a "visible header" with whatever I want (title with a toggle) in this case. The consumer can decide to create a reusable header that they can pass to both Trigger and Header. This could eliminate the props: headerVisible and customToggleButton

const MyVisibleHeader = () => <div>coucou</div>

<Drawer.Root>
  <Drawer.Trigger>
     <MyVisibleHeader />
  </Drawer.Trigger>
  <Drawer.Content direction="right">
    <Drawer.Header hasClose={hasClose} hasToggle={hasToggle}>
        <MyVisibleHeader />
    </Drawer.Header>
    <Drawer.Body>
      <p>Drawer content goes here.</p>
    </Drawer.Body>
  </Drawer.Content>
</Drawer.Root>

Comment on lines +505 to +511
<Close>
{customCloseButton ?? (
<IconButton withTooltip={false} label={closeLabel}>
<Cross />
</IconButton>
)}
</Close>
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Couldn't this be a composable component that accepts children. This would eliminate hasClose and customCloseButton as props

Suggested change
<Close>
{customCloseButton ?? (
<IconButton withTooltip={false} label={closeLabel}>
<Cross />
</IconButton>
)}
</Close>
const Close = ({ children }) => {
if (children) return children
return <IconButton withTooltip={false} label={closeLabel}>
<Cross />
</IconButton>
}

Similar design to radix ui dialog:

Image

@Adzouz Adzouz marked this pull request as draft January 30, 2026 10:34
@Adzouz
Copy link
Copy Markdown
Contributor Author

Adzouz commented Jan 30, 2026

Putting it on hold for the moment to improve the component API with Mark comments

@sonarqubecloud
Copy link
Copy Markdown

Quality Gate Failed Quality Gate failed

Failed conditions
C Reliability Rating on New Code (required ≥ A)

See analysis details on SonarQube Cloud

Catch issues before they fail your Quality Gate with our IDE extension SonarQube for IDE

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

pr: feature This PR adds a new feature source: design-system relates to design-system package

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants