Algorithm for putting double border around isosceles triangle - algorithm

I've been trying to figure out the best way to draw double border around an isosceles triangle in source code. I would like to draw something like the following:
I've tried two approaches neither of which work.
First the naive approach. Enlarge the bounding box and redraw the triangle inside the larger box. Problem is that the space between the two triangles is uneven. A bit of algebra shows why this is the case. See next image:
Scale the triangle relative to the center point. I do this by translating the 'center' of the triangle to the origin, scale and translate back. I compute the center using cx = (x1+x2+x3)/3, and cy = (y1+y2+y3)/3 (centroid center), and x and y are the coordinatess of the vertices. If I do this I get the following image which is obviously not right either.
Question. I think approach number two should work but I am using the right center when scaling?

The scaling center you should use is the Incenter and not the Centroid. You could find the incenter using the formula:
((a*x1+b*x2+c*x3)/(a+b+c), (a*y1+b*y2+c*y3)/(a+b+c))
where a is the length of the side opposite to the point (x1, y1), b - the opposite to (x2, y2) and c - (x3, y3).
Visual proof:
Notice that it is irrelevant whether the triangle is isosceles.

Related

Draw shapes between coordinates

Given some random w and h and 4 coordinates(x1, y1)...(x4, y4) check if x, y counters are inside those 4 coordinates.
I am trying to fill the space between those 4 coordinates, they will usually form a rectangle shape, but at different rotations.
At the moment I have a nested for loop to move over my "canvas", but I am failing to find a way to check if my counters are inside the coordinates.
I have looked at line drawing algorithms to build this, but so far no luck.
Can someone point me to some resources please.
To check if a point is inside a triangle, take the orientation
(y2 - y1)*(x3 - x2) - (y3 - y2)*(x2 - x1)
the sign is zero if the points are linear, otherwise it is negative for counter-clockwise and positive for clockwise. If orientation ABC, ABD, and ACD is the same, then A is in the triangle BCD.
So we can first check our convex hull which will either be a line, a triangle, or a quad. If it is a triangle, we can easily test for further points inside. It it is a convex quad, the test also works, but we have to add an extra point.

Equidistant Points in Wrapping Rectangle

I am having trouble figuring out the math for a problem I am having.
I have an n by m rectangle and need to place k points in it such that points are, as close as possible, completely equidistant from each other.
Normally this is pretty easy, I construct the regular polygon with k points on it, center it in the center of my rectangle, stretch it to fit and voila, its vertices are my output points.
The catch is that when calculating distances on this rectangle, you can wrap. As such the point (0,0) is just 1 pixel away from the point (n-1,m-1) (using 0-indexed coordinates).
I've been messing around a bit on paper and getting nowhere fast with this. Does anybody have any idea how to calculate this?
tl;dr:
Inputs: n - width of rectangle, m - height of rectangle, k - number of points
Outputs: k pairs of (x,y) coordinates
Constraints: the output coordinates are equidistant from one another under wrapping coordinate systems.
Any advice on where I could look for such a geometry problem?

Tricky Line Algorithm for a Game (language agnostic)

I need help creating a specialized line-collision algorithm that allows "cutting corners" at certain angles.
In the following pictures, let the blue square represent the player and the black square represent a wall. The white squares, then, represent squares in a player's "line of sight" (valid squares), and the grey squares are squares outside a player's "line of sight" (invalid squares):
The second image is where things get more interesting as we start cutting corners:
Let's take a closer look at this line which is allowed despite passing over the corner of the wall:
The line is allowed because:
dx <= 0.5 (with a square being 1x1)
dx/dy is above a certain ratio (say, 2 - I'm not sure of the exact value represented in these images.)
The converse line is not allowed because the ratio (of dy/dx in this case) is too low:
Or perhaps I should talk about the angle of entry vs exit from the square....
The main problem I'm having is that I can't figure out how to generalize a solution for vectors traveling at any angle between two points on the grid. I can't decide if I should use trigonometry or what. My closest solution so far has been to use the decimal parts of line interceptions with each square as the dx and dy's and check whether it's allowed based on the slope of the line and what quadrant it's in.
Can anyone help?
I've also looked at borrowing or starting from other line algorithms, but I haven't found anything too useful. Most of them that I've seen want a line from (x1, y1) to (x2, y2) to be the same as from (x2, y2) to (x1, y1) which makes this problem quite different.
I suggest using circles, they are quite optimal corner wise.
I assume that coordinates are taken at the center of each pixels.
The algorithm for knowing if (xo,yo) is hiding the view from (xa,ya) to (xb,yb) would then be:
compute (xc,yc) the nearest point to (xo,yo) on the line from (xa,ya) to (xb,yb)
compute distance d from (xo,yo) to (xc,yc)
if d < half a pixel, then the view is hidden
You can simplify first two stages by directly calculating the distance between point and line http://en.wikipedia.org/wiki/Distance_from_a_point_to_a_line and eventually compute squared distance if you want to avoid sqrt

How to find collision center of two rectangles? Rects can be rotated

I've just implemented collision detection using SAT and this article as reference to my implementation. The detection is working as expected but I need to know where both rectangles are colliding.
I need to find the center of the intersection, the black point on the image above (but I don't have the intersection area neither). I've found some articles about this but they all involve avoiding the overlap or some kind of velocity, I don't need this.
The information I've about the rectangles are the four points that represents them, the upper right, upper left, lower right and lower left coordinates. I'm trying to find an algorithm that can give me the intersection of these points.
I just need to put a image on top of it. Like two cars crashed so I put an image on top of the collision center. Any ideas?
There is another way of doing this: finding the center of mass of the collision area by sampling points.
Create the following function:
bool IsPointInsideRectangle(Rectangle r, Point p);
Define a search rectangle as:
TopLeft = (MIN(x), MAX(y))
TopRight = (MAX(x), MAX(y))
LowerLeft = (MIN(x), MIN(y))
LowerRight = (MAX(x), MIN(y))
Where x and y are the coordinates of both rectangles.
You will now define a step for dividing the search area like a mesh. I suggest you use AVG(W,H)/2 where W and H are the width and height of the search area.
Then, you iterate on the mesh points finding for each one if it is inside the collition area:
IsPointInsideRectangle(rectangle1, point) AND IsPointInsideRectangle(rectangle2, point)
Define:
Xi : the ith partition of the mesh in X axis.
CXi: the count of mesh points that are inside the collision area for Xi.
Then:
And you can do the same thing with Y off course. Here is an ilustrative example of this approach:
You need to do the intersection of the boundaries of the boxes using the line to line intersection equation/algorithm.
http://en.wikipedia.org/wiki/Line-line_intersection
Once you have the points that cross you might be ok with the average of those points or the center given a particular direction possibly. The middle is a little vague in the question.
Edit: also in addition to this you need to work out if any of the corners of either of the two rectangles are inside the other (this should be easy enough to work out, even from the intersections). This should be added in with the intersections when calculating the "average" center point.
This one's tricky because irregular polygons have no defined center. Since your polygons are (in the case of rectangles) guaranteed to be convex, you can probably find the corners of the polygon that comprises the collision (which can include corners of the original shapes or intersections of the edges) and average them to get ... something. It will probably be vaguely close to where you would expect the "center" to be, and for regular polygons it would probably match exactly, but whether it would mean anything mathematically is a bit of a different story.
I've been fiddling mathematically and come up with the following, which solves the smoothness problem when points appear and disappear (as can happen when the movement of a hitbox causes a rectangle to become a triangle or vice versa). Without this bit of extra, adding and removing corners will cause the centroid to jump.
Here, take this fooplot.
The plot illustrates 2 rectangles, R and B (for Red and Blue). The intersection sweeps out an area G (for Green). The Unweighted and Weighted Centers (both Purple) are calculated via the following methods:
(0.225, -0.45): Average of corners of G
(0.2077, -0.473): Average of weighted corners of G
A weighted corner of a polygon is defined as the coordinates of the corner, weighted by the sin of the angle of the corner.
This polygon has two 90 degree angles, one 59.03 degree angle, and one 120.96 degree angle. (Both of the non-right angles have the same sine, sin(Ɵ) = 0.8574929...
The coordinates of the weighted center are thus:
( (sin(Ɵ) * (0.3 + 0.6) + 1 - 1) / (2 + 2 * sin(Ɵ)), // x
(sin(Ɵ) * (1.3 - 1.6) + 0 - 1.5) / (2 + 2 * sin(Ɵ)) ) // y
= (0.2077, -0.473)
With the provided example, the difference isn't very noticeable, but if the 4gon were much closer to a 3gon, there would be a significant deviation.
If you don't need to know the actual coordinates of the region, you could make two CALayers whose frames are the rectangles, and use one to mask the other. Then, if you set an image in the one being masked, it will only show up in the area where they overlap.

Formula to determine whether a line form by 2 geo points (lat, lon) intersects geo region (circle)?

It does not need to be very accurate. Does anyone know a good way to do this?
any help is much appreciated.
When you say “it does not need to be very accurate” you don’t say how inaccurate a solution you’re prepared to accept. Also, you don’t say how big the geographic region under consideration is likely to be. These two criteria make a big difference to the kind of approach that needs to be taken.
With a small regions (a few kilometres, say), a flat approximation may be good enough (for example, the Mercator projection) and some of the other responses tell you how to do that. With larger regions you have to take the Earth’s sphericity into account. And if you want inaccuracy less than a percent or so, you need to take the eccentricity of Earth into account.
I’m going to assume for the purposes of this answer that a spherical approximation is good enough, and that your points are at similar enough altitudes that we don’t need to worry about their heights.
You can convert a geographical point (ψ, λ) to Cartesian Earth-centred coordinates using the transformation
(ψ, λ) → (a cos(ψ) cos(λ), a cos(ψ) sin(λ), a sin(ψ))
where a is the mean radius of the Earth (6,371 km). So let’s suppose that the two points that define your line are p₀ and p₁; then the shortest line through p₀ and p₁ is a great circle, which defines a plane that slices the Earth into two halves, with normal n = p₀ × p₁.
Now we need to find the border of the circular region. Suppose the centre of this region is at c and that the surface radius of the region is s. Then the straight-line radius of the region is r = a sin(s/a). We’ll also need the true centre of the circular region, c’ = c cos(s/a). (This point is buried deep underground!)
We’d like to intersect the two circles and solve for the points of intersection. Unfortunately, because of numerical imprecision, the chances are that this procedure will never find any solutions because the imprecise circles will miss each other in 3 dimensions. So I suggest the following procedure: intersect the planes of the two circles, getting the dotted line shown below (unless c’ × n = 0 in which case the two circles are parallel and either c’ = o, in which case they are coincident, or else they do not intersect). Then intersect the line with the circular region.
This two-step procedure reduces the problem to two dimensions, and guarantees that a solution will be found even if numerical imprecision makes the two circles miss in 3 dimensions.
If you need more accuracy than this, then you might need to use geodetic coordinates on a reference ellipsoid such as WGS 1984.
I'd say find the closest point on the line to the center of the circle, then determine whether that point is within the circle (i.e. the distance in question is less than or equal to the circle's radius).
Outline for solving the problem: assume the Earth is a sphere of radius one centered at the origin. Convert all three lat, lon points to 3D coordinates. The two points of the line plus the origin define a plane; intersect that plane with the sphere of radius d centered on the other point. If there is no plane-sphere intersection, then the answer is the line does not intersect the region. If there is a plane-sphere intersection, then the problem is simplified to intersecting the circular region defined by the plane-sphere intersection with the shortest circular arc on the plane going between the end points of the line and centered at the origin. This is a straightforward 2D problem if you convert to the coordinate system of the plane.
This question is too vague to be answered precisely. What do you mean by
a line form by 2 geo points (lat, lon)
This can be either a great circle going through them (also called orthodrome) or it a can be a linear function of spherical coordinates (loxodrome).
BTW, I assume your circle is a circle on the surface of the sphere, right?
Assuming line is formed by points (x1, y1) and (x2, y2), and circle has radius r with origin (0,0):
Calculate:
Incidence = r^2 * [(x2 - x1)^2 + (y2 - y1)^2] - (x1 * y2 - x2 * y1)^2
Then, from the value of Incidence, we can determine the following:
Incidence < 0: No intersection
Incidence = 0: Tangent (intersection at 1 point on circle)
Incidence > 0: Intersection
It's likely your circle is not at the origin (0,0), so to fix this, just add the origin coordinates from your line coordinates in the equation above. So, if the circle is at (x3, y3), x1 in the above equation would become x1 + x3. Likewise, y1 would be y1 + y3, and the same goes for x2 and y2.
For more info check out this link

Resources