Support (or document) `trigger="contextMenu"` on collection items (GridListItem / TreeItem / Row)
Los mantenedores suelen responder en 1 día
Nadie ha tomado este issue todavía.
Evaluación
- Dificultad
- 4/5
- Tiempo estimado
- 3-5 días
- Aptitud para principiantes
- 52/100
- Tipo de issue
- Nueva funcionalidad
- Claridad
- Bastante claro
- Estado de actividad
- Tranquilo
- Stack tecnológico
- react, typescript
- Área
- accessibility, frontend
Línea de trabajo
Empieza por useContextMenu y MenuTrigger; después, compara el manejo de eventos de collection-item en useSelectableItem.ts:409 y usePress.ts:112/1010. Inspecciona las stories y pruebas de Menu mencionadas en el issue para determinar si el resultado admitido es documentación o un cambio de API. La tarea estará terminada cuando una fila de la collection tenga un flujo de menú contextual compatible, sin advertencias, con comportamiento documentado y cobertura.
Escrito por el modelo de indexación a partir del texto del issue.
Descripción
Provide a general summary of the feature here
trigger="contextMenu" (new in v1.20.0) works well for a standalone trigger, but there doesn't appear to be a supported way to use it on a collection item — a GridListItem, TreeItem, or table Row. Right-clicking a row to open the same menu its kebab button opens seems like one of the most common reasons to want a context menu, so I suspect this is either a gap or a pattern I've failed to find.
Either a supported API for it, or docs guidance on the intended approach, would help.
🤔 Expected Behavior?
Being able to attach a context menu to a collection item, so that right-click / long-press / Shift+F10 on a row opens the same menu the row's kebab button opens.
Collection items already look like valid trigger candidates: the docs say MenuTrigger "works with any pressable React Aria component", and rows are pressable —
useGridListItem→useSelectableItem→usePress(useSelectableItem.ts:409)usePressreadsPressResponderContext(usePress.ts:112) and merges the remaining DOM props into its result (usePress.ts:1010)
so a row would consume MenuTrigger's onContextMenu / onKeyDown correctly if it could receive them.
😯 Current Behavior
1. MenuTrigger can't wrap a collection item. MenuTrigger must render as an ancestor of its trigger, but inside a collection it hits the useIsHidden guard and returns null during the collection-building pass, so the item never registers. Wrapping a TreeItem removes every row from the tree — the collection renders empty.
2. Wrapping the row's content in <Pressable> works, but warns once per row. The Pressable child ends up being a div with no interactive ARIA role. The row itself is role="row" (RAC's Tree is a treegrid), which isn't in Pressable's allowed-role list, so there's nothing valid to put the role on:
<Pressable> child must have an interactive ARIA role.
Adding excludeFromTabOrder just swaps it for the other warning:
<Pressable> child must be focusable. Please ensure the tabIndex prop is passed through.
Putting a fake interactive role on a div inside a treegrid row seems worse than the warning, so neither option feels right.
3. Every example uses a standalone <Button>. packages/react-aria-components/stories/Menu.stories.tsx:532, packages/@react-spectrum/s2/stories/Menu.stories.tsx:409, and packages/react-aria-components/test/Menu.test.tsx:652 / :701, plus both docs sites. As a side note, the docs example makes a non-interactive 250×150 region into a <button> purely to satisfy the pressable requirement — it's announced as a button but does nothing when pressed, which reads a little odd as the canonical example.
💁 Possible Solution
useContextMenu works today and looks like the intended escape hatch — contextMenuProps spread straight onto a TreeItem / GridListItem keeps all the platform handling, with no wrapper and no warnings. If that's the recommended pattern for collections, documenting it on the Menu page (or on GridList / Tree / Table) would settle it.
The one thing it loses versus MenuTrigger is positioning the menu at the pointer, which needs getTargetRect — that isn't part of Popover's public types, so it currently needs a @ts-expect-error. Exposing it, or otherwise providing a supported way to anchor a popover to a point, would close that gap.
🔦 Context
We have a collections sidebar built on Tree, where each row has a kebab menu (rename, share, delete, …). We wanted right-click on the row to open that same menu, keeping the kebab button as-is. The kebab stays either way — the context menu is an addition, not a replacement.
We landed on <Pressable> around the row content, which works, but it restructures the row purely to host the trigger and logs a warning per row in development, so it doesn't feel like the intended shape.
💻 Examples
Wrapping the item — collection renders empty:
// Every row disappears: MenuTrigger returns null during the collection build,
// so no TreeItem is ever registered.
<Tree aria-label="Collections">
<MenuTrigger trigger="contextMenu">
<TreeItem textValue="Design">
<TreeItemContent>Design</TreeItemContent>
</TreeItem>
<Popover>
<Menu>
<MenuItem>Rename…</MenuItem>
<MenuItem>Delete…</MenuItem>
</Menu>
</Popover>
</MenuTrigger>
</Tree>
Wrapping the content — works, but warns once per row:
<TreeItem textValue="Design">
<TreeItemContent>
<MenuTrigger trigger="contextMenu">
{/* warns: child must have an interactive ARIA role */}
<Pressable><div className="row-content">Design</div></Pressable>
<Popover>
<Menu>
<MenuItem>Rename…</MenuItem>
<MenuItem>Delete…</MenuItem>
</Menu>
</Popover>
</MenuTrigger>
</TreeItemContent>
</TreeItem>
Possibly related: #7197 (pass onContextMenu in RAC Tab), #7987 (useLongPress with a Table Row — event and labelling props get filtered out), #9863 (right-click a table row containing a link).
Versions: [email protected], [email protected], [email protected], React 19.
🧢 Your Company/Team
Metaview
- Lenguaje dominante
- TypeScript
- Estrellas
- 16k
- Forks
- 1.6k
- Merge medio
- 2 d 17 h
- PR fusionados (30 d)
- 41
Preparar el entorno
- Sin Dockerfile ni archivo de Docker Compose
- Tiene una plantilla de pull request
- Leer la guía de contribución
Primeros pasos
- Lee el issue completo y luego la guía de contribución del proyecto.
- Comenta en el issue que vas a ocuparte — evita que dos personas hagan lo mismo.
- Haz un fork del repositorio y trabaja en una rama.
- Abre un pull request que haga referencia al número del issue.
Más de adobe/react-spectrum
-
S2 quiet Picker menu is always 192px wide: its width calc() has no unitPosiblemente ocupada @darshpatel1052 la tomó hoy. Abiertowaiting on author
Dificultad 2/5 Menos de una hora Aptitud para principiantes 88/100
adobe/react-spectrum#10909 · 3 comentarios ·
Los mantenedores suelen responder en 1 día
-
DatePicker omits timezone for initially empty fields despite zoned placeholderValuePosiblemente ocupada @mrlexcoder la tomó hace 1 día. Abiertobug
Dificultad 2/5 1-3 horas Aptitud para principiantes 68/100
adobe/react-spectrum#10900 · 2 comentarios ·
Los mantenedores suelen responder en 1 día
-
Separator adds a redundant role="separator" to its default <hr>Posiblemente ocupada @Janani-bn la tomó hace 1 día. Abierto
Dificultad 2/5 1-3 horas Aptitud para principiantes 74/100
adobe/react-spectrum#10894 · 2 comentarios ·
Los mantenedores suelen responder en 1 día
-
ComboBox with selectionMode="multiple": Cmd/Ctrl+A does nothing while the popover is openPosiblemente ocupada @mangeshraut712 la tomó hace 7 días. Abierto
Dificultad 2/5 1-3 horas Aptitud para principiantes 76/100
adobe/react-spectrum#10866 ·
Los mantenedores suelen responder en 1 día
-
CheckboxGroup: `validationBehavior="aria"` is ignored by its checkboxes since 1.18Posiblemente ocupada @mangeshraut712 la tomó hace 7 días. Abierto
Dificultad 2/5 1-3 horas Aptitud para principiantes 78/100
adobe/react-spectrum#10856 ·
Los mantenedores suelen responder en 1 día
Todos los issues de adobe/react-spectrum
Issues similares
-
Dificultad 1/5 Menos de una hora Aptitud para principiantes 88/100
-
bug needs triage
Dificultad 2/5 1-3 horas Aptitud para principiantes 72/100
DSpace/dspace-angular#6511 ·
Los mantenedores suelen responder en 1 día
-
area: frontend area:byok bug severity:low
Dificultad 2/5 1-3 horas Aptitud para principiantes 65/100
Los mantenedores suelen responder en 1 día
-
Phone app shows Unknown for a remote machine whose key changedPosiblemente ocupada @janicduplessis la tomó hoy. Abiertoarea: mobile priority: P3 type: bug
Dificultad 1/5 Menos de una hora Aptitud para principiantes 78/100
appandflow/stim#5006 · 1 comentario ·
Los mantenedores suelen responder en 1 día
-
Area - Local to Cloud Bug
Dificultad 2/5 1-3 horas Aptitud para principiantes 66/100
microsoft/vscode-mssql#23209 ·
Los mantenedores suelen responder en 1 día