Comparing position of two sets of points on 2D image - algorithm

I've got question about algorithms to compare if two sets of points are in a similar place on the image.
They don't create similar shapes likes circles, rectangles etc, but they are something like irregular clouds.
For example:
The first cloud of points is learning set of desired area on image and we are checking if second cloud is in similar position.
I was thinking of drawing simple shapes to form points (like rectangles which will accumulate all points) and checking if one is in another or distance between centers of figures, but this method doesn't seem to be very accurate.
Are there better algorithms to solve this problem?

Image Moments
Don't worry about the fancy name, it's just a standard method in image processing to do exactly what you require.
Image moment of power n w.r.t. x and m w.r.t. y is actually the
integration of (pixel value * xPosition^n * xPosition^m) over the
entire image.
So (0, 0)th order moment i.e moment(0, 0) is actually area of the cloud.
Similarly, moment(1, 0)/moment(0, 0) is X coordinate of centroid of the cloud.
And, moment(0, 1)/moment(0, 0) is Y coordinate of centroid of the cloud.
Higher order moments give additional features/information peculiar to shape of the clouds.
Now you can easily compare the arbitrary shapes.
These functions are available in opencv and matlab.
Hope this helps.
Good luck.

Sets will have quite similar shapes (it will be set of points of human skeleton from kinect > sensor) and I want to check if person is sitting in the same place as it was learned in the > first place
Then you will probably be able to derive a correspondence between two points (i.e. you will know that a given point is SHOULDER_RIGHT or ELBOW_LEFT or...). If that is the case you can simply calculate the SUM(SQRT((Xi1-Xi2)^2+(Yi1-Yi2)^2) for each i-th pair of points (X1,Y1) and (X2,Y2) (same goes if you can obtain the third dimension Z).
The value thus obtained will have a minimum of zero when the two sets of points are perfectly coinciding.

Related

How to know if two sets of points have same pattern

I have 2 sets of points in 3D have the same count, I want to know if the have the same pattern, I thought I may project them on XZ,XY and YZ planes then compare the projections in each plane but I am not sure how to do this, I thought the convex hull may help but it won't be accurate.
Is there an easy algorithm to do that? the complexity is not a big issue so far as the points count will be tiny, I implement in Java.
Can I solve this in 3D direct with the same algorithm ?
The attached image shows an example of what I mean.
Edit:
No guarantee for order.
No scale, there are rotation and translation only.
I would gather some information about each point: information that only depends on "shape", not on the actual translation/rotation. For instance, it could be the sum of all the distances between the point and any other point of the shape. Or it could be the largest angle between any two points, as seen from the point under consideration. Choose whatever metric brings the most diversity.
Then sort the points by that metric.
Do the above for both groups of points.
As a first step you can compare both groups by their sorted list of metrics. Allow for a little error margin, since you will be dealing with floating point precision limitations. If they cannot be mapped to each other, abort the algorithm: they are different shapes.
Now translate the point set so that the first point in the ordered list is mapped to the origin (0, 0, 0), i.e. subtract the first point from all points in the group.
Now rotate the point set around the Y axis, so that the second point in the ordered list coincides with XY plane. The rotate the point set around the Z axis, so that that point coincides with the X-axis: it should map to (d, 0, 0), where d is the distance between the first and second point in the sorted list.
Finally, rotate the point set around the X axis, so that the third point in the ordered list coincides with the XY plane. If that point is colinear with the previous points, you need to continue doing this with the next point(s) until you have rotated a non-colinear point.
Do this with both groups of points. Then compare the so-transformed coordinates of both lists.
This is the main algorithm, but I have omitted the cases where the metric value is the same for two points, and thus the sorted list could have permutations without breaking the sort order:
In that case you need to perform the above transformations with the different permutations of those equally valued points at the start of the sorted list, for as long as there is no fit.
Also, while checking the fit, you should take into account that the matching point may not be in the exact same order as in the other group's sorted list, and you should verify the next points that have the same metric as well.
If you have a fixed object with different shapes and movements, pair-wise- or multi-matching can be a helpful solution for you. For example see this paper. This method can be extended for higher-dimensions as well.
If you have two different sets of points that come from different objects and you find the similarity between them, one solution can be computing discrete Frechet distance in both sets of points and then compare their value.
The other related concept is Shape Reconstruction. You can mix the result of a proper shape reconstruction algorithm with two previous methods to compute the similarity:

Construct lines from multiple 2D points and measure the distance between those lines

Multiple points on a 2D plane are given. They represent a window frame of mostly rectangular form with some possible variations. The points which are part of each side are not guaranteed to form a perfect line. Each side of the window should be measured.
A rotating electronic device attached to a window measures the distance in all directions providing a 360 degree measurements. By using the rotation angle and the distance, a set of points are plotted on a 2D coordinate system. So far so good.
Now comes the harder part. The measured window frame could have some variations. The points should be converted to straight lines and the length of each line should be measured.
I imagine that the following steps are required:
Group the different points into straights lines. This means approximating each line “between” the points that form it.
Drawing those lines, getting rid of the separate points used to construct the lines.
Find the points where each two lines intersect.
Measure the distance between those points. However not all distances between all points are interesting. For example diagonals within a frame are irrelevant.
Any Java libraries dealing with geometry that could solve the problem are acceptable. I will write the solution in Kotlin/Java, but any algorithmic insights or code examples and ideas in any other languages or pseudo code are welcome.
Thank you in advance!
New Image
I would solve this in 2 stages:
Data cleaning: round the location (X, Y) of each point to its nearest multiple of N (vary N for varying degrees of precision)
Apply the gift-wrapping algorithm (also known as Jarvis March)
You now have only those points that are not co-linear, and the lines between them, and the order in which they need to be traversed to form the perimeter.
Iterate over the points in order, take point Px and P(x+1), and calculate the distance between them.

Algorithm for distributing points evenly but randomly in a rectangle

I want to place some points in a rectangle randomly.
Generating random x, y coordinates it's not a good idea, because many times happens that the points are mainly distributed on the same area instead cover the whole rectangle.
I don't need an algorithm incredibly fast or the best cover position, just something that could run in a simple game that generate random (x, y) that cover almost the whole rectangle.
In my particular case I'm trying to generate a simple sky, so the idea is to place almost 40/50 stars in the sky rectangle.
Could someone point me some common algorithm to do that?
There is a number of algorithms to pseudo-randomly fill a 2d plane. One of them is Poisson Disk Sampling which places the samples randomly, but then checks that any two are not too close. The result would look something like this:
You can check some articles describing this algorithm. And even some implementations are available.
The problem though is that the resulting distribution looks nothing like the actual stars in the sky. But it gives a good tool to start with - by controlling the Poisson radius we can create very naturally looking looking patterns. For example in this article they use Perlin Noise to control the radius of the Poisson Disk Sampling:
You would also want to adjust the brightness of the stars, but you can experiment with uniform random values or Perlin noise.
Once I have used a completely different approach for a game. I took real positions of the stars in cartesian system from HYG database by David Nash and transformed them to my viewpoint. With this approach you can even create the exact view that can be seen from where you are on Earth.
I once showed this database to the girl I wanted to date, saying "I want to show you the stars… in cartesian coordinate system".
Upd. It’s been over seven years now and we are still together.
Just some ideas which might make your cover to appear "more uniform". These approaches don't necessarily provide an efficient way to generate a truly uniform cover, but they might be good enough and worth looking at in your case.
First, you can divide the original rectangle in 4 (or 10, or 100 - as long as performance allows you) subrectangles and cover those subrectangles separately with random points. By doing so you will make sure that no subrectangle will be left uncovered. You can generate the same number of points for each subrectangle, but you can also vary the number of points from one subrectangle to another. For example, for each subrectangle you can first generate a random number num_points_in_subrectangle (which can come from a uniform random distribution on some interval [lower, upper]) and then randomly fill the subrectangle with this many points. So all subrectangles will contain random number of points and will probably look less "programmatically generated".
Another thing you can try is to generate random points inside the original rectangle and for each generated point check if there already exists a point within some radius R. If there is such point, you reject the candidate and generate the new one. Again, here you can vary the radius from one point to another by making R a random variable.
Finally, you can combine several approaches. Generate some random number n of points you want in total. First, divide the original rectangle in subrectangles and cover those in such a way that there are n / 3 points in total. Then generate next n / 3 points by selecting the random point inside the original rectangle without any restrictions. After this, generate the last n / 3 points randomly with checks for neighbors within the radius.
Using a uniform drawing of X, Y, if you draw 40 points, the probability of having all points in the same half is about one over a trillion (~0.0000000000009).

Matlab: how to generate non-uniform and non-overlap circle/rectangle in a circle with specific radius

I want to generate a series of points as building in simulation.
Points density is 1/1000m^3
The points have its shape just like the real buildings(circle or rectangle or something else)
In order to reach the reality, these shapes should not be overlapped.
The question is how to generate the center point of these 'buildings'?
I tried this
clusterNumber = round((pi*areaRadius^2)/1000);
radius = unifrnd (0,areaRadius,clusterNumber,1);
angle = unifrnd (-pi,pi,clusterNumber,1);
for i=1:clusterNumber
Coordinate(i,1) = cos(angle(i))*radius(i); % x
Coordinate(i,2) = sin(angle(i))*radius(i); % y
and the result showed as what I expected... it did'nt work
When I used scatter it showed
So, my question is how to generate non-uniform and non-overlap circles or rectangles in a specific circle.
If you want your buildings not to intersect, you must check for intersections with already created buildings before creating one at your random position.
Of course, if you create many buildings, collision detection will be costly. You can speed it up with an efficient nearest neighbour search, for example with kd-trees or by creating a fine grid in the building space so that you have only a few neighbour cells to check.
Imposing the condition that buildings must not intersect will also alter your distribution. You will no longer have the marked clustering in the circle's centre. You still generate morre random positionsthere, but as your area gets more populated, most of them will be rejected.
Here's an example distribution:
Enforcing the criterion may also affect your algorithm: It might be a good idea to limit the number of randomly gerenated positions, so that you don't run into an infinite loop when no more buildings can be placed or when the probability to find a suitable space is very low.

Averaging vector images to get in-between images

I am looking for an algorithm that takes vector image data (e.g. sets of edges) and interpolate another set of edges which is the "average" of the two (or more) sets.
To put it in another way, it is just like Adobe Flash where you "tween" two vector images and the software automatically computes the in-between images. Therefore you only specify the starting image and end image, then Flash takes care of all the in-between images.
Is there any established algorithm to do this? Especially in cases like different number of edges?
What exactly do you mean by edges? Are we talking about smooth vector graphics that use curves?
Well a basic strategy would be to simply do a linear interpolation on the points and directions of your control polygon.
Basically you could simply take two corresponding points (one of each curve/vector form) and interpolate them with:
x(t) = (1-t)*p1 + t*p2 with t in [0,1]
(t=0.5 would then of course give you the average between the two)
Since vector graphics usually use curves you'd need to do the same with the direction vector of each control point to get the direction vector of the averaged curve.
One big problem though is to match the right points of each control polygon, especially if both curves have a different degree. You could try doing a degree elevation on one to match the degree of the other and then one by one assign them to each other and interpolate.
Maybe that helps...

Resources