Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/350.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 直线与正方形的交点_Java_Geometry_Intersection_Square_Line Segment - Fatal编程技术网

Java 直线与正方形的交点

Java 直线与正方形的交点,java,geometry,intersection,square,line-segment,Java,Geometry,Intersection,Square,Line Segment,我在二维空间中有一个正方形(宽度=高度)。正方形当前由两个点定义:左下角(X1,Y1)和右上角(X2,Y2) 正方形是轴对齐的,因此找到其他两个角与(X1,Y2)和(X2,Y1)一样容易 我还有两点——一点总是在广场内,另一点肯定在广场外。他们不一定在广场的中心,他们可以在任何地方。我也知道他们的坐标 我需要的是找到由这两点定义的线段与正方形边之间的交点。我还想知道我和广场的哪一边相交。给我带来麻烦的是直线成对角线,并且靠近正方形的角——例如,它可以与顶线或边线相交 蛮力法是尝试计算正方形每一侧

我在二维空间中有一个正方形(宽度=高度)。正方形当前由两个点定义:左下角(X1,Y1)和右上角(X2,Y2)

正方形是轴对齐的,因此找到其他两个角与(X1,Y2)和(X2,Y1)一样容易

我还有两点——一点总是在广场内,另一点肯定在广场外。他们不一定在广场的中心,他们可以在任何地方。我也知道他们的坐标

我需要的是找到由这两点定义的线段与正方形边之间的交点。我还想知道我和广场的哪一边相交。给我带来麻烦的是直线成对角线,并且靠近正方形的角——例如,它可以与顶线或边线相交

蛮力法是尝试计算正方形每一侧的交点,并检查其是否存在。它可以通过计算第二个点相对于正方形的位置并丢弃两条线(例如,如果X和Y坐标都增加,则无需检查正方形的底部和左侧)来优化


我想知道是否有更好/更快的方法解决我的问题?我将用Java编写让内部点是
(x0,y0)
,外部点是
(ox,oy)

以参数形式表示线

现在根据方向查找可能的边界位置:

if vx > 0 then
   ex = x2
else
   ex = x1

if vy > 0 then
    ey = y2
else
   ey = y1
检查水平/垂直线方向的额外情况:

 if vx = 0 then
      return cx = x0,  cy = ey

 if vy = 0 then
      return cx = ex, cy = y0
通常情况下,查找与水平和垂直边缘线相交的参数

 tx = (ex - x0) / vx
 ty = (ey - y0) / vy
并获得较小参数值的交点

 if tx <= ty then //meet vertical edge first
     return cx = ex, cy = y0 + tx * vy
 else
    return  cx = x0 + ty * vx,  cy = ey

如果发送有效解决方案:

我假设您知道哪个点在正方形内(也可以是矩形)

从所有其他点(第二个端点和四个角点)减去该点的坐标。考虑平面在九个区域中的细分,通过扩展正方形的边来形成。要知道另一个点位于八个外部区域中的哪一个区域,需要进行四次符号测试

然后,如果该点位于“边”区域中,您就可以隐式地知道哪边是交叉的。如果点位于“角点”区域中,则必须在两条边之间做出决定,这是通过检查角点位于线段的哪一侧来完成的。这需要计算三角形的有符号面积(两乘一减)

当你知道哪一边是交叉的,很容易通过比例找到交叉点。这只需要一个除法

最后,将平移回内部点的原始位置。总成本为

  • 四减去

  • 四个符号测试

  • 对于角区域,两次乘一次减

  • 一个师

  • 两项补充

再加上一点胶水逻辑


这不能保证是一个绝对最小值,但必须接近。

哇,这确实好得多!我根本没想过要这样做!非常感谢。我会把你的答案标记为正确的。你知道两点中的哪一点在里面吗?谢谢,我有时间去看看。我正在做其他事情,但我会试试你的解决方案
 if tx <= ty then //meet vertical edge first
     return cx = ex, cy = y0 + tx * vy
 else
    return  cx = x0 + ty * vx,  cy = ey