Skip to content

Feature request: New Handwriting / Freehand Drawing component for Vaadin 26 #9115

Description

@letrthang

Motivation

Many enterprise and government applications require users to draw or handwrite directly in the browser — electronic signatures, form annotations, freehand markup on documents, sketching diagrams, or simply capturing handwritten input on touch devices.

Vaadin currently has no first-class component for freehand drawing. Developers must embed a raw <canvas> element and manually wire up pointer events, stroke rendering, touch/pen/mouse compatibility, pressure sensitivity, undo/redo, and image export — a substantial amount of low-level work that is repeated in every project that needs it.

Proposed Component: HandwritingDrawPad (working name)

A new component that provides a freehand drawing surface where the user can draw anything with mouse, touch, or stylus.

Core behavior

┌──────────────────────────────────────────────────┐
│  ✏️  HandwritingDrawPad                           │
│                                                   │
│                                                   │
│       ~~ freehand strokes appear here ~~          │
│                                                   │
│       (user draws freely with mouse /             │
│        finger / stylus / Apple Pencil)            │
│                                                   │
│                                                   │
├──────────────────────────────────────────────────┤
│  [ Undo ] [ Redo ] [ Clear ]   [ Save as PNG ]    │
└──────────────────────────────────────────────────┘
  • The user can draw freely — lines, shapes, handwriting, doodles, anything.
  • Supports mouse, touch, and pen/stylus input (Pointer Events API).
  • Optionally captures pressure sensitivity and tilt from stylus devices.

Suggested API

HandwritingDrawPad pad = new HandwritingDrawPad();
pad.setWidth("600px");
pad.setHeight("400px");

// Configure the brush
pad.setStrokeColor(Color.BLACK);
pad.setStrokeWidth(3);
pad.setBackgroundColor(Color.WHITE);

// Built-in actions
pad.undo();
pad.redo();
pad.clear();

// Export the drawing
byte[] pngData = pad.getPng();
byte[] svgData = pad.getSvg();
String dataUrl = pad.toDataUrl("image/png");

// Listen for drawing events
pad.addStrokeListener(e -> {
    // fired when the user completes a stroke
});

Key features

Feature Description
Freehand drawing Smooth bezier-curve strokes from pointer/touch/mouse input
Input devices Mouse, touch (finger), pen/stylus (incl. pressure & tilt)
Brush settings Color, width, opacity, brush style (solid, dashed, calligraphic)
Undo / Redo Built-in stroke history with configurable depth
Clear One-call reset of the canvas
Export Export to PNG, JPEG, SVG, or data URL
Background Configurable background color or transparent
Responsive Scales to container; works on mobile and desktop
Accessibility Keyboard-accessible toolbar buttons; ARIA labels on actions
Theme variants Lumo theme variants for toolbar layout (inline, floating, hidden)

Use cases

  1. Electronic signatures — capture a user's handwritten signature on contracts and forms.
  2. Document annotation — let users mark up or highlight content freehand.
  3. Sketching / diagrams — quick freehand sketches in collaborative tools.
  4. Educational apps — students solve math problems by hand on a tablet.
  5. Medical / field forms — capture hand-drawn notes on touch devices.

Alternatives considered

  • Manual <canvas> via Element API: every team reimplements pointer-event handling, stroke smoothing, undo stacks, and image export from scratch. High duplication, inconsistent quality, and no built-in cross-browser testing.
  • Third-party JS libraries (e.g., signature_pad): workable but require a Vaadin wrapper, lack server-side integration, and are not maintained alongside Vaadin releases.
  • Existing signature add-ons: a few exist in the Vaadin Directory but are narrow (signature-only) and not general-purpose drawing surfaces.

A built-in, general-purpose HandwritingDrawPad would cover signatures and broader freehand drawing needs with proper server-side integration and Lumo theming.

Prior art

  • Material UI — no built-in, but widely requested
  • PrimeFacesSignature
  • HTML5 <canvas> + Pointer Events — the underlying web standard
  • Excalidraw / tldraw — popular open-source drawing surfaces (React)

Implementation notes

The component would likely wrap an HTML5 <canvas> element using the Pointer Events API (unified mouse/touch/pen), with quadratic-curve smoothing for natural strokes. The server side would manage brush configuration, undo/redo history, and image export via the existing Vaadin element communication layer.


I'd be happy to help refine the API . Is this something the team would consider for Vaadin 26?

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions