context-menu: Change content based on target #3650
Unanswered
adriano-tirloni
asked this question in
Help
Replies: 1 comment
-
|
Radix's ContextMenu does not expose the original import * as ContextMenu from "@radix-ui/react-context-menu";
import { useRef, useState } from "react";
function App() {
const [target, setTarget] = useState<HTMLElement | null>(null);
return (
<ContextMenu.Root>
<ContextMenu.Trigger
onContextMenu={(e) => {
// Capture what was actually right-clicked
setTarget(e.target as HTMLElement);
}}
>
<div className="wrapper">
<div data-context="component-a">Component A</div>
<div data-context="component-b">Component B</div>
<div data-context="component-c">Component C</div>
<textarea data-context="native" />
</div>
</ContextMenu.Trigger>
<ContextMenu.Portal>
<ContextMenu.Content>
{/* Common items always shown */}
<ContextMenu.Item>Copy</ContextMenu.Item>
<ContextMenu.Item>Paste</ContextMenu.Item>
{/* Conditional items based on what was clicked */}
{target?.closest("[data-context='component-a']") && (
<>
<ContextMenu.Separator />
<ContextMenu.Item>Edit Component A</ContextMenu.Item>
<ContextMenu.Item>Delete Component A</ContextMenu.Item>
</>
)}
{target?.closest("[data-context='component-b']") && (
<>
<ContextMenu.Separator />
<ContextMenu.Item>Resize Component B</ContextMenu.Item>
</>
)}
</ContextMenu.Content>
</ContextMenu.Portal>
</ContextMenu.Root>
);
}The key ideas:
For the native textarea case where you want the browser's default context menu, you can prevent Radix from opening: <ContextMenu.Trigger
onContextMenu={(e) => {
const el = e.target as HTMLElement;
if (el.tagName === "TEXTAREA" || el.tagName === "INPUT") {
// Let the browser handle it
e.stopPropagation();
return;
}
setTarget(el);
}}
>This approach scales well — just add more |
Beta Was this translation helpful? Give feedback.
0 replies
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uh oh!
There was an error while loading. Please reload this page.
-
Hi everyone! I'm having a really hard time figuring out how to do this properly.
My app is heavy on the use of right click context menu (think adobe stuff), só when the user right clicks, say a wrapper div, content X shoul show.
But inside the wrapper there are 3 more components, each with additional options for the context-menu.
Also there are children i.e. textarea and other inputs, that should show system context-menu (or my clone of it if this is not feasible).
So, I'm trying to access the event.target from the onContextMenu event inside the menu content. But radix doesn't seem to link those in anyway. So when rendering the menu I have no idea what was clicked on dynamically, only if I hardcode 3 or 4 contextmenu trees.
Does that make sense?
Anyone can point me in the right direction?
Beta Was this translation helpful? Give feedback.
All reactions