# How can I make a Genus 3 Surface?

I would like to create a Genus 3 Surface (i.e. a "triple torus") like this one:

Ideally, its topology should be fairly decent (unlike the one in the picture) and I'd rather not make this surface out of the connected sum of three separate tori. Is there an easy way to do this?

Here is a way to do it, create a torus, make it as simple as possible, like 16x8 vertices, move it away from its origin on Y or X axis in Edit mode, duplicate and rotate 120° twice with the 3D cursor as axis of rotation, cut a hole on each one:

CtrlE > Bridge Edge Loops between these vertices:

Do the same all around, continue to fill the faces until you get that:

Create an edge loop around each bridge:

Merge these 3 inner vertices at center:

Scale these edge loops except on Z:

Result with a Subdivision Surface modifier and Shade Smooth:

• R + Z for stress relief Sep 1, 2023 at 3:33

If you are a person who likes to start from top view in 2D, you can try this method starting with a circle with 8 vertices, inset, remove face, add Loop Cut, and duplicate it 2 times around the 3D Cursor by 120 degrees.

Then select the outer edge loops and inner circle edge loops for the top and the bottom of the geometry, and press Alt+S to uniformly scale it to approximate the Torus shape.

Final result with Subdivision Surface Modifier and Shade Smooth.

Without creating anything too complicated, you can run this script and with a little mesh cleanup you can get something close. Make it in a new scene because it will remove everything in the scene.

import bpy

def create_genus_3_surface():
# Clear existing mesh objects
bpy.ops.object.select_all(action='DESELECT')
bpy.ops.object.select_by_type(type='MESH')
bpy.ops.object.delete()

# Create first torus
align='WORLD', location=(0, 0, 0),
rotation=(0, 0, 0),
)
torus1 = bpy.context.object

# Create second torus
align='WORLD', location=(4, 0, 0),
rotation=(0, 0, 0),
)
torus2 = bpy.context.object

# Create third torus
align='WORLD', location=(2, 4, 0),
rotation=(0, 0, 0),
)
torus3 = bpy.context.object

# Use boolean modifiers to merge the tori
torus1.modifiers.new(name="BooleanTorus2", type='BOOLEAN')
torus1.modifiers["BooleanTorus2"].operation = 'UNION'
torus1.modifiers["BooleanTorus2"].object = torus2
bpy.ops.object.modifier_apply({"object": torus1}, modifier="BooleanTorus2")

torus1.modifiers.new(name="BooleanTorus3", type='BOOLEAN')
torus1.modifiers["BooleanTorus3"].operation = 'UNION'
torus1.modifiers["BooleanTorus3"].object = torus3
bpy.ops.object.modifier_apply({"object": torus1}, modifier="BooleanTorus3")

# Delete the original second and third tori
bpy.ops.object.select_all(action='DESELECT')
torus2.select_set(True)
torus3.select_set(True)
bpy.ops.object.delete()

# Apply a smooth shading to the final object
bpy.ops.object.select_all(action='DESELECT')
torus1.select_set(True)