I asked this question earlier but didn't communicated it clearly, so forgive me for the duplicate. This should be better.
I need to figure the position of a coordinate, given three other coordinates and 2 slopes. Basically, the intersection point of two lines. However, I don't have all of the information normally available to solve this.
I have an arbitrary shape defined by a bunch of vertices. The user may drag a line between these vertices and the shape should react as the diagrams below show.
So in the first example, the user drags line EF from the position on the left to the position on the right (line E2F2). What needs to happen is that line EF grows/shrinks such that it's slope stays the same and that it's beginning and ending coordinates remain on the lines DE and AF respectively. This is shown as line E2F2.
This needs to be generic enough that it can handle any sort of strange or regular angles I throw at it. The second set of shapes shows a simpler approach. The user drags line CD to the position of C2D2. Notice how the slopes stay the same and D2 essentially slides down that diagonal line and B2C2 and C2D2 both extend in length. The result is that all 3 slopes stay the same but lines B2C2 and C2D2 grow in length to stay connected, while line D2E2 shrinks.
You'll need to understand that when dragging line EF, you're actually moving the coordinate "E". So, figuring the first coordinate is easy. And the previous and next one's never change. So I essentially have the slopes of the 3 relevant lines and 3 of the 4 necessary coordinates. I need the 4th, so in my example, F2 or D2.
This code is called on an event every time the coordinate moves. Lets say we're dragging line EF - the coordinate is E then.
var next = this.model.get("next"), // coordinate F
nextNext = next.get("next"), // coordinate A
nextDx = nextNext.get("x") - next.get("x"), // delta X of AF
nextDy = nextNext.get("y") - next.get("y"), // delta Y of AF
prev = this.model.get("prev"), // coordinate D
prevDx = prev.get("x") - this.model.get("x"), // delta X of DF
prevDy = prev.get("y") - this.model.get("y"), // delta Y of DF
selfDx = next.get("x") - this.model.get("x"), // delta X of EF
selfDy = next.get("y") - this.model.get("y"), // delta Y of EF
selfX = this.initialCoords.x + this.shape.getX(), // the new position of E
selfY = this.initialCoords.y + this.shape.getY(),
selfM, selfB, prevM, prevB, nextM, nextB, m, x, y, b;
// check for would-be infinities
if (selfDx == 0) {
// **** THIS WHOLE BLOCK IS CORRECT ****
// i'm vertical
// we can safely assume prev/next aren't also vertical. i think? right?
prevM = prev.get("slope");
prevB = prev.get("y") - prevM * prev.get("x");
var myX = selfX,
myY = prevM * myX + prevB;
this.model.set({
x: myX,
y: myY
});
nextM = next.get("slope");
nextB = next.get("y") - nextM * next.get("x");
var nextX = selfX,
nextY = nextM * nextX + nextB;
next.set({
x: nextX,
y: nextY
});
} else if (selfDy == 0) {
//***** THIS WHOLE BLOCK IS CORRECT **** //
// i'm horizontal
if (prevDx == 0) {
// prev is a vertical line
this.model.set({
y: selfY
});
} else {
prevM = prev.get("slope");
prevB = prev.get("y") - prevM * prev.get("x");
var myY = selfY,
myX = (selfY - prevB) / prevM;
this.model.set({
x: myX,
y: myY
});
}
if (nextDx == 0) {
// next is a vertical line
next.set({
y: selfY
});
} else {
nextM = next.get("slope");
nextB = next.get("y") - nextM * next.get("x");
var nextY = selfY,
nextX = (selfY - nextB) / nextM;
next.set({
x: nextX,
y: nextY
});
}
} else {
// HELP HERE - you've chosen to drag an arbitrarily angled line. Figure out the "next" coordinate given the "current" one.
selfM = this.model.get("slope");
selfB = this.model.get("y") - this.model.get("slope") * this.model.get("x");
if (selfM < 0) {
prevM = prev.get("slope");
prevB = prev.get("y") - prevM * prev.get("x");
var myY = selfY,
myX = (selfY - prevB) / prevM;
// CORRECT, but need "next" position based on this
this.model.set({
x: myX,
y: myY
});
} else {
// CORRECT but need "next" position based on this.
var myX = selfX;
this.model.set({
x: myX
});
}
}