From 0cf696cded43cbf646d39707161cf581a4daeba3 Mon Sep 17 00:00:00 2001 From: hsiegeln <37154749+hsiegeln@users.noreply.github.com> Date: Thu, 2 Apr 2026 22:40:18 +0200 Subject: [PATCH] fix(sidebar): move search below Header, remove section chevrons MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Search input now renders between Sidebar.Header and first Section instead of above Header (fixes cameleer3-server#120) - Remove ChevronRight/ChevronDown from section headers — the entire row is already clickable, chevrons added visual noise Co-Authored-By: Claude Opus 4.6 (1M context) --- src/design-system/layout/Sidebar/Sidebar.tsx | 78 +++++++++++--------- 1 file changed, 44 insertions(+), 34 deletions(-) diff --git a/src/design-system/layout/Sidebar/Sidebar.tsx b/src/design-system/layout/Sidebar/Sidebar.tsx index 8c5080b..f154c9f 100644 --- a/src/design-system/layout/Sidebar/Sidebar.tsx +++ b/src/design-system/layout/Sidebar/Sidebar.tsx @@ -1,11 +1,9 @@ -import { type ReactNode } from 'react' +import { type ReactNode, Children, isValidElement } from 'react' import { Search, X, ChevronsLeft, ChevronsRight, - ChevronRight, - ChevronDown, } from 'lucide-react' import styles from './Sidebar.module.css' import { SidebarContext, useSidebarContext } from './SidebarContext' @@ -124,9 +122,6 @@ function SidebarSection({ aria-label={open ? `Collapse ${label}` : `Expand ${label}`} onKeyDown={(e) => { if (e.key === 'Enter' || e.key === ' ') { e.preventDefault(); onToggle() } }} > - {icon && {icon}} {label} @@ -199,35 +194,50 @@ function SidebarRoot({ )} - {/* Search (only when expanded and handler provided) */} - {onSearchChange && !collapsed && ( -
-
- - onSearchChange(e.target.value)} - /> - {searchValue && ( - - )} -
-
- )} + {/* Render Header first, then search, then remaining children */} + {(() => { + const childArray = Children.toArray(children) + const headerIdx = childArray.findIndex( + (child) => isValidElement(child) && child.type === SidebarHeader, + ) + const header = headerIdx >= 0 ? childArray[headerIdx] : null + const rest = headerIdx >= 0 + ? [...childArray.slice(0, headerIdx), ...childArray.slice(headerIdx + 1)] + : childArray - {children} + return ( + <> + {header} + {onSearchChange && !collapsed && ( +
+
+ + onSearchChange(e.target.value)} + /> + {searchValue && ( + + )} +
+
+ )} + {rest} + + ) + })()} )