簡體   English   中英

檢測元素已被用戶使用 React 調整大小

[英]Detect an element has been resized by a user with React

我有一個 React 組件,它呈現 canvas 並在其上繪制多邊形:

function Plot(props) {

  const [localPlot, setLocalPlot] = useState(props.plot);
  ...

  useEffect(() => {

    // here we get the Canvas context and draw polygons to it


  }, [localPlot]);

  return (
    <>
      <div
        style={{
          resize: "both",
          border: "1px solid #32a1ce",
          overflow: "auto",
        }}
        ref={ref}
      >
        <canvas
          style={{ border: "thick solid #32a1ce" }}
          className="canvas"
          id={`canvas-${props.plotIndex}`}
        />
      </div>
  );

現在我想讓用戶能夠調整 canvas 的大小,所以我通過圍繞它的divresize: "both"實現了這一點。 我正在使用庫react-resize-detector庫來檢測 div 何時調整大小:

function Plot(props) {

  const [localPlot, setLocalPlot] = useState(props.plot);
  ...

  useEffect(() => {

    // here we get the Canvas context and draw polygons to it


  }, [localPlot]);
  

  const onResize = useCallback((w, h) => {
    // on resize logic
    console.log("in onResize, w, h is ", w, h);
  }, []);

  const { width, height, ref } = useResizeDetector({
    onResize,
  });

  return (
    <>
      <div
        style={{
          resize: "both",
          border: "1px solid #32a1ce",
          overflow: "auto",
        }}
        ref={ref}
      >
        <canvas
          style={{ border: "thick solid #32a1ce" }}
          className="canvas"
          id={`canvas-${props.plotIndex}`}
      </div>
  );

問題是因為我添加了這個,canvas 是空白的。 我相信這是因為 onResize 在渲染之后調用,並且以某種方式擦除 canvas 上的所有內容。當我更改為:

const { width, height, ref } = useResizeDetector({
   handleHeight: false,
   refreshMode: 'debounce',
   refreshRate: 1000,
   onResize
});

在擦除之前,我在 canvas 上看到了多邊形一秒鍾。 我究竟做錯了什么?

您可以使用 state 和 effect 的組合在調整大小時重新繪制 canvas。

這是一個簡化的例子:

function Plot() {
  const onResize = useCallback((w, h) => {
    setSize({ w, h });
  }, []);

  const canvasRef = useRef();

  const { ref } = useResizeDetector({ onResize });

  const [size, setSize] = useState({ w: 300, h: 300 });

  useEffect(() => {
    const ctx = canvasRef.current.getContext("2d");
    ctx.fillStyle = "green";
    ctx.font = "18px serif";
    ctx.fillText(`${size.w} x ${size.h}`, 10, 50);
  }, [size]);

  return (
    <div id="resizer" ref={ref}>
      {/* subtract 10 for the resize corner in the enclosing div */}
      <canvas ref={canvasRef} width={size.w - 10} height={size.h - 10} />
    </div>
  );
}

你可以在這里看到一個完整的演示:

編輯

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM