# Clipping a mesh to a ball

**URL:** https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833
**Category:** General Usage
**Tags:** question, plotting
**Created:** [July 6, 2022, 11:23am UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833 "2022-07-06T11:23:49Z")
**Posts on this page:** 19
**Page:** 1

<div class="post-metadata">

### Author: ![\_stla](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/_stla/32/35613_2.png) [@\_stla](https://discourse.julialang.org/u/_stla)
#### Post date: [July 6, 2022, 11:23am UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/1 "2022-07-06T11:23:50Z")

</div>

Hello,

It looks like **Makie** has no functionality to clip a 3d mesh to a ball (i.e. to discard the part of the mesh which is outside the ball). Is there another package to achieve that? [Motivation](https://laustep.github.io/stlahblog/posts/MeshClipping.html). This is possible with the R package **rgl** , and with the C++ library **CGAL**. I took a look at **CGAL.jl** but didn’t found anything related to 3d meshes.

---

<div class="post-metadata">

### Author: ![sjkelly](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sjkelly/32/9280_2.png) [@sjkelly](https://discourse.julialang.org/u/sjkelly)
#### Post date: [July 6, 2022, 1:36pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/2 "2022-07-06T13:36:43Z")

</div>

[ConstructiveGeometry.jl](https://github.com/plut/ConstructiveGeometry.jl) should provide the [CSG](https://en.wikipedia.org/wiki/Constructive_solid_geometry) operations you would need.

---

<div class="post-metadata">

### Author: ![juliohm](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/juliohm/32/215266_2.png) [@juliohm](https://discourse.julialang.org/u/juliohm)
#### Post date: [July 6, 2022, 2:04pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/3 "2022-07-06T14:04:50Z")

</div>

Here is a solution with Meshes.jl:

```julia
using Meshes, MeshViz

import PlyIO # for reading PLY files
import GLMakie as Mke # for visualization

# helper function to load mesh from PLY file
function readply(fname)
  ply = PlyIO.load_ply(fname)
  x = ply["vertex"]["x"]
  y = ply["vertex"]["y"]
  z = ply["vertex"]["z"]
  points = Point3.(x, y, z)
  connec = [connect(Tuple(c.+1)) for c in ply["face"]["vertex_indices"]]
  SimpleMesh(points, connec)
end

# download mesh from the web
file = download("https://raw.githubusercontent.com/juliohm/JuliaCon2021/master/data/beethoven.ply")

# read mesh from disk
mesh = readply(file)

viz(mesh)

```

 ![image](https://global.discourse-cdn.com/julialang/original/3X/4/d/4d18e803b95f4eaac0536976a0eee58264e0f555.jpeg)

```julia
# create a neighborhood with radius (and optional metric)
ball = MetricBall(2.0)

# create a search method, in this case ball search
searcher = BallSearch(mesh, ball)

# find the indices of the elements inside a ball centered at the origin
inds = search(Point(0.,0.,0.), searcher)

# lazy view of elements in the mesh
vmesh = view(mesh, inds)

viz(vmesh)

```

 ![image](https://global.discourse-cdn.com/julialang/original/3X/7/0/70ddcd295420ac2d5ffda0f38a5155d681c1a807.png)

---

<div class="post-metadata">

### Author: ![\_stla](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/_stla/32/35613_2.png) [@\_stla](https://discourse.julialang.org/u/_stla)
#### Post date: [July 6, 2022, 2:41pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/4 "2022-07-06T14:41:39Z")

</div>

Thank you. But the mesh you obtain has abrupt borders. With **rgl** or **CGAL** , the borders are refined. I will try on another example, perhaps this is specific to this example.

---

<div class="post-metadata">

### Author: ![\_stla](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/_stla/32/35613_2.png) [@\_stla](https://discourse.julialang.org/u/_stla)
#### Post date: [July 6, 2022, 2:44pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/5 "2022-07-06T14:44:16Z")

</div>

Thanks. Not sure. The clipping is not really a Boolean operation.

---

<div class="post-metadata">

### Author: ![\_stla](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/_stla/32/35613_2.png) [@\_stla](https://discourse.julialang.org/u/_stla)
#### Post date: [July 6, 2022, 2:58pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/6 "2022-07-06T14:58:35Z")

</div>

Ah maybe with the intersection… I’ve just tried with **CGAL** and the computation of the intersection fails with my example.

---

<div class="post-metadata">

### Author: ![sjkelly](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sjkelly/32/9280_2.png) [@sjkelly](https://discourse.julialang.org/u/sjkelly)
#### Post date: [July 6, 2022, 3:03pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/7 "2022-07-06T15:03:33Z")

</div>

It sounds like the intersection is what you would want. Are you certain your mesh is manifold and the vertices are indexed uniquely? E.g. Some formats like STL discard topology, which makes CSG operations difficult.

---

<div class="post-metadata">

### Author: ![\_stla](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/_stla/32/35613_2.png) [@\_stla](https://discourse.julialang.org/u/_stla)
#### Post date: [July 6, 2022, 3:26pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/8 "2022-07-06T15:26:12Z")

</div>

My mesh self-intersects. If I modify it a little, it does not self-intersect anymore but the computation fails, I don’t know why.

Clipping with the intersection is a hammer to kill a fly. Clipping is easier than intersection. A guy made it manually in R here: [r - How to clip an isosurface to a ball? - Stack Overflow](https://stackoverflow.com/a/56265558/1100107).

---

<div class="post-metadata">

### Author: ![juliohm](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/juliohm/32/215266_2.png) [@juliohm](https://discourse.julialang.org/u/juliohm)
#### Post date: [July 6, 2022, 3:36pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/9 "2022-07-06T15:36:14Z")

</div>

Can you please elaborate on why the proposed solution with Meshes.jl doesn’t meet the requirements?

---

<div class="post-metadata">

### Author: ![\_stla](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/_stla/32/35613_2.png) [@\_stla](https://discourse.julialang.org/u/_stla)
#### Post date: [July 6, 2022, 3:38pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/10 "2022-07-06T15:38:42Z")

</div>

Take a look at my link. The borders of the clipped mesh are smooth. On the clipped Beethoven mesh, they are highly non-smooth.

---

<div class="post-metadata">

### Author: ![juliohm](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/juliohm/32/215266_2.png) [@juliohm](https://discourse.julialang.org/u/juliohm)
#### Post date: [July 6, 2022, 3:53pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/11 "2022-07-06T15:53:19Z")

</div>

Smoothness is a property of the mesh, if you want to have smoother borders you have to have more elements or curved elements. You are confusing things.

---

<div class="post-metadata">

### Author: ![juliohm](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/juliohm/32/215266_2.png) [@juliohm](https://discourse.julialang.org/u/juliohm)
#### Post date: [July 6, 2022, 3:54pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/12 "2022-07-06T15:54:36Z")

</div>

Now if you want the result to be a different mesh with curved elements than that is another thing. You can clip as I did but just viewing the original mesh or actually produce a new mesh with curved elements. That is not currently implemented.

---

<div class="post-metadata">

### Author: ![\_stla](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/_stla/32/35613_2.png) [@\_stla](https://discourse.julialang.org/u/_stla)
#### Post date: [July 6, 2022, 3:57pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/13 "2022-07-06T15:57:05Z")

</div>

I’m not confusing 🙂 The smoothness on the Togliatti example is not intrinsically due to the mesh. When clipping, the borders are refined, there are new faces. See the second link where the guy explains the method.

---

<div class="post-metadata">

### Author: ![\_stla](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/_stla/32/35613_2.png) [@\_stla](https://discourse.julialang.org/u/_stla)
#### Post date: [July 6, 2022, 4:03pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/14 "2022-07-06T16:03:20Z")

</div>

Look. I’ve clipped Beethoven with **rgl** , the borders are regular:

![beethoven](https://global.discourse-cdn.com/julialang/original/3X/2/8/2832ebc7b5cec0889cd86c90f11b1087d6c4debc.png)

---

<div class="post-metadata">

### Author: ![juliohm](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/juliohm/32/215266_2.png) [@juliohm](https://discourse.julialang.org/u/juliohm)
#### Post date: [July 6, 2022, 4:05pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/15 "2022-07-06T16:05:47Z")

</div>

I see. Feel free to submit PRs with a clipping method. We don’t have this operation defined yet, it deserves a new verb in the API. Our `search` methods only return a view of the original mesh:

[https://juliageometry.github.io/Meshes.jl/stable/algorithms/neighborsearch.html](https://juliageometry.github.io/Meshes.jl/stable/algorithms/neighborsearch.html)

You can add a new `clip` verb and provide clipping methods.

---

<div class="post-metadata">

### Author: ![juliohm](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/juliohm/32/215266_2.png) [@juliohm](https://discourse.julialang.org/u/juliohm)
#### Post date: [July 6, 2022, 4:06pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/16 "2022-07-06T16:06:43Z")

</div>

Can you clip with a similar ball size? The ball you used in the R example is much larger.

---

<div class="post-metadata">

### Author: ![\_stla](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/_stla/32/35613_2.png) [@\_stla](https://discourse.julialang.org/u/_stla)
#### Post date: [July 6, 2022, 7:00pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/17 "2022-07-06T19:00:38Z")

</div>

This is similar with radius=2.

I’m really not familiar with meshes in Julia. It would be nice to use **CGAL** for the clipping. And I’m not familiar with the usage of C/C++ in Julia as well.

---

<div class="post-metadata">

### Author: ![stillyslalom](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/stillyslalom/32/45687_2.png) [@stillyslalom](https://discourse.julialang.org/u/stillyslalom)
#### Post date: [July 6, 2022, 7:08pm UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/18 "2022-07-06T19:08:12Z")

</div>

There’s also [GitHub - rgcv/CGAL.jl: CGAL meets Julia](https://github.com/rgcv/CGAL.jl), although the documentation is minimalist.

---

<div class="post-metadata">

### Author: ![juliohm](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/juliohm/32/215266_2.png) [@juliohm](https://discourse.julialang.org/u/juliohm)
#### Post date: [July 7, 2022, 11:42am UTC](https://discourse.julialang.org/t/clipping-a-mesh-to-a-ball/83833/19 "2022-07-07T11:42:00Z")

</div>

@_stla perhaps you should set radius=1 in the R version because clearly the clipping is different with radius=2.
