ThingRenderer¶
Vanilla game class at Assets.Scripts.Objects.ThingRenderer. Wrapper around a Unity Renderer that unifies material access across two drawing paths (MeshRenderer and DrawData, used for batched / instanced geometry). Each Thing carries a List<ThingRenderer> in its Renderers field; mod code that needs to read or mutate the rendered material for a Thing goes through this wrapper.
Containing collection¶
Thing.Renderers at decompile Thing.cs line 534:
Populated during Thing initialization from the prefab's renderers. May be empty for Things with no visible geometry. Mod code must guard with thing.Renderers.Count > 0 before indexing.
Material accessors¶
ThingRenderer exposes three accessors for the underlying material(s):
| Accessor | Line | Returns | Notes |
|---|---|---|---|
Materials { get; } |
ThingRenderer.cs:130 | Material[] |
Clones on the DrawData path, returns the shared-material array on the MeshRenderer path. Use when the intent is "read or mutate per-instance". |
sharedMaterials { get; } |
ThingRenderer.cs:160 | Material[] |
Always returns the shared-material array (or a clone on DrawData). Can be null if the parent was destroyed. |
GetMaterial() |
ThingRenderer.cs:247 | Material |
Convenience getter returning _drawData.materials[0]. DrawData-specific. |
Callers that want to read the current emission color or shader name use Materials[0] (or sharedMaterials[0]) and then call Unity's Material.GetColor("_EmissionColor"), .shader.name, .IsKeywordEnabled("_EMISSION"), etc.
The underlying UnityRenderer field (ThingRenderer.cs:17) is private; the three accessors above are the supported entry points.
Null safety¶
Materials and sharedMaterials can return null on the DrawData path if the parent Thing has been destroyed (ThingRenderer.cs:168-169). Guard:
if (thing.Renderers.Count > 0)
{
var mat = thing.Renderers[0].Materials[0];
if (mat != null) { ... }
}
Related vanilla usage¶
Thing.SetCustomColor(int index, bool emissive = false) iterates every entry in Renderers to write the _EmissionColor / DiffuseIndexPropertyID / SmoothnessIndexPropertyID shader properties. See ./ColorSwatch.md "Normal vs Emissive selection" for the full body. Mods that need to inspect the shader state post-SetCustomColor read the renderer list and the material on each entry.
Verification history¶
- 2026-04-21: page created. Findings from decompile of Assembly-CSharp.dll (ThingRenderer.cs line 17 for the private UnityRenderer field, line 130 for
Materials, line 160 forsharedMaterials, line 247 forGetMaterial; Thing.cs line 534 forThing.Renderers).
Open questions¶
- What triggers
ThingRendererto select theDrawDatapath over a plainMeshRenderer? Suspected:structureRenderMode != Standard(see./Structure.md), but unconfirmed. - Whether repeated calls to
Materialsin theMeshRendererpath clone the material each time (Unity's.materialaccessor semantics) or whetherThingRenderercaches the clone internally. Needs a runtime probe.