Generator — Blender

Blender is an extensive open-source 3D creation suite. SimForge leverages Blender's generative capabilities to create a wide range of assets via BlGenerator using its Python API (bpy).

Requirements

Python 3.11

For python_version=='3.11', is it enough to install SimForge with the bpy extra:

# Install SimForge with bpy extra
pip install simforge[bpy]

Other Environments | --subprocess

For other environments, BlGenerator can be run in a subprocess using the embedded Python interpreter. This requires a local Blender installation with the blender executable in PATH.

CLI: Generation in a subprocess can be achieved by simforge gen --subprocess.

BlGenerator

All Bl* assets are automatically registered for generation using the BlGenerator class, which is a subclass of Generator and provides a unified interface for generating Blender assets.

BlGeometry

Geometry generated by Blender is specified using the BlGeometry class, which includes a sequence of BlGeometryOp operations that create and modify the geometry of a mesh object.

The BlGeometryOp operations can use arbitrary bpy calls to manipulate the mesh object. For instance, BlGeometryNodesModifier is a subclass of BlGeometryOp that supports Blender's Geometry Nodes, which can be loaded prior to the generation from a Python file (NodeToPython). Additional typed inputs can be defined as attributes of the operation, and they will be automatically passed as the inputs of the node group.

Example:

from pathlib import Path
from typing import List, Tuple

from pydantic import PositiveFloat, PositiveInt
from simforge import (
    BlGeometry,
    BlGeometryNodesModifier,
    BlGeometryOp,
    BlMaterial,
    BlNodesFromPython,
)


class ExampleNodes(BlGeometryNodesModifier):
    nodes: BlNodesFromPython = BlNodesFromPython(
        name="ExampleNodeGroup",
        python_file=Path(__file__).parent.joinpath("example_nodes.py"),
    )

    input1: PositiveInt = 42
    input2: Tuple[PositiveFloat, PositiveFloat, PositiveFloat] = (0.1, 0.1, 0.1)
    input3: BlMaterial | None = None


class ExampleGeo(BlGeometry):
    ops: List[BlGeometryOp] = [ExampleNodes()]

BlMaterial

Materials of Blender assets are defined using the BlMaterial class, which includes BlShader that specifies the appearance of the object.

The BlShader class must utilize Shader Nodes to define the appearance of the object. Similar to BlGeometryNodesModifier, the nodes can be loaded from a Python file (NodeToPython) and additional typed inputs can be defined as attributes of the shader.

Example:

from pathlib import Path
from typing import Tuple

from pydantic import NonNegativeFloat, PositiveFloat
from simforge import BlMaterial, BlNodesFromPython, BlShader


class ExampleShader(BlShader):
    nodes: BlNodesFromPython = BlNodesFromPython(
        name="ExampleShader",
        python_file=Path(__file__).parent.joinpath("example_nodes.py"),
    )

    input1: PositiveFloat = 1.0
    input2: Tuple[
        NonNegativeFloat, NonNegativeFloat, NonNegativeFloat, NonNegativeFloat
    ] = (
        0.0,
        0.2,
        0.8,
        1.0,
    )


class ExampleMat(BlMaterial):
    shader: BlShader = ExampleShader()

BlModel

The BlModel class combines geo: BlGeometry and an optional mat: BlMaterial to define a model. Furthermore, texture_resolution attribute specifies the resolution of the baked textures for the model.

BlGeometry with BlGeometryNodesModifier operation can internally set the material of the object via BlMaterial inputs. In this case, the mat attribute can be omitted as it would otherwise override the material set by the geometry nodes modifier.

Example:

from pydantic import InstanceOf, SerializeAsAny
from simforge import BakeType, BlGeometry, BlMaterial, BlModel, TexResConfig


class ExampleModel(BlModel):
    geo: SerializeAsAny[InstanceOf[BlGeometry]] = ExampleGeo()
    mat: SerializeAsAny[InstanceOf[BlMaterial]] | None = ExampleMat()
    texture_resolution: TexResConfig = {
        BakeType.ALBEDO: 2048,
        BakeType.EMISSION: 256,
        BakeType.METALLIC: 256,
        BakeType.NORMAL: 4096,
        BakeType.ROUGHNESS: 512,
    }

New Assets

Geometry Nodes and Shader Nodes are the preferred methods for defining new Blender-based geometry and materials because they provide a high level of flexibility via artist-friendly node-based interfaces. The nodes can be exported to Python files using NodeToPython and integrated into the SimForge asset definitions, as shown in the examples above. Furthermore, automatic randomization can be exposed by including a seed attribute in the node group that will be automatically detected and updated by the generator.

If you are new to Blender, there is a vast number of free Blender tutorials and resources available online that can help you get started with creating your own assets. Consider creating your own Donut as the first step!

If you are somewhat familiar with Blender but never used Geometry Nodes, consider watching the Geometry Nodes Fundamentals that provides an excellent introduction to the topic.

If you are a seasoned Blender artist, then please teach us your ways! The contributors of SimForge are mostly non-artists with limited creativity, so we would greatly appreciate your help in improving and expanding the asset library.