Category Archives: Art

3D Design: Spherenes

Updates:

  • 2024/10/23: finally published
  • 2024/10/11: ready for publishing
  • 2024/01/26: starting write-up

Introduction

At Formnext 2023 I spent some unexpected time to discover a new class of procedural structure called “Spherene” (“sphere” + “graphene”), it’s a name as introduced by a company with the same name.

It’s main feature is isotropic (“all directions”) distribution of forces. Their service provides the creation of this structure based on:

  • density (ratio of material vs empty space), hence their term of Adaptive Density Minimal Surface (ADMS)
  • form
  • wall thickness

where all of them are freely definable in 3D space contained within an overall boundary. Their service “renders” a mesh which complies with such, like defining at some point a lower or higher density, and transits in 3D space from one to another.

Spherene Metamaterial in Simulation-Based DFAM: CDFAM NYC 2024 (Video Presentation)

Patent

My immediate impulse was to code the Spherene aside of the existing TPMS’s, but I realized their business core is the service of creating meshes based on their procedure as described in a patent:

  • Method of Additively Manufacturing a Minimal Surface Structure (Original, 2023), PDF available
  • at its core it describes 6 steps (abbreviations added for clarity)
    1. creating envelope
    2. creating density field
    3. adaptive Voronoi tesselation (AVT),
    4. 1st skeleton graph (SG) associated to AVT (SG-AVT1)
      • generated from the edges of the Voronoi cells
    5. 2nd skeleton graph associated to SG-AVT1 (SG-AVT2)
      • generated using Delaunay tetrahedralization
    6. minimal surface from SG-AVT1 and SG-AVT2, using equidistant from both skeleton graphs, with minimal wall thickness requirements
  • Abstract: A method of additively manufacturing a minimal surface structure of a three-dimensional article includes a computer executing the steps of recording, in the computer,
    • an envelope of the three-dimensional article; generating a density field across a volume enclosed by the envelope with densities of the density field corresponding to local requirement values of at least one physical parameter at respective positions of the three-dimensional article;
    • generating an adaptive Voronoi tessellation of the volume using the density field;
    • generating a first skeleton graph associated with the adaptive Voronoi tessellation;
    • generating a second skeleton graph associated with the first skeleton graph; and
    • generating a digital minimal surface model from the first and second skeleton graphs.
  • The method may further include a 3D printer additively manufacturing the minimal surface structure according to the digital minimal surface model.

I think if Spherene is truly as significant for Additive Manufacturing, and an essential invention, it has to move beyond the grip of a single company and its patents – time will tell.

Samples

Daniel Bachmann from Spherene Inc. kindly shared with me a few samples, 20x20x20mm cubes, and 20mm diameter spheres with Spherene infills, illustrating their properties:

A few support structures were required for the spherical samples, the cubic samples did not require such:

Lychee Slicer: spherical spherenes required support structure due overhangs

Additionally I printed a few cubic samples with FDM on my CoreXY Ashtar C without supports at 40x40x40mm scale.

Subtractive Manufacturing & Molding Usage

The structure cannot very well machined with subtractive manufacturing processes – or only if the piece is sub-divided so all indentations can be milled, and sequentially fused or welded again.

Another approach comes to my mind is to form dedicated bricks, e.g. for large scale application like a building, and have a limited kinds of bricks depending on their position and use case, and have molds to form those limited kinds in larger quantities.

In order to produce a mold one would inverse the original model, the negative volume, that would be produced using additive manufacturing and then produce lost-form casting molds, or highly simplify the form so one can remove the positive without destroying the mold.

References

3D Design: Slices on Canvas (Parametric Canvas)

Updates:

  • 2024/01/26: published
  • 2024/01/20: adding more examples and mounting tool/ruler
  • 2024/01/15: starting write-up

Introduction

Since a while I was wondering how to create large(r) scale 3D prints like 1m / 1000mm or more, and I thought to use wood planks as slices and make “parametric wall” like sculptures. In order to get an idea of the procedure, I started with “parametric canvas” or Slices on Canvas.

Models

I used OpenSCAD to put together a few examples with 200×150 in size, and settled for 40 slices, which are then scaled up for 400x300mm canvas, the actual size is 340x240mm giving on each side 30mm margin to the edge of the canvas.

3D Printing Slices

In order to test the concept, I used 3D printed slices printed with cold-white PLA+ in order to get a strong contrasts to the black canvas:

Each slice is 240mm wide, and 2.5mm thick and various height depending on the model.

After printing 40 slices finished, I mounted them on the canvas:

As shown on the photo, I used a mounting tool / rulers, also 3D printed, which helped me to keep the slices well aligned and spaced to each other – then glued each slice on the canvas.

40 slices with 240mm width and 2.5mm thickness takes about 20hrs to print (4 slices ~ 2hrs print time) and ~520g of filament like for the Sinus themed sculptures.

Raw slice bundles: Smooth Sinus Meadow, Quarter Drop, Drop each bundle apprx. 520g PLA+

With 2.5mm thickness x 40 and 340mm canvas width, it’s about ~25% or 1/4 of actual volume of the model, and the rest is empty space in between.

Sinus Mountain Range

Cubes

Spheres

Smooth Sinus Meadow

Various Examples

Conclusion

It’s relatively easy to create a Slices on Canvas (parametric canvas) but it takes its time to print and assemble – due the thin slices the sculpture changes its appearance drastically depending on viewing angle, and so is an eye catcher.

It certainly is a viable approach for larger scale sculptures, the saving in material is compensated with additional manual work like aligning and fastening the slices.

References

  • LabSlicer: used to slice the model into SVG slices (PrusaSlicer also supports this functionality)
  • Prynt3r: for printing the individual SVG slices directly

3D Design: 3D Lissajous

Updates:

  • 2024/01/22: published without much reflection & conclusion as research is ongoing
  • 2023/12/02: adding more examples and refining details
  • 2023/10/22: start writeup

Introduction

While studying continuous fiber 3D printing and its main nature is to find ways to lay fiber without interruption. In order to refresh my memory I revisited the Lissajous forms, which until recently only knew in their 2D form, the swirling strings or lines – and now extending it into 3D as well.

The main idea is to realize how a line, string or fiber can be used to fill non-planar and circumvent a 3D structure and how angular shifting in Lissajous context affects such form.

3D Lissajous

  • angle: 0 .. 2pi or 0 .. 360°
  • p, n, m: 0 .. 1000, the amount of loops
  • phi0, phi1, phi2: the angular offsets 0 … 2pi or 0 .. 360°
  • X = sin(angle*p+phi0)*r
  • Y = sin(angle*n+phi1)*r
  • Z = sin(angle*m+phi2)*r

I did a lot of experimenting – I could post hundreds of forms – but let me focus on one a bit closer, which got my attention:

It is a very interesting transition, 8/13/21 with phi0=0° gives almost a cube-like structure, and shifting the X loop to 90° we get a tetrahedron:

Spherical Lissajous

While playing with 3D Lissajous, I thought to adapt the cyclic nature, but apply it to a circle laying in the XY plane and then rotate in X axis, and Y axis as well, and optionally cyclic translation as well:

  • d: diameter
  • angle: 0 .. 2pi or 0 .. 360°
  • p: amount of loops as in X=sin(angle*p)*d/2, Y=cos(angle*p)*d/2
  • q: amount of X rotations: rotateX(angle*q)
  • r: amount of Y rotations: rotateY(angle*r)
Spherical Lissajous 12.23 with spreading struts

The model was printed with MSLA white resin at XYZ 50um resolution with 120mm diameter, with a few support structures near the bottom:

Spherical Lissajous with Translations

Using the Spherical Lissajous and extend it slightly:

  • [A,B,C]loop/offset/radius: translate([ sin(angle*AL+AO)*AR], sin(angle*BL+BO)*BR], sin(angle*CL+CO)*CR ])

which spreads the ribbons away from the spherical surface origins.

Spherical Lissajous 5.11 AL=3, AR=5

Spherical Lissajous 5.11 AL=3, AR=5

It’s symmetric X- and Z-wise, in Y-axis it isn’t.

The model was printed with MSLA white resin at XY 35um / Z 50um, at 60mm in Z height, ~94mm width; with a some support structures:

Spherical Lissajous 11.15 AL=2, AR=5

A more elaborate form is 11.15 AL=2, AR=5:

Spherical Lissajous 11.15 AL=2, AR=5 with spreading struts

So, there is no X-, Y- or Z-wise symmetry.

The model was printed with MSLA white resin at XY 35um / Z 50um, at 60mm in Z height, ~94mm width; with a some support structures:

and printing it larger with ~200mm width with manually positioned support:

That’s it (for now).

References

3D Printing: MSLA printing Triply Periodic Minimal Surfaces (TPMS) – Gallery

Updates:

  • 2023/07/25: adding 20mm/40mm TPMS photos
  • 2023/03/12: starting write-up, and published

20mm cubes of several Triply Periodic Minimal Surfaces (TPMS) as explored at Generative Parametric Infill Geometries printed with MSLA (Anycubic Photon Mono 4K) at 35 μm XY, 50 μm Z:

Most of the cubes were printed without support, the cylindrical and spherical projections required supports.

Closeups

20mm and 40mm cubes of TPMS mounted on canvases:

References

3D Modeling: Random Snapshots 2020

3D Modeling: Elegant Pieces in OpenSCAD with rcube(), rcylinder() and chainhull()

Updates:

  • 2020/12/31: rcube() extended, RCUBE_FLAT{BOTTOM, TOP, FRONT, BACK, LEFT, RIGHT} support added, rcylinder() with RCYLINDER_FLAT{TOP, BOTTOM}
  • 2020/12/30: rcube() source code extended, support RCUBE_FLATX, RCUBE_FLATY, RCUBE_FLATZ
  • 2020/12/28: inital post

While working on Ashtar D (Classic XY) I looked at some pieces I rushed to design with cube() and hull() and they didn’t appeal to me – yes, it kind of hurt my eyes.

A while back I coded a simple rcube([x,y,z],r) which takes r as a radius for the edges, internally it’s an OpenSCAD module which uses 8 spheres and hulls them together, providing round edges; but I hesitated to actually use it in my designs – until now. Further I thought, let’s do the same with cylinder() using rcylinder(d=10,h=5,r=1) providing round edges by using two torii and hull them together.

These two new functions, rcube([x,y,z],r) and rcylinder(h,d,r) allow to create more organic and elegant pieces, see for yourself:

From Bulky To Elegance

The position of the Y pulley mount is given, a bit of an X- & Y-offset to ensure printable area is not sacrificed for the Y carriage:

Using Chained Hulls

And another example . . . replacing hull() with chainhull():

The final version is composed by only 3 pieces chain hulled together:

difference() {
   chainhull() {
      rcylinder(...);
      translate([0,0,-20]) rcube(...);
      translate([...,-60]) rcube([5,20,50],2); // 2020 mount plate
   }
   rcube(...);     // pulley cutout
}

rcube() & rcylinder()

rcube();
translate([5,0,0]) rcube(0.75);
translate([10,0,0]) rcube([2,1,1],0.2);

translate([0,2,0]) rcube([2,1,1],0.2,false);
translate([5,2,0]) rcube([2,1,1],0.2,true);

translate([0,4,0]) rcube([2,1,1],0.2,RCUBE_FLATX);
translate([5,4,0]) rcube([2,1,1],0.2,RCUBE_FLATY);
translate([10,4,0]) rcube([2,1,1],0.2,RCUBE_FLATZ);

translate([0,6,0]) rcube([2,1,1],0.2,RCUBE_FLATBOTTOM);
translate([5,6,0]) rcube([2,1,1],0.2,RCUBE_FLATTOP);

translate([0,8,0]) rcube([2,1,1],0.2,RCUBE_FLATFRONT);
translate([5,8,0]) rcube([2,1,1],0.2,RCUBE_FLATBACK);

translate([0,10,0]) rcube([2,1,1],0.2,RCUBE_FLATLEFT);
translate([5,10,0]) rcube([2,1,1],0.2,RCUBE_FLATRIGHT);

translate([0+1,14,0]) rcylinder(3,1.5,0.2);
translate([3+1,14,0]) rcylinder(3,1.5,0.2,false);
translate([6+1,14,0]) rcylinder(3,1.5,0.2,RCYLINDER_FLATBOTTOM);
translate([9+1,14,0]) rcylinder(3,1.5,0.2,RCYLINDER_FLATTOP);

The library code (I might later release it as a separate library):

// Title: rcube(), rcylinder() & torus()
// Author: Rene K. Mueller
// License: MIT License 2020
// Version: 0.0.2

RCUBE_FLATX = [false,true,true];
RCUBE_FLATY = [true,false,true];
RCUBE_FLATZ = [true,true,false];
RCUBE_FLATBOTTOM = [false,false,false,false,true,true,true,true];
RCUBE_FLATTOP = [true,true,true,true,false,false,false,false];
RCUBE_FLATFRONT = [false,false,true,true,false,false,true,true];
RCUBE_FLATBACK = [true,true,false,false,true,true,false,false];
RCUBE_FLATLEFT = [false,true,true,false,false,true,true,false];
RCUBE_FLATRIGHT = [true,false,false,true,true,false,false,true];

module rcube(a=1,r=0.1,rd=[true,true,true],center=false,$fn=32) {
    if(FAST_RCUBE)
       cube(a);
    else {
       x = len(a) ? a[0] : a;
       y = len(a) ? a[1] : a;
       z = len(a) ? a[2] : a;
       rd = len(rd) ? rd : [rd,rd,rd];

          if((len(rd)==3 && rd[0] && rd[1] && rd[2]) || (len(a)==0 && rd)) // rd=[true,true,true] or true
             hull() {
                translate([r,r,r]) sphere(r);
                translate([x-r,r,r]) sphere(r);
                translate([x-r,y-r,r]) sphere(r);
                translate([r,y-r,r]) sphere(r);
                translate([r,r,z-r]) sphere(r);
                translate([x-r,r,z-r]) sphere(r);
                translate([x-r,y-r,z-r]) sphere(r);
                translate([r,y-r,z-r]) sphere(r);
             } 
          else                                                        // anything else
             hull() {
                translate([r,r,r]) rcube_prim(r,rd,0);
                translate([x-r,r,r]) rcube_prim(r,rd,1);
                translate([x-r,y-r,r]) rcube_prim(r,rd,2);
                translate([r,y-r,r]) rcube_prim(r,rd,3);
                translate([r,r,z-r]) rcube_prim(r,rd,4);
                translate([x-r,r,z-r]) rcube_prim(r,rd,5);
                translate([x-r,y-r,z-r]) rcube_prim(r,rd,6);
                translate([r,y-r,z-r]) rcube_prim(r,rd,7);
             }
    }
 } 

module rcube_prim(r,rd,i) {
    a = len(rd);
    if(a<=3) {
       if(a && rd[0] && rd[1] && rd[2]) 
          sphere(r);
       else if(a && rd[0] && rd[1])
          translate([0,0,-r]) cylinder(r=r,h=r*2);
       else if(a && rd[1] && rd[2])
          translate([-r,0,0]) rotate([0,90,0]) cylinder(r=r,h=r*2);
       else if(a && rd[0] && rd[2])
          translate([0,-r,0]) rotate([-90,0,0]) cylinder(r=r,h=r*2);
       else
          translate([-r,-r,-r]) cube(r*2);
    } else 
       if(rd[i]) 
          sphere(r);
       else 
          translate([-r,-r,-r]) cube(r*2);
 }

RCYLINDER_FLATBOTTOM = [false,true];
RCYLINDER_FLATTOP = [true,false];

module rcylinder(h=2,d=1,r=0.1,rd=[true,true],$fn=40) {
    if(FAST_RCYLINDER)
       cylinder(d=d,h=h);
    else
       hull() { 
          translate([0,0,r]) 
             if(len(rd) && rd[0]) torus(do=d,di=r*2); else translate([0,0,-r]) cylinder(d=d,h=r);          
          translate([0,0,h-r]) 
             if(len(rd) && rd[1]) torus(do=d,di=r*2); else cylinder(d=d,h=r);
       }
 }

 module torus(do=2,di=0.1,a=360) {
    rotate_extrude(convexity=10,angle=a) {
       translate([do/2-di/2,0,0]) circle(d=di,$fn=20);
    }
 }

chainhull()

module chainhull() {
    for(i=[0:1:$children-2])
       hull() {
          children(i);
          children(i+1);
       }
 }

There is one drawback using chainhull() { } as you can’t use conditional if else with { } within as it combines them as a group and becomes a child structure and so it will act as hull(), so you only can list non-conditional pieces within chainhull() as of OpenSCAD 2019.05, perhaps at a later time this limit vanishes.

That’s it.