react-konva

repository·master·Indexed 27 days ago

https://github.com/konvajs/react-konva

React bindings for the Konva framework, providing declarative and reactive components for drawing complex canvas graphics. Includes support for Stage, Layer, and various shapes, with features such as strict mode for property updates, a minimal core version for reduced bundle size, and specific integration guides for Next.js.

Tokens
1.5K
Snippets
4
Records
6
Agent score
42%

What's inside react-konva

  1. Minimize bundle size with ReactKonvaCore

    master

    To reduce bundle size, you can import the minimal core version of react-konva. Note that the core version does NOT include support for core shapes and filters. If you need a specific shape, you must import it into the Konva namespace manually.

    // load minimal version of 'react-konva'
    import { Stage, Layer, Rect } from 'react-konva/lib/ReactKonvaCore';
    
    // minimal version has NO support for core shapes and filters
    // if you want to import a shape into Konva namespace you can just do this:
    import 'konva/lib/shapes/Rect';
  2. Use react-konva with Next.js

    master

    Since react-konva is designed for client-side rendering, using it in Next.js can cause Module not found: Can't resolve 'canvas' errors during SSR.

    Note: For konva@10.0.0 and above, this works out-of-the-box. For versions <= 9, use one of the following approaches:

    Approach 1: Manually install canvas module

    Install the canvas module to satisfy the Node.js environment requirement:

    npm install canvas@next

    Load your canvas components on the client-side only using next/dynamic with ssr: false.

    1. Create the component (outside of pages or app folders):
    // components/canvas.js
    import { Stage, Layer, Circle } from 'react-konva';
    
    function Canvas(props) {
      return (
        <Stage width={window.innerWidth} height={window.innerHeight}>
          <Layer>
            <Circle x={200} y={100} radius={50} fill="green" />
          </Layer>
        </Stage>
      );
    }
    export default Canvas;
    1. Import dynamically in your page:
    'use client';
    import dynamic from 'next/dynamic';
    
    const Canvas = dynamic(() => import('../components/canvas'), {
      ssr: false,
    });
    
    export default function Page(props) {
      return <Canvas />;
    }
    1. Configure next.config.js (if required by your Next.js version):

    For standard Webpack:

    /** @type {import('next').NextConfig} */
    const nextConfig = {
      webpack: (config) => {
        config.externals = [...config.externals, { canvas: 'canvas' }];
        return config;
      },
    };
    module.exports = nextConfig;

    For Turbopack: Create an empty.js file in your root, then update next.config.js:

    /** @type {import('next').NextConfig} */
    const nextConfig = {
      experimental: {
        turbo: {
          resolveAlias: {
            canvas: './empty.js',
          },
        },
      },
    };
    module.exports = nextConfig;
  3. Configure Strict Mode in react-konva

    master

    By default, react-konva works in "non-strict" mode. In this mode, if you change a property manually (e.g., via drag-and-drop), react-konva only updates properties that changed in your render() function.

    In strict mode, react-konva will update all properties of the nodes to the values provided in your render() function, regardless of whether they changed. This will reset manual changes (like position after a drag) back to the values defined in your React state.

    To enable strict mode globally:

    import { useStrictMode } from 'react-konva';
    useStrictMode(true);

    To enable strict mode for a specific component, use the _useStrictMode prop:

    <Rect width={50} height={50} fill="black" _useStrictMode />
  4. Basic usage example with Stage, Layer, and Shapes

    master

    React Konva allows you to use Konva components (like Stage, Layer, Rect, Text) as declarative React components. Events are supported using the on prefix (e.g., onClick).

    import React, { useState } from 'react';
    import { render } from 'react-dom';
    import { Stage, Layer, Rect, Text } from 'react-konva';
    import Konva from 'konva';
    
    const ColoredRect = () => {
      const [color, setColor] = useState('green');
    
      const handleClick = () => {
        setColor(Konva.Util.getRandomColor());
      };
    
      return <Rect x={20} y={20} width={50} height={50} fill={color} shadowBlur={5} onClick={handleClick} />;
    };
    
    const App = () => {
      return (
        <Stage width={window.innerWidth} height={window.innerHeight}>
          <Layer>
            <Text text="Try click on rect" />
            <ColoredRect />
          </Layer>
        </Stage>
      );
    };
    
    render(<App />, document.getElementById('root'));
  5. Get a reference to Konva objects using ref

    master

    You can access the underlying Konva instance of a node by using the ref property on the React component.

    import React, { useEffect, useRef } from 'react';
    import { Circle } from 'react-konva';
    
    const MyShape = () => {
      const circleRef = useRef();
    
      useEffect(() => {
        // log Konva.Circle instance
        console.log(circleRef.current);
      }, []);
    
      return <Circle ref={circleRef} radius={50} fill="black" />;
    };