This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
This project uses Yarn, not npm. Always use yarn for package management.
This project uses Make for builds. Key commands:
make build- Full build (cleans, then builds CJS and web bundles)make lint- Runs Flow type checker, ESLint, and TypeScript type checking on typingsmake test- Runs unit tests via Vitestmake test-browser- Runs browser tests via Puppeteer (requires build first)make test-all- Runs both unit and browser testsmake dev- Starts webpack dev server with example page at localhost:8080
Yarn scripts:
yarn test- Run unit tests (jsdom environment)yarn test:watch- Run unit tests in watch modeyarn test -- path/to/test.jsx- Run a single test fileyarn test -- -t "test name"- Run tests matching a patternyarn test:browser- Build and run browser tests (Puppeteer)yarn test:all- Run all testsyarn test:coverage- Run tests with coverage report
Pre-commit hooks run make lint and make test automatically.
Tests are split into two categories:
-
Unit tests (
test/*.test.{js,jsx}) - Run in jsdom via Vitest- Fast, no browser required
- Test component logic, callbacks, prop handling
- Some coordinate-based tests skipped (require real browser)
-
Browser tests (
test/browser/*.test.js) - Run in headless Chrome via Puppeteer- Test actual drag behavior with real coordinate calculations
- Test transforms, axis constraints, bounds, scale
test/testUtils.js provides helpers for simulating drag events:
simulateDrag(element, {from, to})- Complete drag operationstartDrag(element, {x, y})/moveDrag({x, y})/endDrag(element, {x, y})- Step-by-step dragsimulateTouchDrag(element, {from, to})- Touch event drag
DraggableCore (lib/DraggableCore.js) - Low-level component that handles raw drag events
- Maintains minimal internal state (just
dragging,lastX,lastY) - Manages mouse/touch event binding and cleanup
- Provides
onStart,onDrag,onStopcallbacks with position data - Use this when you need full control over positioning
Draggable (lib/Draggable.js) - High-level wrapper around DraggableCore
- Manages position state, bounds checking, axis constraints
- Applies CSS transforms or SVG transform attributes
- Supports controlled (
positionprop) and uncontrolled (defaultPosition) modes - Adds dragging-related CSS classes
lib/utils/domFns.js- DOM helpers: event binding, CSS transforms, user-select hackslib/utils/positionFns.js- Position calculations: bounds checking, grid snapping, delta computationslib/utils/getPrefix.js- Browser prefix detection for CSS transforms
build/cjs/- CommonJS build (Babel)build/web/react-draggable.min.js- UMD browser bundle (Webpack)
The codebase uses Flow for internal type checking (// @flow annotations) and ships TypeScript definitions in typings/index.d.ts. Both must stay in sync when modifying component props or types.
To avoid ReactDOM.findDOMNode deprecation warnings in Strict Mode, components accept a nodeRef prop:
const nodeRef = React.useRef(null);
<Draggable nodeRef={nodeRef}>
<div ref={nodeRef}>Content</div>
</Draggable>Returning false from onStart, onDrag, or onStop cancels the drag operation.
Dragging uses CSS transforms (translate) rather than absolute positioning, allowing draggable elements to work regardless of their CSS position value.
- Update CHANGELOG.md
make release-patch,make release-minor, ormake release-majormake publish