Java 直线穿过矩形-如何找到交叉点?
我在画布上画了一个矩形,从矩形的中心到坐标空间中的某个随机点画了一条线 现在,我想用矩形内的长度截断这条线,使这条线从矩形边缘开始 我怎么能这样做 示例Java 直线穿过矩形-如何找到交叉点?,java,gwt,math,vector,java-canvas,Java,Gwt,Math,Vector,Java Canvas,我在画布上画了一个矩形,从矩形的中心到坐标空间中的某个随机点画了一条线 现在,我想用矩形内的长度截断这条线,使这条线从矩形边缘开始 我怎么能这样做 示例 矩形可以由两个点定义:Pstart(1,3),Pend(3, 1) 中心点可以计算为:P(2,2) 现在从P(2,2)到Q(10,2)画一条线 我知道矩形的宽度是2,我可以告诉行从p(4,2)开始,而不是p(2,2) 当点不平行于其中一个XY轴时,这会变得更加复杂。此外,对于对角线,矩形内的长度将不同 如何计算直线点相对于矩形中心和直线端
- 矩形可以由两个点定义:
,Pstart(1,3)
Pend(3, 1)
- 中心点可以计算为:
P(2,2)
- 现在从
到P(2,2)
画一条线Q(10,2)
p(4,2)
开始,而不是p(2,2)
当点不平行于其中一个XY轴时,这会变得更加复杂。此外,对于对角线,矩形内的长度将不同
如何计算直线点相对于矩形中心和直线端点的起点偏移
可能我必须找到直线与矩形相交的点,然后让直线从交叉点开始。但是我怎样才能得到这一点呢?矩形的顶点:a,b,c,d。表示每个坐标的x和y坐标,如ax、ay等 直线的端点:x,y 该线跟随y=mx+b,向上或向下、向右或向左移动。这样可以将交叉的可能矩形边缩小到2
使用y=mx+b确定其穿过水平线的垂直坐标,以及其穿过垂直线的水平分量。要么只有一个实际位于矩形上(即,包含在一个矩形边内),要么在一个角相交。老实说,我不懂数学,但是 基本上,你有5行。矩形的原始行和4行。所以,如果你把它分解成一个简单的直线相交的问题,它应该会变得容易一点
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.geom.Ellipse2D;
import java.awt.geom.Line2D;
import java.awt.geom.Point2D;
import java.awt.geom.Rectangle2D;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
public class IntersectPoint {
public static void main(String[] args) {
new IntersectPoint();
}
public IntersectPoint() {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
}
JFrame frame = new JFrame("Testing");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setLayout(new BorderLayout());
frame.add(new TestPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class TestPane extends JPanel {
@Override
public Dimension getPreferredSize() {
return new Dimension(200, 200);
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
int x = (int) (getWidth() * 0.2f);
int y = (int) (getHeight() * 0.2f);
int width = (int) (getWidth() * 0.6f);
int height = (int) (getHeight() * 0.6f);
int x1 = x;
int y1 = 0;
int x2 = x + width;
int y2 = getHeight();
Line2D line = new Line2D.Double(x1, y1, x2, y2);
Rectangle2D rect = new Rectangle2D.Double(x, y, width, height);
Graphics2D g2d = (Graphics2D) g.create();
g2d.draw(rect);
g2d.draw(line);
g2d.setColor(Color.RED);
Point2D[] ps = getIntersectionPoint(line, rect);
for (Point2D p : ps) {
if (p != null) {
g2d.fill(new Ellipse2D.Double(p.getX() - 4, p.getY() - 4, 8, 8));
}
}
g2d.dispose();
}
public Point2D[] getIntersectionPoint(Line2D line, Rectangle2D rectangle) {
Point2D[] p = new Point2D[4];
// Top line
p[0] = getIntersectionPoint(line,
new Line2D.Double(
rectangle.getX(),
rectangle.getY(),
rectangle.getX() + rectangle.getWidth(),
rectangle.getY()));
// Bottom line
p[1] = getIntersectionPoint(line,
new Line2D.Double(
rectangle.getX(),
rectangle.getY() + rectangle.getHeight(),
rectangle.getX() + rectangle.getWidth(),
rectangle.getY() + rectangle.getHeight()));
// Left side...
p[2] = getIntersectionPoint(line,
new Line2D.Double(
rectangle.getX(),
rectangle.getY(),
rectangle.getX(),
rectangle.getY() + rectangle.getHeight()));
// Right side
p[3] = getIntersectionPoint(line,
new Line2D.Double(
rectangle.getX() + rectangle.getWidth(),
rectangle.getY(),
rectangle.getX() + rectangle.getWidth(),
rectangle.getY() + rectangle.getHeight()));
return p;
}
public Point2D getIntersectionPoint(Line2D lineA, Line2D lineB) {
double x1 = lineA.getX1();
double y1 = lineA.getY1();
double x2 = lineA.getX2();
double y2 = lineA.getY2();
double x3 = lineB.getX1();
double y3 = lineB.getY1();
double x4 = lineB.getX2();
double y4 = lineB.getY2();
Point2D p = null;
double d = (x1 - x2) * (y3 - y4) - (y1 - y2) * (x3 - x4);
if (d != 0) {
double xi = ((x3 - x4) * (x1 * y2 - y1 * x2) - (x1 - x2) * (x3 * y4 - y3 * x4)) / d;
double yi = ((y3 - y4) * (x1 * y2 - y1 * x2) - (y1 - y2) * (x3 * y4 - y3 * x4)) / d;
p = new Point2D.Double(xi, yi);
}
return p;
}
}
}
查看用于按矩形进行线裁剪的解决方案。此页上有一组解决方案:在该页上选择对您最有意义的解决方案,然后开始使用。实际上,您可以只使用
y=mx
,因为线从矩形的中心开始。我还没有完全计算出数学,但我认为这不起作用。“b”偏移告诉您x=0的“y”坐标,即斜率为“m”的直线的垂直位置。在一般情况下,这肯定会影响哪个矩形边与直线相交。我不假设这些点中的任何一个都在原点。是的,如果矩形以原点为中心,则只能假设b=0。如果知道其中一条直线是垂直的或水平的,则getIntersectionPoint()函数可以大大简化,您可以这样做。