crystal-renderer

Render crystal geometry to SVG for visualization, STL for 3D printing, and glTF for web/AR/VR applications.

pip install crystal-renderer

SVG Rendering

# generate_svg(geometry, output, **options) → str | None

Render crystal geometry to SVG format.

from crystal_renderer import generate_svg

# Save to file
generate_svg(geom, "crystal.svg")

# Get SVG string
svg_string = generate_svg(geom, None)

# With options
generate_svg(geom, "crystal.svg",
    width=400,
    height=400,
    elevation=30,
    azimuth=-45,
    face_color="#0ea5e9",
    edge_color="#0369a1",
    edge_width=1.5,
    opacity=0.85,
    gradient=True,
    show_axes=False,
    show_labels=False
)

SVG Options

OptionTypeDefaultDescription
width int 400 SVG width in pixels
height int 400 SVG height in pixels
elevation float 30 View elevation in degrees
azimuth float -45 View azimuth in degrees
zoom float 1.0 Zoom factor
face_color str "#0ea5e9" Face fill color (hex)
edge_color str "#0369a1" Edge stroke color
edge_width float 1.5 Edge stroke width
opacity float 0.85 Face opacity (0-1)
gradient bool True Apply lighting gradient
show_axes bool False Show crystallographic axes
show_labels bool False Show Miller index labels
title str None Title text below crystal
# generate_cdl_svg(cdl, output, **options) → str | None

Convenience function to render directly from a CDL string.

from crystal_renderer import generate_cdl_svg

# One-liner from CDL to SVG
generate_cdl_svg("cubic[m3m]:{111}", "diamond.svg")

# With options
generate_cdl_svg(
    "cubic[m3m]:{111}@1.0 + {100}@1.3",
    "truncated.svg",
    face_color="#8b5cf6"
)

3D Export

# export_stl(geometry, output, **options) → None

Export crystal geometry to STL format for 3D printing.

from crystal_renderer import export_stl

# Basic export
export_stl(geom, "crystal.stl")

# With options
export_stl(geom, "crystal.stl",
    scale=20.0,      # Scale to 20mm
    binary=True,     # Binary format (smaller)
    units="mm"       # Unit metadata
)

STL Options

OptionTypeDefaultDescription
scale float 10.0 Scale factor (output size)
binary bool True Use binary format
units str "mm" Units: "mm", "cm", "in"
# export_gltf(geometry, output, **options) → None

Export crystal geometry to glTF 2.0 format for web, AR, and VR applications.

from crystal_renderer import export_gltf

# Basic export
export_gltf(geom, "crystal.gltf")

# With material properties
export_gltf(geom, "crystal.gltf",
    color=(0.05, 0.65, 0.91),  # RGB (0-1)
    metallic=0.0,
    roughness=0.3,
    opacity=0.85
)

# Binary format (single file)
export_gltf(geom, "crystal.glb")  # Auto-detects from extension

glTF Options

OptionTypeDefaultDescription
scale float 1.0 Scale factor
color tuple (0.05, 0.65, 0.91) Base color RGB (0-1)
metallic float 0.0 Metallic factor (0-1)
roughness float 0.3 Roughness factor (0-1)
opacity float 1.0 Opacity (0-1)
binary bool auto Use GLB format
# export_gemcad(geometry, output) → None

Export to GEMCAD .asc format for gem cutting design.

from crystal_renderer import export_gemcad

export_gemcad(geom, "crystal.asc")

Batch Rendering

# render_batch(items, output_dir, **options) → list[str]

Render multiple crystals efficiently.

from crystal_renderer import render_batch
from mineral_database import list_presets, get_preset

# Prepare items
items = []
for name in list_presets():
    preset = get_preset(name)
    items.append({
        'name': name,
        'cdl': preset.cdl
    })

# Render all to SVG
output_files = render_batch(
    items,
    output_dir="./crystals",
    format="svg",
    width=300,
    height=300
)

print(f"Generated {len(output_files)} files")

View Utilities

# create_camera(elevation, azimuth, distance) → Camera

Create a camera for consistent view angles.

from crystal_renderer import create_camera, generate_svg

camera = create_camera(
    elevation=35,   # degrees from horizontal
    azimuth=-45,    # rotation around vertical
    distance=5.0   # distance from origin
)

# Use same camera for multiple renders
generate_svg(geom1, "crystal1.svg", camera=camera)
generate_svg(geom2, "crystal2.svg", camera=camera)
# project_to_2d(geometry, camera) → ProjectedGeometry

Project 3D geometry to 2D for custom rendering.

from crystal_renderer import project_to_2d, create_camera

camera = create_camera(elevation=30, azimuth=-45)
projected = project_to_2d(geom, camera)

# Access 2D data
for face in projected.faces:
    print(face.vertices_2d)   # [(x, y), ...]
    print(face.depth)         # Z-order for painting
    print(face.brightness)    # Lighting intensity