【问题标题】:Algorithm to detect the point intersect the semi circle in android Java [duplicate]在android Java中检测点与半圆相交的算法[重复]
【发布时间】:2015-01-28 04:51:30
【问题描述】:

我有一个点 x 和 y,我需要检查在半饼图中相交的点。

我需要一种算法来找到与半圆相交的点。对于矩形,我们有 point contains 方法来检查点与矩形相交,但这不适用于具有起点和终点角度的半圆。

我已经创建了许多半饼图段,当我触摸饼图段时,我需要检查与哪个段相交的点。

【问题讨论】:

  • 抱歉,我需要澄清一下。您是否只想找到位于半圆内的所有点?半圆是怎么定义的?
  • @Suresh 如果你知道圆的中心和半径,那么就得到点到中心的距离。如果距离大于半径,即不在其他兴趣范围内相交。
  • 这对于整圆来说很好,我需要让点相交半圆,就像弧一样。
  • 我会采用 Ajit 的解决方案,但是这个半圆是如何定位的?如果它是垂直或水平的,从半径开始检查 x 和 y 值应该很容易。
  • 我已经根据开始和结束角度将馅饼放在了很多地方

标签: java android algorithm


【解决方案1】:

我假设这是速度关键,并且您希望能够将半圆指定为具有中心和任意开始和结束角度,所以不仅仅是一个半圆,而是一个 circular sector .对于半圆,只需将开始角和结束角分开 180 度,或者删除针对 endVector 的测试。

让测试分为两步。对于给定的点,首先检查它是否在包围半圆的矩形内。您可以为此使用现有的排序和二进制搜索算法。如果一个点不在矩形中,则拒绝该点,如果是,则对半圆进行测试。

此外,在循环之外,将指定半圆的值转换为可以更快完成测试的形式:

  • 将半径转换为半径的平方。比较一个点到中心平方的距离与半径的平方。这在计算距离时节省了平方根。

  • 将半圆的起始角和终止角转换为几个二维向量,然后使用它们来检查点是否在扇区内。这样您就不必使用像 atan2(y, x) 这样很慢的三角函数,也不必对开始和结束角度进行烦人的繁琐比较,并处理角度从 360 环绕到 0 的情况。

伪代码:

 float radiusSquared;
 float startVectorX;
 float startVectorY;
 float endVectorX;
 float endVectorY;
 float centerX;
 float centerY;
 void convertSector(float radius, float startAngle, float endAngle)
 {
     radiusSquared = radius * radius;
     startVectorX = cos(startAngle);
     startVectorY = sin(startAngle);
     endVectorX = cos(endAngle);
     endVectorY = sin(endAngle);
 }

 boolean testPoint(float x, float y)
 {
     // check if point is within the radius:
     float distanceX = x - centerX;
     float distanceY = y - centerY;
     if((distanceX * distanceX) + (distanceY * distanceY)) > radiusSq)
         return false;

     // check if point is outside start radius vector using 2D dot-product with normal:
     if(((distanceX * -startVectorY) + (distanceY * startVectorX)) < 0.0f)
         return false;

     // check if point is outside end radius vector using 2D dot-product with normal:
     if(((distanceX * -endVectorY) + (distanceY * endVectorX)) > 0.0f)
         return false;

     return true;
 }

以上代码仅适用于内角 Pac-Man 形状)测试一个点,请测试该点是否在圆圈内,然后测试它是否在该扇区内组成圆圈的其余部分。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-01-09
    • 1970-01-01
    • 1970-01-01
    • 2012-02-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多