映射图像点并设置样式

huangapple go评论82阅读模式
英文:

react mapping image point and setting style

问题

我有一个需求,要求在单击人体图像上时,在该身体部位显示一个圆圈。我能够渲染出这个圆圈,但是无法将其显示在身体部位上。而且,如果我滚动并单击相同的身体部位,圆圈会出现在不同的位置。以下是示例。

CodeSandBox

这也会在不同屏幕尺寸上产生问题。

英文:

I have a requirement where on clicking on a human body image I have to display a circle on that body part. I'm able to render the circle but not on the body part. And if I scroll and click on the same body part the circle renders in a different place. Here's the example.

CodeSandBox

This also creates an issue with different screen sizes.

答案1

得分: 1

event.target.getBoundingClientRect() 返回元素的大小以及相对于视口的位置。event.target.naturalWidthevent.target.naturalHeight 提供<img/>元素的自然宽度和高度(原始像素宽度),因此您可以通过以下方式计算要放置在图像上的圆的绝对位置:event.target.naturalWidth / rect.widthevent.target.naturalHeight / rect.height

示例

import React, { useState } from "react";
import "./styles.css";

import human_body from "./images/human body.png";
import circle from "./images/hover-circle.png";

export default function App() {
  const [circlePosition, setCirclePosition] = useState({ left: 0, top: 0 });

  const imgClick = (event: any) => {
    const rect = event.target.getBoundingClientRect();
    const scaleX = event.target.naturalWidth / rect.width;
    const scaleY = event.target.naturalHeight / rect.height;
    const left = event.nativeEvent.offsetX * scaleX - 20; 
    const top = event.nativeEvent.offsetY * scaleY - 20;
    setCirclePosition({ left, top });
  };

  return (
    <div className="App">
      <div>
        {circlePosition.left > 0 && circlePosition.top > 0 && (
          <img
            src={circle}
            alt="hover-body"
            style={{
              width: 50,
              height: 50,
              left: circlePosition.left,
              top: circlePosition.top,
              position: "absolute",
              zIndex: 10
            }}
          />
        )}
        <img id="human_body" onClick={imgClick} src={human_body} alt="body" />
      </div>
    </div>
  );
}

(注意:上述示例中的 &lt;&gt; 已被正常的HTML标签 <> 替代。)

英文:

event.target.getBoundingClientRect() returns the size of an element and its position relative to the viewport. And event.target.naturalWidth and event.target.naturalHeight provides the natural width and height of &lt;img/&gt; (original pixels wide)

so you can calculate absolute position of circle which will be placed on image by event.target.natural(width or height) / rect.(width or height)

Example

import React, { useState } from &quot;react&quot;;
import &quot;./styles.css&quot;;

import human_body from &quot;./images/human body.png&quot;;
import circle from &quot;./images/hover-circle.png&quot;;

export default function App() {
  const [circlePosition, setCirclePosition] = useState({ left: 0, top: 0 });

  const imgClick = (event: any) =&gt; {
    const rect = event.target.getBoundingClientRect();
    const scaleX = event.target.naturalWidth / rect.width;
    const scaleY = event.target.naturalHeight / rect.height;
    const left = event.nativeEvent.offsetX * scaleX - 20; 
    const top = event.nativeEvent.offsetY * scaleY - 20;
    setCirclePosition({ left, top });
  };

  return (
    &lt;div className=&quot;App&quot;&gt;
      &lt;div&gt;
        {circlePosition.left &gt; 0 &amp;&amp; circlePosition.top &gt; 0 &amp;&amp; (
          &lt;img
            src={circle}
            alt=&quot;hover-body&quot;
            style={{
              width: 50,
              height: 50,
              left: circlePosition.left,
              top: circlePosition.top,
              position: &quot;absolute&quot;,
              zIndex: 10
            }}
          /&gt;
        )}
        &lt;img id=&quot;human_body&quot; onClick={imgClick} src={human_body} alt=&quot;body&quot; /&gt;
      &lt;/div&gt;
    &lt;/div&gt;
  );
}

答案2

得分: 0

我对你的代码进行了一些修改,你可以检查一下是否适用。

Code Sandbox

英文:

I made some dits to your code, you can cehck if this works for you.

Code Sandbox

huangapple
  • 本文由 发表于 2023年3月8日 16:24:12
  • 转载请务必保留本文链接:https://go.coder-hub.com/75670739.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定