<Stencil />
Drag shapes from a React-built palette onto the paper. Unlike the built-in
JointJS stencil, this one is headless: it renders a host <div> (forwarding
any div attributes you pass) that wraps your own palette UI as children,
so you control the look and layout entirely in React.
Start a drag by calling useStencil's startCellDrag from a palette
item. While dragging, the preview is rendered through the JointJS drag paper
via StencilProps.renderElement, which defaults to the target paper's
own renderElement so the preview matches the dropped element.
The drop target is resolved from the nearest <Paper> / <PaperScroller>
context, or set it explicitly with StencilProps.paper.
Type Parameters
| Type Parameter | Default type |
|---|---|
ElementData | unknown |
See
Example
import { Paper, HTMLBox, Diagram, PaperScroller, Stencil, useStencil } from '@joint/react-plus';
// Build the palette yourself; start a drag from any item.
function Palette() {
const { startCellDrag } = useStencil();
return (
<button
onPointerDown={(event) =>
startCellDrag({ type: 'element', data: { label: 'Task' } }, event)
}
>
Add task
</button>
);
}
function Editor() {
return (
<Diagram>
<PaperScroller>
<Paper renderElement={({ label }) => <HTMLBox>{label}</HTMLBox>} />
</PaperScroller>
<Stencil>
<Palette />
</Stencil>
</Diagram>
);
}
Props
autoZIndex?
readonly optional autoZIndex?: boolean;
Place dropped elements above existing ones by auto-assigning their z-index.
Default
true
children?
readonly optional children?: ReactNode;
Your palette UI, rendered inside the stencil host element.
dropAnimation?
readonly optional dropAnimation?: DropAnimation;
Animate the clone snapping into place on a valid drop. true for the
default animation, or an object to tune duration / easing.
Default
true
onCellDrag?
optional onCellDrag?: (params) => void;
Fires continuously while an element is being dragged from the stencil.
Parameters
| Parameter | Type |
|---|---|
params | StencilDragParams |
Returns
void
onCellDragEnd?
optional onCellDragEnd?: (params) => void;
Fires once when the user releases, before onCellDrop / onCellDropInvalid.
Parameters
| Parameter | Type |
|---|---|
params | StencilDragParams |
Returns
void
onCellDragStart?
optional onCellDragStart?: (params) => void;
Fires when the drag actually starts (async, once the drag preview's size has been measured).
Parameters
| Parameter | Type |
|---|---|
params | StencilDragParams |
Returns
void
onCellDrop?
optional onCellDrop?: (params) => void;
Fires when the cell lands on a valid drop target.
Parameters
| Parameter | Type |
|---|---|
params | StencilDropParams |
Returns
void
onCellDropInvalid?
optional onCellDropInvalid?: (params) => void;
Fires when the cell is released outside any valid drop target.
Parameters
| Parameter | Type |
|---|---|
params | StencilDropInvalidParams |
Returns
void
options?
readonly optional options?: Options;
Raw ui.Stencil.Options passthrough for anything joint-react-plus doesn't
expose as a dedicated prop.
Values set here override top-level props of the same name: treat this as
the authoritative form for users who need direct access to the raw
JointJS API. Avoid overriding joint-react-plus-controlled options
(paper, groups, layout, paperOptions, search): the headless
component has no UI to consume them.
paper?
readonly optional paper?: PaperTarget;
Target paper the stencil drops onto: a paper id, dia.Paper instance,
or paper ref. Defaults to the nearest <Paper> / <PaperScroller>
context when omitted.
renderElement?
readonly optional renderElement?: RenderElement<ElementData>;
Renders the drag preview while a clone is dragged from the palette.
Defaults to the target paper's renderElement, so the preview matches the
element that will be dropped. Omit it to skip React-rendered previews.
scaleClones?
readonly optional scaleClones?: boolean;
Scale the drag clone to match the target paper's current zoom.
Default
true
usePaperGrid?
readonly optional usePaperGrid?: boolean;
Snap the dragged clone to the target paper's grid.
Default
true