@@ -86,7 +86,6 @@ export interface AgentListItemProps extends AgentListItemBaseProps {
8686 variant ?: "workspace" ;
8787 metadata : FrontendWorkspaceMetadata ;
8888 projectName : string ;
89- subAgentConnectorLayout ?: "default" | "task-group-member" ;
9089 isArchiving ?: boolean ;
9190 /** True when deletion is in-flight (optimistic UI while backend removes). */
9291 isRemoving ?: boolean ;
@@ -121,26 +120,18 @@ const LIST_ITEM_BASE_CLASSES =
121120 "bg-surface-primary relative flex items-start gap-1.5 rounded-l-sm py-2 pr-1.5 select-none transition-all duration-150" ;
122121
123122const HIDE_INLINE_ACTIONS_ON_MOBILE_TOUCH =
124- "[@media(max-width:768px)_and_(hover:none)_and_(pointer:coarse)]:invisible [@media(max-width:768px)_and_(hover:none)_and_(pointer:coarse)]:pointer-events-none " ;
123+ "[@media(max-width:768px)_and_(hover:none)_and_(pointer:coarse)]:hidden " ;
125124const SHOW_INLINE_ACTIONS_ON_WIDE_TOUCH =
126125 "[@media(min-width:769px)_and_(hover:none)_and_(pointer:coarse)]:opacity-100" ;
126+ // Dense sidebar icon buttons should not inherit the global 44px coarse-pointer
127+ // minimum, otherwise hidden/inline actions still reserve row width and push the
128+ // visible controls off-screen.
129+ const COMPACT_SIDEBAR_ICON_BUTTON_CLASSES = "!min-h-0 !min-w-0" ;
127130
128131/** Calculate left padding based on nesting depth */
129132function getItemPaddingLeft ( depth ?: number ) : number {
130133 const safeDepth = typeof depth === "number" && Number . isFinite ( depth ) ? Math . max ( 0 , depth ) : 0 ;
131- return 8 + Math . min ( 32 , safeDepth ) * 12 ;
132- }
133-
134- function getSubAgentConnectorLeft (
135- indentLeft : number ,
136- layout : "default" | "task-group-member"
137- ) : number {
138- return layout === "task-group-member" ? indentLeft - 2 : indentLeft + 9 ;
139- }
140-
141- function getAncestorTrunkLeft ( depth : number , layout : "default" | "task-group-member" ) : number {
142- const indentLeft = getItemPaddingLeft ( depth ) ;
143- return layout === "task-group-member" ? indentLeft + 6 : indentLeft + 8 ;
134+ return 12 + Math . min ( 32 , safeDepth ) * 12 ;
144135}
145136
146137type VisualState = "active" | "idle" | "seen" | "hidden" | "error" | "question" ;
@@ -257,7 +248,12 @@ function QuickArchiveButton(props: {
257248 < TooltipTrigger asChild >
258249 < button
259250 type = "button"
260- className = "text-muted hover:text-foreground focus-visible:text-foreground pointer-events-none inline-flex h-4 w-4 cursor-pointer items-center justify-center border-none bg-transparent p-0 opacity-0 transition-[color,opacity] duration-200 group-focus-within/row:pointer-events-auto group-focus-within/row:opacity-100 group-hover/row:pointer-events-auto group-hover/row:opacity-100"
251+ className = { cn (
252+ "text-muted hover:text-foreground focus-visible:text-foreground pointer-events-none inline-flex h-4 w-4 cursor-pointer items-center justify-center border-none bg-transparent p-0 opacity-0 transition-[color,opacity] duration-200 group-focus-within/row:pointer-events-auto group-focus-within/row:opacity-100 group-hover/row:pointer-events-auto group-hover/row:opacity-100" ,
253+ COMPACT_SIDEBAR_ICON_BUTTON_CLASSES ,
254+ HIDE_INLINE_ACTIONS_ON_MOBILE_TOUCH ,
255+ SHOW_INLINE_ACTIONS_ON_WIDE_TOUCH
256+ ) }
261257 onKeyDown = { stopKeyboardPropagation }
262258 onClick = { ( event ) => {
263259 event . stopPropagation ( ) ;
@@ -294,31 +290,20 @@ function ActionButtonWrapper(props: { children: React.ReactNode; className?: str
294290// ─────────────────────────────────────────────────────────────────────────────
295291
296292function DraftAgentListItemInner ( props : DraftAgentListItemProps ) {
297- const { projectPath, isSelected, depth, sectionId , draft } = props ;
293+ const { projectPath, isSelected, depth, draft } = props ;
298294 const paddingLeft = getItemPaddingLeft ( depth ) ;
299295 const hasPromptPreview = draft . promptPreview . length > 0 ;
300- const draftBorderStyle : React . CSSProperties = {
301- backgroundImage : [
302- "repeating-linear-gradient(to right, var(--color-border) 0 5px, transparent 5px 10px)" ,
303- "repeating-linear-gradient(to right, var(--color-border) 0 5px, transparent 5px 10px)" ,
304- "repeating-linear-gradient(to bottom, var(--color-border) 0 5px, transparent 5px 10px)" ,
305- ] . join ( ", " ) ,
306- backgroundSize : "100% 1.5px, 100% 1.5px, 1.5px 100%" ,
307- backgroundPosition : "left top, left bottom, left top" ,
308- backgroundRepeat : "no-repeat" ,
309- } ;
310296
311297 const ctxMenu = useContextMenuPosition ( { longPress : true } ) ;
312298
313299 return (
314300 < div
315301 className = { cn (
316302 LIST_ITEM_BASE_CLASSES ,
317- sectionId != null ? "ml-8" : "ml-6.5" ,
318- "cursor-pointer pl-1 hover:bg-surface-secondary [&:hover_button]:opacity-100" ,
303+ "border-border cursor-pointer border-t border-b border-l border-dashed pl-1 hover:bg-surface-secondary [&:hover_button]:opacity-100" ,
319304 isSelected && "bg-surface-secondary"
320305 ) }
321- style = { { paddingLeft, ... draftBorderStyle } }
306+ style = { { paddingLeft } }
322307 onClick = { ( ) => {
323308 if ( ctxMenu . suppressClickIfLongPress ( ) ) return ;
324309 draft . onOpen ( ) ;
@@ -374,6 +359,7 @@ function DraftAgentListItemInner(props: DraftAgentListItemProps) {
374359 type = "button"
375360 className = { cn (
376361 "text-muted hover:text-content-destructive inline-flex h-4 w-4 cursor-pointer items-center justify-center border-none bg-transparent p-0 opacity-0 transition-colors duration-200" ,
362+ COMPACT_SIDEBAR_ICON_BUTTON_CLASSES ,
377363 // Keep long-press as the compact mobile affordance on narrow
378364 // touch layouts, but show the button on wider touch screens so
379365 // it never becomes an invisible tappable hotspot.
@@ -687,7 +673,6 @@ function RegularAgentListItemInner(props: AgentListItemProps) {
687673 className = { cn (
688674 LIST_ITEM_BASE_CLASSES ,
689675 "group/row" ,
690- sectionId != null ? "ml-7.5" : "ml-5" ,
691676 isDragging && "opacity-50" ,
692677 isRemoving && "opacity-70" ,
693678 // Keep hover styles enabled for initializing workspaces so the row feels interactive.
@@ -813,6 +798,7 @@ function RegularAgentListItemInner(props: AgentListItemProps) {
813798 type = "button"
814799 className = { cn (
815800 "text-muted inline-flex h-4 w-4 items-center justify-center border-none bg-transparent p-0 transition-colors duration-200" ,
801+ COMPACT_SIDEBAR_ICON_BUTTON_CLASSES ,
816802 // Keep cancel affordance hidden until row-hover while initializing,
817803 // but force it visible as a spinner once deletion starts.
818804 isRemoving
@@ -873,6 +859,7 @@ function RegularAgentListItemInner(props: AgentListItemProps) {
873859 ref = { overflowMenuButtonRef }
874860 className = { cn (
875861 "text-muted hover:text-foreground inline-flex h-4 w-4 cursor-pointer items-center justify-center border-none bg-transparent p-0 transition-colors duration-200" ,
862+ COMPACT_SIDEBAR_ICON_BUTTON_CLASSES ,
876863 ctxMenu . isOpen ? "opacity-100" : "opacity-0" ,
877864 HIDE_INLINE_ACTIONS_ON_MOBILE_TOUCH ,
878865 SHOW_INLINE_ACTIONS_ON_WIDE_TOUCH
@@ -992,7 +979,7 @@ function RegularAgentListItemInner(props: AgentListItemProps) {
992979 ) }
993980
994981 { /* Keep title row anchored so status dot/title align across single+double-line states. */ }
995- < div className = "flex min-w-0 flex-1 flex-col gap-0.5" >
982+ < div className = "flex min-w-0 flex-1 flex-col gap-0.5 overflow-hidden " >
996983 < div
997984 className = { cn (
998985 // Keep the title column shrinkable on narrow/mobile viewports so the
@@ -1013,7 +1000,7 @@ function RegularAgentListItemInner(props: AgentListItemProps) {
10131000 data-workspace-id = { workspaceId }
10141001 />
10151002 ) : (
1016- < div className = "flex min-w-0 items-center gap-1" >
1003+ < div className = "flex min-w-0 flex-1 items-center gap-1 overflow-hidden " >
10171004 < span
10181005 className = { cn (
10191006 "min-w-0 flex-1 truncate text-left text-[14px] leading-6 transition-colors duration-200" ,
@@ -1104,15 +1091,9 @@ function AgentListItemInner(props: UnifiedAgentListItemProps) {
11041091 // Connector geometry is driven by render metadata so visible siblings keep
11051092 // consistent single/middle/last shapes as parents expand/collapse children.
11061093 const isElbowActive = props . metadata . taskStatus === "running" ;
1107- // Task-group members use a slightly different left rail so their connector
1108- // trunk aligns with the group's leading chevron column.
1109- const connectorLayout = props . subAgentConnectorLayout ?? "default" ;
1110- const connectorLeft = getSubAgentConnectorLeft (
1111- getItemPaddingLeft ( props . depth ) ,
1112- connectorLayout
1113- ) ;
1094+ const indentLeft = getItemPaddingLeft ( props . depth ) ;
11141095 const ancestorTrunks = rowMeta . ancestorTrunks . map ( ( trunk ) => ( {
1115- left : getAncestorTrunkLeft ( trunk . depth , connectorLayout ) ,
1096+ left : getItemPaddingLeft ( trunk . depth ) - 4 ,
11161097 active : trunk . active ,
11171098 } ) ) ;
11181099
@@ -1123,7 +1104,7 @@ function AgentListItemInner(props: UnifiedAgentListItemProps) {
11231104 sharedTrunkActiveThroughRow = { rowMeta . sharedTrunkActiveThroughRow }
11241105 sharedTrunkActiveBelowRow = { rowMeta . sharedTrunkActiveBelowRow }
11251106 ancestorTrunks = { ancestorTrunks }
1126- connectorLeft = { connectorLeft }
1107+ indentLeft = { indentLeft }
11271108 isSelected = { props . isSelected }
11281109 isElbowActive = { isElbowActive }
11291110 >
0 commit comments