首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >椭圆-鼠标碰撞检测

椭圆-鼠标碰撞检测
EN

Stack Overflow用户
提问于 2016-01-11 21:56:30
回答 3查看 1.9K关注 0票数 3

我试图弄清楚如何判断鼠标是否在HTML5画布上的椭圆上。我需要更精确的检查。

对不起,这是个模糊的问题。我完全不知所措。

任何帮助都将不胜感激。

到目前为止我有这样的想法:

代码语言:javascript
复制
// This is a pretend object. m.x and m.y will have the position of the mouse.
var m = {
    x:245,
    y:341,
    onEnter: function(){}
};

m.onEnter = function () {
    console.log('The mouse entered the ellipse!');
};

// The important parts of my ellipse object
var e = {
    width:100,
    height:50,
    x:132,
    y:143
};

// This is already working - I use a bounding-box first to increase performance.
if (m.x >= e.x - (e.width/2) && m.x <= e.x + (e.width/2) && m.y >= e.y - (e.height/2) && m.y <= e.y + (e.height/2)) {

    if (/* I havn't got the slightest idea what to put here. */) {
        m.onEnter();
    }

}
EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2016-01-11 23:14:58

@pvg的重复答案是可以的,但是重复的答案应该指出它们使用的变量是如何计算的:

代码语言:javascript
复制
// Given cx,cy,a,b defining an ellipse 
function isInEllipse(mouseX,mouseY){
    var dx=mouseX-cx;
    var dy=mouseY-cy;
    return ((dx*dx)/(a*a)+(dy*dy)/(b*b)<=1);
}

这里的示例代码和演示:

代码语言:javascript
复制
var canvas=document.getElementById("canvas");
var ctx=canvas.getContext("2d");
var cw=canvas.width;
var ch=canvas.height;
function reOffset(){
  var BB=canvas.getBoundingClientRect();
  offsetX=BB.left;
  offsetY=BB.top;        
}
var offsetX,offsetY;
reOffset();
window.onscroll=function(e){ reOffset(); }
window.onresize=function(e){ reOffset(); }

var PI=Math.PI;
var PI2=PI*2;
var cx=cw/2;
var cy=ch/2;
var a=120;
var b=80;
var points=getPointsOnEllipse(cx,cy,a,b);

$("#canvas").mousemove(function(e){handleMouseMove(e);});

drawEllipse(points);


function dot(x,y,color){
  ctx.beginPath();
  ctx.arc(x,y,3,0,PI2);
  ctx.closePath();
  ctx.fillStyle=color;
  ctx.fill();
}

function isInEllipse(x,y){
  var dx=x-cx;
  var dy=y-cy;
  return ((dx*dx)/(a*a)+(dy*dy)/(b*b)<=1);
}

function drawEllipse(points){
  ctx.beginPath();
  ctx.moveTo(points[0].x,points[0].y);
  for(var j=0;j<points.length;j++){
    ctx.lineTo(points[j].x,points[j].y);
  }
  ctx.closePath();
  ctx.lineWidth=1;
  ctx.strokeStyle='forestgreen';
  ctx.stroke();
}

function getPointsOnEllipse(cx,cy,a,b){
  var startAngle=-PI/2;
  var lastX=cx-(a*Math.cos(startAngle));
  var lastY=cy+(b*Math.sin(startAngle));
  var points=[];
  for(var i=0;i<1000;i++){
    var angle=startAngle+PI2/1000*i;
    var x=cx-(a*Math.cos(angle));
    var y=cy+(b*Math.sin(angle));
    var dx=x-lastX;
    var dy=y-lastY;
    var length=parseInt(Math.sqrt(dx*dx+dy*dy));
    var eAngle=(Math.atan2(dy,dx)+PI2)%PI2;
    if(length>0){
      points.push({x:x,y:y,angle:eAngle});
      lastX=x;
      lastY=y;
    }
  }
  return(points);
}

function handleMouseMove(e){
  // tell the browser we're handling this event
  e.preventDefault();
  e.stopPropagation();

  mouseX=parseInt(e.clientX-offsetX);
  mouseY=parseInt(e.clientY-offsetY);

  var hit=isInEllipse(mouseX,mouseY);
  var color=(hit)?'red':'green';
  dot(mouseX,mouseY,color);

}
代码语言:javascript
复制
body{ background-color: ivory; }
#canvas{border:1px solid red; }
代码语言:javascript
复制
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<h4>Move mouse in & out of ellipse.<br>Red mouse dots are inside ellipse, Green outside.</h4>
<canvas id="canvas" width=300 height=300></canvas>

票数 4
EN

Stack Overflow用户

发布于 2016-01-12 07:45:00

2DRenderingContext有一个检测点是否在路径中的方法:

代码语言:javascript
复制
CanvasRenderingContext2D.isPointInPath()

你可以把它和每一种路径一起使用,不依赖于几何形式。一个缺点:它只能在绘图时使用,所以你必须在你的嘴上重画场景。对于静态场景来说,这可能是不需要的,但是如果您有一个动画,这应该不是一个问题。

https://developer.mozilla.org/en-US/docs/Web/API/CanvasRenderingContext2D/isPointInPath

票数 1
EN

Stack Overflow用户

发布于 2016-01-11 22:32:16

很抱歉最初的回答含糊不清,这需要改进,但为了让事情进展顺利.

给定椭圆是围绕两个焦点的平面上的一条曲线(F1 & F2)定义的,使得到这两个焦点的距离之和对于曲线上的每一个点都是恒定的。

也就是说,对于椭圆上的任意点P,两个距离的F1P + F2P是一个常数。这个常数(显然和有益的)等于所述椭圆的较长(长)轴A的长度。

因此,对于这个问题,我怀疑椭圆的重要部分不是宽度、高度、x、y,而是它的两个焦点F1和F2 (与定义它的椭圆中心等距的两个点)和主轴的长度。

然后..。对于任何给定的鼠标点击点M,如果2距离F1M + F2M

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/34731883

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档