Uniform generation of three-dimensional points on a cylinder / cone

I want to randomly and evenly create points on the cylinder and cone (separately). A cylinder is defined by its center, its radius and height. The same specifications for the cone. I can get a bounding box for each shape, so I was thinking about creating points in a bounding box. However, I am not sure how to project them onto a cylinder / cone or if this is the best idea.

Any suggestions?

Thanks.

+6
geometry trigonometry 3d opengl particles
source share
7 answers

The case of a cylinder is trivial. If a cylinder with radius r> 0 and height h> 0 is the image (x, y, z) = (r cos Ο†, r sin Ο†, z) on Ο† ∈ [0, 2Ο€ [and z ∈ [-h / 2, h / 2], then simply select Ο† and z at random at these intervals. Of course, you can simply parameterize the cone using standard parameterization, but then the element of the region will not be constant on the plane of parameters, so the distribution of points will not be random. So you need to find another parameterization. I discussed in detail this topic in the field of my site AlgoSim .

+4
source share

It would be easier to create points directly on the cylinder or cone.

Some time has passed since I did this, but I parameterize the axis of the cylinder, and then for each point we parameterize the circle at this height. This will create points on the surface. The radius of the circle is equal to the radius of the cylinder.

For a cone, you need to reduce the radius of the circle when moving from the base to the top.

+2
source share

One way to think about this is that both the cylinder and the cone can be deployed on flat surfaces - just cut each straight line from top to bottom.

The cylinder expands to the rectangle (if you include the upper and lower parts, and then add several disks).

The cone unfolds to a triangle with a curved bottom that is an arc of a circle (if you include the base of the cone, then add a disk).

It is easy enough to insert these flat surfaces inside the rectangle R on the xy plane. Create evenly distributed points in R , and whenever they are inside flat surfaces, return them back to the original surfaces.

Keep track of some of the other answers here that try to coordinate the cone in terms of angle and height. Although the points will be evenly distributed relative to the angle and height, they will not be evenly distributed wrt area. They will be more densely distributed at the tip.

+2
source share

Let the point be determined by the coordinates r, a, h, where r is the "radius" (distance from the vertical axis passing from the center), a is the angle, as in polar coordinates, h is its height.

For cylinder (radius R and height H): select independently

  • uniform in [0, 2pi),
  • h uniform in [0, H] and
  • r with a "triangular density": f (r) = 2 r / R if 0 = r = R, 0 otherwise (the density at r should be proportional to the circumference of a radius r).

It is not difficult to select such a triangular distribution, since its cumulative distribution (quadratic monomial) is easily reversible (see this article ). In addition, this answer is based on intuition, but it is not difficult to prove that the distribution that you get on the cylinder is uniform.

For cone (radius R and height H): select

  • uniform in [0, 2pi),
  • h with a density made with a segment of a parabola: f (h) = 3 (H - h) ^ 2 / H ^ 3 if 0 = h <= H, 0 otherwise (the density with h must be proportional to the circular cross-sectional area on height h)
  • let r (h) = (H - h) R / H (the radius of the cross section at a height h); then choose r with a triangular distribution f (r) = 2 r / r (h) if 0 = lt; = r (h), 0 otherwise.

Again, the sample h should be simple, since the cumulative distribution is easily reversible.

EDIT. If you want to create points on the surface of the figures, then the solution is simpler:

Cylinder : select

  • uniform in [0, 2pi),
  • h uniform in [0, H],
  • r = R.

Cone : select

  • uniform in [0, 2pi),
  • h with a triangular density: f (h) = 2 (H - h) / H ^ 2, if not (density h at 0 should be proportional to the circumference at a height h).
  • r = r (h) = (H - h) R / H = radius at height h.
0
source share

Other answers already covered the cylinder body quite well. For a cone, everything is a little more complicated. To maintain a constant point density, you need to compensate for the change in radius.

To do this, you can start by choosing the distance between the points. When you move along the axis of the cone, you calculate the circle at that height, then divide the circle by the linear distance between the points to get the number of points. Then you divide 2pi radians (or 360 degrees or something else) by the number of points to get the angular distance for that radius.

Depending on the required accuracy, you can track the remainder of one circle when you calculate the next circle. For example, if you have two circles in a row that need xxx.4 points, you will go around them if you look in isolation - but looking at them together, you have xxx.8 points, so you have one round down and another to keep the overall density as close to the correct value as possible.

Please note that although this is not so obvious, the latter can also apply to the cylinder - usually you will have rounding when distributing each circle of points.

0
source share

To put these answers in pseudocode:

For cylinder, given cylinder, Radius and cylinder Height:

 angle = random number between 0 & 360 x = cos(pi/180*angle)*cylinderRadius y = sin(pi/180*angle)*cylinderRadius z = random number between 0 and cylinderHeight. 

For the cone given by coneRadius, coneHeight:

 angle = random number between 0 & 360 z = random number between 0 and coneHeight thisRadius = coneRadius * (1-(z/coneHeight)); //This gives a decreasing radius as height increases. x = cos(pi/180*angle)*thisRadius y = sin(pi/180*angle)*thisRadius 

Each point (x, y, z) will lie on a cylinder / cone. Generate enough of these points, and you can spawn particles on the surface of the cylinder / cone, but this may not make an exactly uniform distribution ...

-one
source share

For uniform points on a circle or cone of radius R and height / height H:

 generate: angle= uniform_random(0,2*pi) value= uniform_random(0,1) in either case, let: r= R * sqrt(value) then (using separate random numbers for each): circle_point= point3d( r*cos(angle), r*sin(angle), H ) or: cone_point= point3d( r*cos(angle), r*sin(angle), r*H ) 

Please note: if you need a base on your cone, you will need to do this separately from the curved shape. To make sure that the density of points is the same for different parts, a simple way is to calculate the area of ​​the parts and create a proportional number of points for each part.

sqrt (value) is what ensures that the density of your random points is uniform. As mentioned in other issues, this requires a triangular distribution; taking sqrt () turns the uniform distribution on [0,1) into a triangular one.

For the cylinder you do not need sqrt (); curved part:

  cylinder_point= point3d( R*cos(angle), R*sin(angle), H*value ) 
-one
source share

All Articles