drawDB/src/components/draw_area.jsx

90 lines
2.4 KiB
React
Raw Normal View History

2023-09-19 20:47:06 +08:00
import React, { useRef, useState } from "react";
import { useDrop } from "react-dnd";
2023-09-19 20:47:06 +08:00
import Rect from "./rect";
export default function Canvas(props) {
const [dragging, setDragging] = useState(false);
const [offset, setOffset] = useState({ x: 0, y: 0 });
2023-09-19 20:46:43 +08:00
const canvas = useRef(null);
2023-09-19 20:47:06 +08:00
const handleMouseDown = (event, id) => {
const { clientX, clientY } = event;
const rectangle = props.rectangles.find((rect) => rect.id === id);
setOffset({
x: clientX - rectangle.x,
y: clientY - rectangle.y,
});
setDragging(id);
};
const handleMouseMove = (event) => {
if (dragging === false) return;
const { clientX, clientY } = event;
const updatedRectangles = props.rectangles.map((rect) => {
if (rect.id === dragging) {
return {
...rect,
x: clientX - offset.x,
y: clientY - offset.y,
};
}
2023-09-19 20:47:06 +08:00
return rect;
});
props.setRectangles(updatedRectangles);
};
2023-09-19 20:46:43 +08:00
2023-09-19 20:47:06 +08:00
const handleMouseUp = () => {
setDragging(false);
};
const [, drop] = useDrop(
() => ({
accept: "CARD",
drop: (item, monitor) => {
const offset = monitor.getClientOffset();
const canvasRect = canvas.current.getBoundingClientRect();
const x = offset.x - canvasRect.left - 100 * 0.5;
const y = offset.y - canvasRect.top - 100 * 0.5;
const newRectangle = {
id: props.rectangles.length + 1,
x,
y,
width: 100,
height: 100,
label: `rect ${props.rectangles.length + 1}`,
};
props.setRectangles([...props.rectangles, newRectangle]);
2023-09-19 20:46:43 +08:00
},
2023-09-19 20:47:06 +08:00
collect: (monitor) => ({
isOver: !!monitor.isOver(),
}),
}),
[props.rectangles]
);
2023-09-19 20:46:43 +08:00
return (
2023-09-19 20:47:06 +08:00
<div ref={drop} className="flex-grow" id="canvas">
<div ref={canvas} className="w-full h-screen">
<svg
onMouseMove={handleMouseMove}
onMouseUp={handleMouseUp}
style={{ width: "100%", height: "100%" }}
>
{props.rectangles.map((rectangle) => (
<Rect
key={rectangle.id}
x={rectangle.x}
y={rectangle.y}
label={rectangle.label}
width={rectangle.width}
height={rectangle.height}
onMouseDown={(event) => handleMouseDown(event, rectangle.id)}
/>
))}
</svg>
</div>
</div>
);
2023-09-19 20:46:43 +08:00
}