найти точку пересечения двух векторов независимо от направления - PullRequest
1 голос
/ 24 октября 2019

У меня есть два вектора, и я хочу знать, где эти векторы будут пересекаться независимо от направления или длины. Итак, давайте просто скажем, что я бы нарисовал бесконечную линию в любом направлении, и я хочу знать, где эти две линии будут пересекаться, и получить координаты. См. Изображение ниже для уточнения:

enter image description here

Итак, я хочу знать координаты розового X. Но я могу найти только формулы для расчета точки пересеченияиз двух линий со стандартной и конечной точкой, которых у меня нет :( Поэтому я ищу некоторую помощь о том, как правильно подойти к этому.

Я вычислил нормализованное направление синих линий: вот так:

PVector norm12 = new PVector(-dir12.y, dir12.x);
PVector norm23 = new PVector(dir23.y, -dir23.x);

Некоторый контекст о том, почему я хочу сделать это: я пытаюсь найти центральную точку круга, созданного из 3 точек.

Все это в 2D

Если нужна дополнительная информация, я с радостью предоставлю.

1 Ответ

1 голос
/ 24 октября 2019

Если у вас есть бесконечная линия, которая определяется точкой P и нормализованным направлением R, и вторая бесконечная линия, которая определяется точкой Q и направлением S, тоТочка пересечения бесконечных линий X составляет:

alpha ... angle between Q-P and R
beta  ... angle between R and S

gamma  =  180° - alpha - beta

h  =  | Q - P | * sin(alpha)
u  =  h / sin(beta)

t  = | Q - P | * sin(gamma) / sin(beta)

t  =  dot(Q-P, (S.y, -S.x)) / dot(R, (S.y, -S.x))  =  determinant(mat2(Q-P, S)) / determinant(mat2(R, S))
u  =  dot(Q-P, (R.y, -R.x)) / dot(R, (S.y, -S.x))  =  determinant(mat2(Q-P, R)) / determinant(mat2(R, S))

X  =  P + R * t  =  Q + S * u

Это можно рассчитать с помощью PVector, следующим образом:

// Intersect 2 endless lines
// line 1: "P" is on endless line, the direction is "dir1" ("R")
// line 2: "Q" is on endless line, the direction is "dir2" ("S")
PVector Intersect( PVector P, PVector dir1, PVector Q, PVector dir2) {

    PVector R = dir1.copy();
    PVector S = dir2.copy();
    R.normalize();
    S.normalize();

    PVector QP  = PVector.sub(Q, P);
    PVector SNV = new PVector(S.y, -S.x);

    float t  =  QP.dot(SNV) / R.dot(SNV); 

    PVector X = PVector.add(P, PVector.mult(R, t));
    return X;
}

См. Пример:

void setup() {
    size(500,500);
}

void draw() {

    background(0, 0, 0);

    stroke(255);
    fill(255, 0, 0);

    PVector l1p1 = new PVector(250, 150);
    PVector l1p2 = new PVector(300, 300);
    PVector l2p1 = new PVector(200, 180);
    PVector l2p2 = new PVector(300, 220);
    PVector l3p1 = new PVector(200, 300);
    PVector l3p2 = new PVector(250, 280);

    line(l1p1.x, l1p1.y, l1p2.x, l1p2.y);
    line(l2p1.x, l2p1.y, l2p2.x, l2p2.y);
    line(l3p1.x, l3p1.y, l3p2.x, l3p2.y);

    PVector dir1 = PVector.sub(l1p2, l1p1);
    PVector dir2 = PVector.sub(l2p2, l2p1);
    PVector dir3 = PVector.sub(l3p2, l3p1);

    PVector x1 = Intersect(l1p1, dir1, l2p1, dir2);
    circle(x1.x, x1.y, 10);
    PVector x2 = Intersect(l1p1, dir1, l3p1, dir3);
    circle(x2.x, x2.y, 10);
    PVector x3 = Intersect(l2p1, dir2, l3p1, dir3);
    circle(x3.x, x3.y, 10);
}

Обратите внимание, если линии параллельнытогда скаляры возвращаемой точки (PVector объекта) бесконечны. Это можно оценить по Float.isInfinite. например:

if (!Float.isInfinite(x1.x) || !Float.isInfinite(x1.y))
    circle(x1.x, x1.y, 10);
...