diff --git a/src/App.js b/src/App.js index 85c180f..70e2331 100644 --- a/src/App.js +++ b/src/App.js @@ -5,7 +5,7 @@ import { LayoutFilled, ProductFilled, CloudUploadOutlined } from "@ant-design/ic import Sidebar from './sidebar/sidebar' import WidgetsContainer from './sidebar/widgetsContainer' import UploadsContainer from './sidebar/uploadsContainer' -import Canvas from './canvas/main' +import Canvas from './canvas/mainClass' function App() { diff --git a/src/canvas/fabricCanvas.js b/src/canvas/fabricCanvas.js index 96d5d82..b743ee1 100644 --- a/src/canvas/fabricCanvas.js +++ b/src/canvas/fabricCanvas.js @@ -1,7 +1,9 @@ import React, { useCallback, useEffect, useRef, useState } from 'react' import * as fabric from 'fabric' - +/** + * NOTE: Not in use + */ function FabricJSCanvas({ canvasOptions, className = '', onCanvasContextUpdate }) { const canvasRef = useRef(null) @@ -22,8 +24,9 @@ function FabricJSCanvas({ canvasOptions, className = '', onCanvasContextUpdate } canvasRef.current.parentNode.style.width = "100%" canvasRef.current.parentNode.style.height = "100%" - console.log("Parent: ", canvasRef.current.parentNode) - + console.log("Parent: ", canvasRef.current.parentNode.parentNode) + + canvasRef.current.parentNode.parentNode.addEventListener("resize", updateCanvasDimensions) window.addEventListener("resize", updateCanvasDimensions) // make the fabric.Canvas instance available to your app @@ -33,6 +36,7 @@ function FabricJSCanvas({ canvasOptions, className = '', onCanvasContextUpdate } return () => { window.removeEventListener("resize", updateCanvasDimensions) + canvasRef.current.parentNode.parentNode.removeEventListener("resize", updateCanvasDimensions) if (onCanvasContextUpdate) onCanvasContextUpdate(null) @@ -45,17 +49,19 @@ function FabricJSCanvas({ canvasOptions, className = '', onCanvasContextUpdate } const updateCanvasDimensions = useCallback(() => { if (!canvasRef.current || !fabricCanvasRef.current) return - + // console.log("Updating canvas") const parent = canvasRef.current.parentNode.parentNode fabricCanvasRef.current.setDimensions({ width: parent.clientWidth, height: parent.clientHeight }) + fabricCanvasRef.current.calcOffset() + fabricCanvasRef.current.renderAll() }, [fabricCanvasRef, canvasRef]) - return + return } diff --git a/src/canvas/main.js b/src/canvas/main.js index b87eedb..6fa06dd 100644 --- a/src/canvas/main.js +++ b/src/canvas/main.js @@ -1,30 +1,64 @@ -import { useCallback, useRef, useState } from "react" -import FabricJSCanvas from "./fabricCanvas" +import { useCallback, useRef, useEffect, useMemo } from "react" +import * as fabric from 'fabric' + function Canvas(){ - const fabricCanvasRef = useRef() + const canvasRef = useRef(null) - const updateCanvasDimensions = useCallback((event) => { - console.log("Updating: ", fabricCanvasRef) - if (!fabricCanvasRef.current) + const canvas = useMemo(() => { + const options = {} + + if (canvasRef.current) + return new fabric.Canvas(canvasRef.current, options) + else + return null + + }, [canvasRef.current]) + + useEffect(() => { + + return () => { + canvas?.dispose() // if already exist, dispose before re-initializing + } + + }, []) + + + + useEffect(() => { + if (canvasRef.current && canvas) { + window.addEventListener("resize", updateCanvasDimensions) + updateCanvasDimensions() + } + + return () => { + window.removeEventListener("resize", updateCanvasDimensions) + } + }, [canvasRef, canvas]) + + + const updateCanvasDimensions = useCallback(() => { + if (!canvasRef.current || !canvas) return + // console.log("Updating canvas") + const parent = canvasRef.current.parentNode.parentNode // this is the canvas outer container - const parent = event.target - - fabricCanvasRef.current.setDimensions({ width: parent.clientWidth, height: parent.clientHeight }) - fabricCanvasRef.current.renderAll() + canvas.setDimensions({ width: parent.clientWidth, height: parent.clientHeight }) + canvas.calcOffset() + + canvas.renderAll() + + }, [canvas, canvasRef]) - }, [fabricCanvasRef]) return ( -
- fabricCanvasRef.current = canvas}/> +
+ +
) } diff --git a/src/canvas/mainClass.js b/src/canvas/mainClass.js new file mode 100644 index 0000000..425f5ea --- /dev/null +++ b/src/canvas/mainClass.js @@ -0,0 +1,138 @@ +import React from "react" +import * as fabric from 'fabric' + + +class Canvas extends React.Component { + + constructor(props) { + super(props) + + this.fabricCanvas = null + this.canvasRef = React.createRef() + + this.mousePressed = false + this.mousePos = { + startX: 0, + startY: 0 + } + + this.modes = { + PAN: 'pan', + } + this.currentMode = 'pan' + + this.updateCanvasDimensions = this.updateCanvasDimensions.bind(this) + } + + componentDidMount() { + this.fabricCanvas = new fabric.Canvas(this.canvasRef.current, { + selection: false, + }) + const rect = new fabric.Rect({ + left: 100, + top: 100, + fill: 'red', + width: 200, + height: 100, + angle: 0 + }) + this.fabricCanvas.add(rect) + console.log("Mounted: ", rect) + fabric.FabricImage.fromURL("https://images.unsplash.com/photo-1722898614949-c9a315e35209?q=80&w=1974&auto=format&fit=crop&ixlib=rb-4.0.3&ixid=M3wxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHx8fA%3D%3D", + (oImg) => { + console.log("added image", oImg) + + const canvasWidth = this.fabricCanvas.getWidth() + const canvasHeight = this.fabricCanvas.getHeight() + + // Get the image's original dimensions + const imgWidth = oImg.getScaledWidth() + const imgHeight = oImg.getScaledHeight() + + // Set the position to the center + oImg.set({ + left: (canvasWidth - imgWidth) / 2, + top: (canvasHeight - imgHeight) / 2 + }) + + oImg.scaleX(2) + oImg.scaleY(2) + + // this.fabricCanvas.backgroundImage = oImg + this.fabricCanvas.add(oImg) + this.fabricCanvas.renderAll() + }) + + this.initPan() + + window.addEventListener("resize", this.updateCanvasDimensions) + this.updateCanvasDimensions() + } + + componentWillUnmount() { + this.fabricCanvas.dispose() + window.removeEventListener("resize", this.updateCanvasDimensions) + } + + updateCanvasDimensions() { + if (!this.canvasRef.current || !this.fabricCanvas) return + + const parent = this.canvasRef.current.parentNode.parentNode // Get the outer container + + this.fabricCanvas.setDimensions({ + width: parent.clientWidth, + height: parent.clientHeight + }) + + this.fabricCanvas.calcOffset() + this.fabricCanvas.renderAll() + } + + initPan(){ + + this.fabricCanvas.on("mouse:down", (event) => { + this.mousePressed = true + + this.startX = event.e.clientX + this.startY = event.e.clientY + + this.fabricCanvas.setCursor("grab") + + }) + + this.fabricCanvas.on("mouse:up", () => { + this.mousePressed = false + this.fabricCanvas.setCursor("default") + + }) + + this.fabricCanvas.on("mouse:move", (event) => { + + if (this.mousePressed && this.currentMode === this.modes.PAN){ + + this.fabricCanvas.setCursor("grab") + + const deltaX = event.e.clientX - this.mousePos.startX + const deltaY = event.e.clientY - this.mousePos.startY + + this.fabricCanvas.relativePan({ x: deltaX, y: deltaY }) + + this.mousePos.startX = event.e.clientX + this.mousePos.startY = event.e.clientY + + } + + }) + + } + + render() { + return ( +
+ {/* Don't add any bg color here */} +
+ ) + } +} + +export default Canvas diff --git a/src/sidebar/sidebar.js b/src/sidebar/sidebar.js index ba0868f..3c755de 100644 --- a/src/sidebar/sidebar.js +++ b/src/sidebar/sidebar.js @@ -43,9 +43,9 @@ function Sidebar({tabs}){ } return ( -