place points with only distance matrix - algorithm

I want to visualize some points, but only a distance matrix for them is given. It is there any good method to get one possible way to place them on 2D space.
Input: a distance matrix
Ouput: coordinates of these points

For a given matrix, if you come up with a possible placement, then any translation of the points will also satisfy the matrix, as will any rotation, and also mirroring.
For one possible placement:
Choose 3 points A B C (i.e. 3 rows from the matrix) that form a triangle with distances AB, AC and BC taken from the matrix. The points can't all lie on a line, so AB != AC + BC, AC != AB + BC and BC != AB + AC.
Place A at the origin and B at (AB, 0). Then use the Cosine rule to deduce the angle between the lines AB and AC:
angle = arccos((AB2 + AC2 - BC2) / (2 * AB * AC))
Now that you have the angle you can calculate the position of C:
C = (cos(angle) * AC, sin(angle) * AC);
You now have positions for A B and C. You can go through each of the other rows in the matrix corresponding to the other points, and find the distance between each point and A B and C. Then you can use this formula to work out the position of the point based on your assumed positions of A B C and the distance of the point to each:
Finding location of a point on 2D plane, given the distances to three other know points
So, you only actually need 3 values from each row of the matrix. For a large matrix, most of it is totally redundant. This might be helpful to you if you are trying to minimize storage space.
Remember that any translation, rotation and mirroring is also valid.

Related

How can I find the coordinates of the resulting vector so that I can display it on an image?

I try to calculate and display a point on an image. Suppose I have the following points:
A = (x1, y1)
B = (x2, y2)
C = (x3, y3)
I want to calculate the coordinates of the resulting vector between the vectors AB and AC. What I thought:
AB=(x2-x1,y2-y1)
AC=(x3-x1,y3-y1)
and the resulting vector would be
AD(for example)=(((x2-x1)+(x3-x1)),((y2-y1)+(y3-y1)))
I'm not sure I thought well mathematically, but my biggest problem is that the result does not match the image, the coordinates can give negative numbers after this calculation. How can I find the coordinates of the resulting vector so that I can display it on an image?
I also added a small image, to better understand what I'm trying to say:
What you are doing is essentially adding two vectors, AD = AC + AB. So your image is correct if that is what you want to do. As for the negative numbers this depends on what your vectors are. The vector will be negative if it goes opposite the positive directions of your coordinate system.
Added an image to show how the vector AD is made graphically:
I recommend checking out some basic vector operations
EDIT: found similar topics:
How to get the vector between two vectors?
Hmm so if I see it right you want something between mirror and projection ... As there is probably no guarantee than AB and AC are symmetrical ...
I would try this using vector math:
ba = A-B
bc = C-B
E = B + bc* dot(ba,bc)/(|bc|^2)
D = E + (E-A)
D = 2.0*E - A
D = 2.0*(B + bc* dot(ba,bc)/(|bc|^2)) - A
Where dot(a,b)=a.x*b.x+a.y*b.y is scalar multiplication and |a|^2=(a.x*a.x)+(a.y*a.y) is vector size squared
So the E is perpendicular projection of A onto BC and D is mirror reflection of A around E and BC ...

how to get new coordinates with width, length and angle known?

I have trapezoid with three coordinates known. So I need to create 4th coordinate with length, width and angles I am having. You can assume this problem with triangle as ADC from trapezoid. The model comes as differently expected . The Law of cosines gives the angle but it should be applied to local coordinates of the model. Right side I am showing with arrow pointed as wrong object which i am getting. Even if I rotate the object or flip it, the coordinates should not get wrong.
newWidth2 is AB. newLength is AD. Point C need to be created from A,D with angle D. Math.Pow is "to the power of" and 2 is it's square.(for who can't understand this notation).
Assume that I dont have coordinates of C. I know only A,D coordinates. I know length of AD, Width2 and Width1. I can get angle ADC from initial coordinates of C where coordinates of C will vary when I change Width2 of DC. So coordinates of C will be based on length of AD, angle D and so on. Finally what I need is coordinates of C if the entire object is rotated in any angle.
newWidth2 is AB.
newLength is AD.
Point C need to be created from A,D with angle A or angle D also.
Math.Pow is "to the power of" and 2 is it's square.(for who can't understand this notation).
//Initially I will have Coordinates for C but later I should remove them and create from the model width and heights. So I can't take input as C Coordinates of (X3,Y3) which I already have.
//distance formula
newWidth2 = Math.Sqrt(Math.Pow(CoordX3 - CoordX5, 2) + Math.Pow(CoordY3 - CoordY5, 2));
//from the formula -> b2 = a2 + c2 - 2acCos(B)
diagangle = Math.Acos((Math.Pow(newWidth2, 2) - Math.Pow(newdiagonal, 2) - Math.Pow(newLength, 2)) / (-2 * (newdiagonal) * (newLength)) );
//I am getting this C coordinates as wrong.
//for getting C (third coordinates)
xcoord3 = CoordX5 + (newWidth2 * Math.Cos(diagangle));
ycoord3 = CoordY5 + (newWidth2 * Math.Sin(diagangle));
//sample values of one model
Width1 36
Width2 24
Length 88.0783
A
CoordX1 43.944
CoordY1 409.2514
B
CoordX2 46.9337
CoordY2 373.3758
C
CoordX3 133.7111
CoordY3 392.6488
D
CoordX4 131.718
CoordY4 416.5659
It is not clear what exactly is known and what is to be found. I assume that you know coordinates of A, B, C and length AB = width1 and CD = width2 and need to find coordinates of D.
I think this problem is easier to solve if you see it as a vector problem rather than a trigonometry problem. If you look at vectors BA and CD you may see that they are collinear and |BA| = width1 while |CD| = width2. It means that vector CD = width2/width1 * BA. Not you can trivially calculate the coordinates of D by:
Calculating vector BA
Calculating CD = width2/width1 * BA
Calculating D = C + CD

How much a point inside an ABC triangle moved from its origin, knowing the offset of the A,B,C

I'm trying to measure in % how much the X and Y coordinates of a point inside an ABC triangle moved from its original place, knowing how much % has the A,B,C points moved.
Example: Knowing that the following points moved from their original position: A.x 30%, A.y 45%, B.x 10%, B.y 20%, C.x 70%, C.Y 60%, find out how much the coordinates X and Y of a point P inside the A,B,C triangle moved.
How can I calculate the offset of any point inside such a triangle?
I believe you need the Barycentric coordinates here. Eventually those give you a chance to represent a given point P in the triangle with vertices t1, t2, t3 as P = a * t1 + b * t2 + c * t3. Given this, the new coordinates after translating the triangle into t1', t2', t3' will result into P' = a * t1' + b * t2' + c * t3' i.e. you would just apply the same weights to every corner.
Taken into account you start with cartesian coordinates here are the formulas to do the conversion from cartesian to barycentric i.e. find the a, b, c I mentioned before.
Since you did have the c++, I'll answer the question from a programmer prospective rather than a mathematician so this may not be the best mathematical way to do it. the way i would calculate this is I would first work out the left-most and right-most point of the triangle so this would be the points with the lowest x value and the highest x value then using the following formula we calculate it's percentile position within the triangle.
percentile.x = (rightMostPoint.x - leftMostPoint.x) / (point.x - leftMostPoint.x);
The Y axis is pretty much the same. Please note as well that firstly this function returns a float percentile so 0.5 = 50% and also a values between 0% and 100% don't guarantee that the point is within the triangle.
Now you know the percentile position you can simply calculate the difference in between the before and after percentile position. i.e.
percentileChangeOnX = abs(precentPosBefore.x - precentPosAfter.x);

Finding the length of 3 rectangles so that they share one corner to form a triangle, given a common width and 3 points

Hi sorry for the confusing title.
I'm trying to make a race track using points. I want to draw 3 rectangles which form my roads. However I don't want these rectangles to overlap, I want to leave an empty space between them to place my corners (triangles) meaning they only intersect at a single point. Since the roads have a common width I know the width of the rectangles.
I know the coordinates of the points A, B and C and therefore their length and the angles between them. From this I think I can say that the angles of the yellow triangle are the same as those of the outer triangle. From there I can work out the lengths of the sides of the blue triangles. However I don't know how to find the coordinates of the points of the blue triangles or the length of the sides of the yellow triangle and therefore the rectangles.
This is an X-Y problem (asking us how to accomplish X because you think it would help you solve a problem Y better solved another way), but luckily you gave us Y so I can just answer that.
What you should do is find the lines that are the edges of the roads, figure out where they intersect, and proceed to calculate everything else from that.
First, given 2 points P and Q, we can write down the line between them in parameterized form as f(t) = P + t(Q - P). Note that Q - P = v is the vector representing the direction of the line.
Second, given a vector v = (x_v, y_v) the vector (y_v, -x_v) is at right angles to it. Divide by its length sqrt(x_v**2 + y_v**2) and you have a unit vector at right angles to the first. Project P and Q a distance d along this vector, and you've got 2 points on a parallel line at distance d from your original line.
There are two such parallel lines. Given a point on the line and a point off of the line, the sign of the dot product of your normal vector with the vector between those two lines tells you whether you've found the parallel line on the same side as the other, or on the opposite side.
You just need to figure out where they intersect. But figuring out where lines P1 + t*v1 and P2 + s*v2 intersect can be done by setting up 2 equations in 2 variables and solving that. Which calculation you can carry out.
And now you have sufficient information to calculate the edges of the roads, which edges are inside, and every intersection in your diagram. Which lets you figure out anything else that you need.
Slightly different approach with a bit of trigonometry:
Define vectors
b = B - A
c = C - A
uB = Normalized(b)
uC = Normalized(c)
angle
Alpha = atan2(CrossProduct(b, c), DotProduct(b,c))
HalfA = Alpha / 2
HalfW = Width / 2
uB_Perp = (-uB.Y, ub.X) //unit vector, perpendicular to b
//now calculate points:
P1 = A + HalfW * (uB * ctg(HalfA) + uB_Perp) //outer blue triangle vertice
P2 = A + HalfW * (uB * ctg(HalfA) - uB_Perp) //inner blue triangle vertice, lies on bisector
(I did not consider extra case of too large width)

I'm implementing the Expanding Polytope Algorithm, and I am unsure how to deduce the contact points from a point on the minkowski difference

I've been reading about the EPA from several sources, but they all seem to abruptly stop being useful after the closest point on the minkowski difference to the origin is located. Most of them say something along the lines of "With this information, we can then generate the local and global contact points and contact tangents," but I don't understand how that is even possible, much less how to do it. I don't see how someone could derive the minuend and subtrahend from a difference alone, and certainly not in a reasonable amount of time. What is the standard solution to this problem?
I am looking to implement this algorithm in 3D, if that changes the answer. Thanks
OP of the blog post here.
The post actually says how to compute the contact point in step 8 of the EPA algorithm:
Project the origin onto the closest triangle. This is our closest
point to the origin on the CSO’s boundary. Compute the barycentric
coordinates of this closest point with respect to the vertices from
the closest triangle. The barycentric coordinates are coefficients of
linear combination of vertices from the closest triangle. Linearly
combining the individual support points (original results from
individual colliders) corresponding to the vertices from the closest
triangle, with the same barycentric coordinates as coefficients, gives
us contact points on both colliders in their own model space. We can
then convert these contact points to world space.
Allow me to rephrase it here.
Let Ca, Cb, and Cc denote the three vertices of the triangle of the CSO that contains the closest point, denoted Cp, on the CSO boundary to the origin.
Compute the barycentric coordinate (x, y, z) of the triangle for Cp.
x Ca + y Cb + z Cc = Cp
Note that it is required that we keep the original support function results in global space from the two objects (A & B) used to obtain Ca, Cb, and Cc. Let Aa, Ab, and Ac denote the original support function results for object A. Let Ba, Bb, and Bc denote the original support function results for object B.
Ca = Aa + Ba
Cb = Ab + Bb
Cc = Ac + Bc
Using the barycentric coordinate (x, y, z) obtained earlier to linearly combine the original support function results from object A & B, we can compute the contact points on both objects, denoted Ap and Bp:
Ap = x Aa + y Ab + z Ac
Bp = x Ba + y Bb + z Bc
I hope this clarifies the computation process for you.

Resources