Finding centre line of a pipe using python - mesh

I am currently writing a code in Python for flows through pipes. In this regard, I have to find a centre line passing thorough a 3D pipe geometry defined by a nastran mesh (cells with three or four edges whose coordinates i can access). I am using the pyNastran module in Python to get all the relevant data and functions.
My question is what would be the most efficient way of finding the centre line of the pipe. The pipe is a 3d pipe with bends in all direction. ( I have all the coordinates of every single point on the mesh in an array)

That is not so easy topic :-/ Problem is that center line is not local property.
For sure, each point on center line corresponds to one slice through pipe or simpler to one perimeter on pipe surface. For any kind of defining that relation on local characteristics, it is easy to find example with bendings or changing pipe diameter that produces 'strange' result.
One way to solve it is to look for topics that have similar properties that are needed here. Like we want slices to be 'parallel' and to uniformly pass through pipe. On one project we used heat diffusion/transfer to tackle a problem. Idea is to put boundary conditions, on one pipe side set boundary condition 1 and on the other side boundary condition 0. Heat will transfer from one side to the other and isoterm will have good properties.
After that, choose center line discterization (on [0-1]), for each point find isoterm on that temperature and find center of mass of that isoterm. Connecting these centers will produce center line.
It is possible to make diffusion on 3D (volume) and 2D (surface) case. It is probably faster to do it on surface.

Related

How to have continuous features for a shapefile and get rid off the wrapdateline?

How to have continuous features for a shapefile ?
I mean NOT cut by the dateline to respect [-180:180] longitude excursion that I do not
want to respect.
Here is an example where I display the Russia shapefile in a leaflet map.
In fact I would like to have continuous continent.
Shapefile comes from
https://gadm.org/about.html
Any command from gdal or ogr2ogr to merge separated features ?
Thanks
If you load the GADM level-0 layer into QGIS and toggle Show Feature Count, you'll see that, even though the shape seems split, the actual layer only has a single feature:
Your shape gets cut off because the polygon crosses the boundary in the projection you are using and gets wrapped around. This doesn't mean the features get actually split.
If you want to display it as a continuous feature, you need to specify an appropriate projection. For instance, using the example here gives me this:
This is just one way, there might be different projections that fit your purpose better. Also, getting this done in leaflet is a different question.

CGAL cut cube with arbitrary surface

I'm new to CGAL and I'm trying to cut a cube with an arbitrary surface mesh in 3d (no self intersections, not closed/no volume). The goal is to get a volume which consists of one "side" of the cut cube, closed by the part of the surface inside the cube.
The surface itself consists of unordered triangles which should have the same winding order (consistent normal directions) but have no neighborhood information and could contain same points multiple times for different triangles.
I tried to use the clip function, like:
CGAL::Polygon_mesh_processing::clip(cube,surface,true);
Which of course does not work because the surface is not closed (as far as I understood). But It shows the idea on how the operation should work.
Boolean operations (https://doc.cgal.org/latest/Polygon_mesh_processing/index.html#title14)) cannot be used for this as well since they are calculated on volumes and the surface has no volume.
I also thought about extending the outside of the surface so that it is closed. This, however, does not seem like a good approach.
Sadly, my research on similar problems was not successful.
I'm pretty sure that there is a nice way to do this in CGAL. Maybe someone with more experience in CGAL knows how to do this.
What would be the best approach for getting this volume?
Regards
EDIT:
By removing redundant points in my surface mesh I was able to get clip to work. Nevertheless, I do not always get the right side of the volume, even though the winding order should yield normals which point to the outside.
Is it necessary to calculate the normals and pass them as an extra parameter (see here) of the surface before the cut in order to always get the same "inner" side of the volume?
Also, the clip function seems to be quite slow. I have to do this cut for a very high number of cubes and different surfaces.
I use CGAL as header only lib and without GMP and MPFR, since it crashed my other application. How big is the speedup using these libraries and are there any other tricks which can be used to speedup computation, e.g. using parallelization?
I saw that CGAL uses Intel's TBB which. But in the header files which are included by the clipping algorithm CGAL_LINKED_WITH_TBB is not tested.
Thanks
It was a problem with the clipping mesh. Clipping could not be done properly. I increased it size and now it always intersects the volume.

Mesh to mesh. Mesh fitting (averaging). Mesh comparison.

I have 3 sets of point cloud that represent one surface. I want to use these point clouds to construct triangular mesh, then use the mesh to represent the surface. Each set of point cloud is collected in different ways so their representation to this surface are different. For example, some sets can represent the surface with smaller "error". My questions are:
(1) What's the best way to evaluate such mesh-to-surface "error"?
(2) Is there a mature/reliable way to convert point cloud to triangular mesh? I found some software doing this but most requests extensive manual adjustment.
(3) After the conversion I get three meshes. I want to use a fourth mesh, namely Mesh4, to "fit" the three meshes, and get an "average" mesh of the three. Then I can use this Mesh4 as a representation of the underlying surface. How can I do/call this "mesh to mesh" fitting? Is it a mature technique?
Thank you very much for your time!
Please find below my answers for point 1 and 2:
as a metric for mesh-to-surface error you can use Hausdorff distance. For example, you could use Libigl to compare two meshes.
To obtain a mesh from a point cloud, have a look at PCL

Tetrahedralization from surface mesh of thin-walled object

I need to generate a tetrahedral (volume) mesh of thin-walled object object. Think of objects like a bottle or a plastic bowl, etc, which are mostly hollow. The volumetric mesh is needed for an FEM simulation. A surface mesh of the outside surface of the object is available from measurement, using e.g. octomap or KinectFusion. Therefore the vertex spacing is relatively regular. The inner surface of the object can be calculated from the outside surface by moving all points inside, since the wall thickness is known.
So far, I have considered the following approaches:
Create a 3D Delaunay triangulation (which would destroy the existing surface meshes) and then remove all tetrahedra which are not between the two original surfaces. For this check, it might be required to create an implicit surface representation of the 2 surfaces.
Create a 3D Delaunay triangulation and remove tetrahedra which are "inside" (in the hollow space) or "outside" (of the outer surface) with Alphashapes.
Close the outside and inside meshes and load them into tetgen as the outside hull and as a hole respectively.
These approaches seem to be a bit inelegant to me, and they still have some pitfalls. I would probably need several libraries/tools for them. For 1 and 2, probably tetgen or another FEM meshing tool would still be required to create well-conditioned tetrahedra. Does anyone have a more straight-forward solution? I guess this should also be a common problem in 3D printing.
Concerning tools/libraries, I have looked into PCL, meshlab and tetgen so far. They all seem to do only part of the job. Ideally, I would like to use only open source libraries and avoid tools which require manual intervention.
One way is to:
create triangular mesh of surface points,
extrude (move) that surface to inner for a given thickness. That produces volume (triangular prism) mesh of a wall,
each prism can be split in three tetrahedrons.
The problem I see is aspect ratio.
A single layer of tetrahedra will not reproduce shell or bending behavior very well. A single element through the thickness will already require a large mesh. Putting more than one will likely break the bank in order to keep aspect ratios and angles acceptable.
I'd prefer brick or thick shell elements to tetrahedra in this case. I think the modeling will be easier and the behavior will be more faithful to the physics.

Tweaking Heightmap Generation For Hexagon Grids

Currently I'm working on a little project just for a bit of fun. It is a C++, WinAPI application using OpenGL.
I hope it will turn into a RTS Game played on a hexagon grid and when I get the basic game engine done, I have plans to expand it further.
At the moment my application consists of a VBO that holds vertex and heightmap information. The heightmap is generated using a midpoint displacement algorithm (diamond-square).
In order to implement a hexagon grid I went with the idea explained here. It shifts down odd rows of a normal grid to allow relatively easy rendering of hexagons without too many further complications (I hope).
After a few days it is beginning to come together and I've added mouse picking, which is implemented by rendering each hex in the grid in a unique colour, and then sampling a given mouse position within this FBO to identify the ID of the selected cell (visible in the top right of the screenshot below).
In the next stage of my project I would like to look at generating more 'playable' terrains. To me this means that the shape of each hexagon should be more regular than those seen in the image above.
So finally coming to my point, is there:
A way of smoothing or adjusting the vertices in my current method
that would bring all point of a hexagon onto one plane (coplanar).
EDIT:
For anyone looking for information on how to make points coplanar here is a great explination.
A better approach to procedural terrain generation that would allow
for better control of this sort of thing.
A way to represent my vertex information in a different way that allows for this.
To be clear, I am not trying to achieve a flat hex grid with raised edges or platforms (as seen below).
)
I would like all the geometry to join and lead into the next bit.
I'm hope to achieve something similar to what I have now (relatively nice undulating hills & terrain) but with more controllable plateaus. This gives me the flexibility of cording off areas (unplayable tiles) later on, where I can add higher detail meshes if needed.
Any feedback is welcome, I'm using this as a learning exercise so please - all comments welcome!
It depends on what you actually want and what you mean by "more controlled".
Do you want to be able to say "there will be a mountain on coordinates [11, -127] with radius 20"? Complexity of this this depends on how far you want to go. If you want just mountains, then radial gradients are enough (just add the gradient values to the noise values). But if you want some more complex shapes, you are in for a treat.
I explore this idea to great depth in my project (please consider that the published version is just a prototype, which is currently undergoing major redesign, it is completely usable a map generator though).
Another way is to make the generation much more procedural - you just specify a sequence of mathematical functions, which you apply on the terrain. Even a simple value transformation can get you very far.
All of these methods should work just fine for hex grid. If artefacts occur because of the odd-row shift, then you could interpolate the odd rows instead (just calculate the height value for the vertex from the two vertices between which it is located with simple linear interpolation formula).
Consider a function, which maps the purple line into the blue curve - it emphasizes lower located heights as well as very high located heights, but makes the transition between them steeper (this example is just a cosine function, making the curve less smooth would make the transformation more prominent).
You could also only use bottom half of the curve, making peaks sharper and lower located areas flatter (thus more playable).
"sharpness" of the curve can be easily modulated with power (making the effect much more dramatic) or square root (decreasing the effect).
Implementation of this is actually extremely simple (especially if you use the cosine function) - just apply the function on each pixel in the map. If the function isn't so mathematically trivial, lookup tables work just fine (with cubic interpolation between the table values, linear interpolation creates artefacts).
Several more simple methods of "gamification" of random noise terrain can be found in this paper: "Realtime Synthesis of Eroded Fractal Terrain for Use in Computer Games".
Good luck with your project