parameters¶
Demonstrates different ways to access and modify parameters of Cinema 4D scene elements.
parameters.py¶
"""Demonstrates different ways to access and modify parameters of Cinema 4D scene elements.
Topics:
- Atomic parameter access
- Bracket operator access
- Data container access
Related:
- data/_c4d_basecontainer.py
- data/_c4d_descid.py
- scene/_c4d_atom.py
- scene/_c4d_gelistnode.py
- scene/_c4d_baselist2d.py
"""
__author__ = "Ferdinand Hoppe"
__copyright__ = "Copyright (C) 2026 MAXON Computer GmbH"
__license__ = "Apache-2.0 License"
__version__ = "2027.0.0"
__date__ = "07/09/2026"
import c4d
import mxutils
doc: c4d.documents.BaseDocument # The active Cinema 4D document.
op: c4d.BaseObject | None # The currently selected object in the Cinema 4D document, can be None.
def main() -> None:
"""Runs the example.
"""
# Instantiate a cube. What is shown here would work for any type of BaseList2D scene element,
# not just objects. E.g., documents, materials, tags, etc.
cube: c4d.BaseObject = mxutils.CheckType(c4d.BaseObject(c4d.Ocube))
doc.InsertObject(cube)
# Cinema 4D has a parameter model then provides multiple ways to get or set parameters for scene
# elements.
print(f"--- Atom Access --------------------------------------------------------------------\n")
# First of all, there is the atomic parameter access via C4DAtom.Get/SetParameter methods. It is
# the most powerful way to access and modify parameters of scene elements but usually also the
# most cumbersome one.
# Set the size parameter of the cube using the atomic access methods.
cube.SetParameter(c4d.PRIM_CUBE_LEN, c4d.Vector(200, 200, 200), c4d.DESCFLAGS_SET_NONE)
print(f"{cube.GetParameter(c4d.PRIM_CUBE_LEN) = }")
# We can also set parameters using DescIDs instead of integer symbols.
cube.SetParameter(c4d.DescID(c4d.PRIM_CUBE_LEN), c4d.Vector(200, 200, 200), c4d.DESCFLAGS_SET_NONE)
print(f"{cube.GetParameter(c4d.DescID(c4d.PRIM_CUBE_LEN)) = }")
# What makes SetParameter calls more powerful is that we have here the get/set flags. We can
# for example simulate a user interaction as shown below. Other than for the two other methods,
# we also get a return value for set operations, indicating whether the operation was successful.
# But failure is extremely rare in typical usage scenarios.
if not cube.SetParameter(c4d.PRIM_CUBE_LEN, c4d.Vector(200, 200, 200), c4d.DESCFLAGS_SET_USERINTERACTION):
print("Failed to set cube size with user interaction.")
print(f"--- Bracket Operator Access --------------------------------------------------------\n")
# Unique to Python is the bracket operator access for parameters. We can again use both plain
# integers and DescIDs with the bracket operator. For example:
cube[c4d.PRIM_CUBE_LEN] = c4d.Vector(200, 200, 200)
cube[c4d.DescID(c4d.PRIM_CUBE_LEN)] = c4d.Vector(200, 200, 200)
print(f"{cube[c4d.PRIM_CUBE_LEN] = }")
print(f"{cube[c4d.DescID(c4d.PRIM_CUBE_LEN)] = }")
print(f"--- Data Container Access ----------------------------------------------------------\n")
# Each scene element has a data container that stores the parameters unique to that element. I.e.,
# things that show up in the Basic Tab (Name, Color, etc.) or Coordinates Tab (Position,
# Rotation, Scale) are not part of the data container. Only the parameters that are specific to
# the element itself are stored there. We also cannot use DescIDs with the data container; only
# the integer symbols work.
data: c4d.BaseContainer = cube.GetDataInstance()
# Modify the cube length parameter in the data container. This will affect the node in the document
# since we are working on the actual data instance of the node.
data[c4d.PRIM_CUBE_LEN] = c4d.Vector(200, 200, 200)
# Sometimes we do not want to modify the actual data instance directly. In such cases, we can
# work on a copy of the data container instead.
copy: c4d.BaseContainer = data.GetClone(c4d.COPYFLAGS_NONE)
copy[c4d.PRIM_CUBE_LEN] = c4d.Vector(100, 100, 100)
print(f"{copy = }")
# We can also overwrite the full container of an element. Here we write our copy into the cube.
# This is an easy way to copy most of the parameters from one object to another.
cube.SetData(copy)
# There exist also type specific access methods.
copy.SetVector(c4d.PRIM_CUBE_LEN, c4d.Vector(300, 300, 300))
size: c4d.Vector = copy.GetVector(c4d.PRIM_CUBE_LEN)
print(f"{size = }")
if __name__ == "__main__":
c4d.ClearPythonConsole()
main()