{
 "site": "https://cinder.ash10.dev",
 "generated": "2026-11-09T14:07:18.836Z",
 "engine": {
  "version": "0.1.0",
  "commit": "47c93524b42ce10d500285bf5c2319798a571277",
  "imported": "2026-11-09T14:03:27.213Z",
  "platforms": [
   "linux-64",
   "osx-arm64"
  ]
 },
 "formats": {
  "llms": "https://cinder.ash10.dev/llms.txt",
  "llmsFull": "https://cinder.ash10.dev/llms-full.txt",
  "agents": "https://cinder.ash10.dev/agents/AGENTS.md",
  "search": "https://cinder.ash10.dev/search-index.json",
  "mcp": "https://cinder.ash10.dev/mcp",
  "markdown": "Each page's `md` path serves its raw Markdown."
 },
 "pages": [
  {
   "path": "/docs/",
   "md": "/docs.md",
   "title": "Cinder documentation",
   "section": "Start",
   "source": null,
   "summary": "Cinder 0.1.0 is a 3D game engine written in Mojo 1.2.0 over one C11 native shim. These pages are imported verbatim from the engine repository; the status report is the source of truth for what has been verified. Every page is also available as raw Markdown at its path plus…",
   "headings": [
    {
     "id": "start",
     "text": "Start",
     "depth": 2
    },
    {
     "id": "guides",
     "text": "Guides",
     "depth": 2
    },
    {
     "id": "engine-design",
     "text": "Engine design",
     "depth": 2
    },
    {
     "id": "decisions",
     "text": "Decisions",
     "depth": 2
    },
    {
     "id": "api-reference",
     "text": "API reference",
     "depth": 2
    },
    {
     "id": "project",
     "text": "Project",
     "depth": 2
    },
    {
     "id": "using-cinder-with-ai-agents",
     "text": "Using Cinder with AI agents",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/tutorial/",
   "md": "/docs/tutorial.md",
   "title": "Build your first game",
   "section": "Start",
   "source": "docs/TUTORIAL.md",
   "summary": "This tutorial builds a small game on Cinder from nothing: a red ball you push around a lit ledge to knock six crates off the edge. It takes about an hour. The finished code is in examples/first_game/ and is compiled and run headless by tests/examples/test_first_game.mojo, so…",
   "headings": [
    {
     "id": "0-prerequisites",
     "text": "0. Prerequisites",
     "depth": 2
    },
    {
     "id": "1-an-app-and-a-game",
     "text": "1. An App and a Game",
     "depth": 2
    },
    {
     "id": "2-a-ledge-crates-and-a-ball",
     "text": "2. A ledge, crates and a ball",
     "depth": 2
    },
    {
     "id": "3-a-sun-and-a-camera",
     "text": "3. A sun and a camera",
     "depth": 2
    },
    {
     "id": "4-input-as-actions-and-axes",
     "text": "4. Input as actions and axes",
     "depth": 2
    },
    {
     "id": "5-pushing-the-ball-the-fixed-step",
     "text": "5. Pushing the ball: the fixed step",
     "depth": 2
    },
    {
     "id": "6-per-frame-logic",
     "text": "6. Per-frame logic",
     "depth": 2
    },
    {
     "id": "7-a-hud",
     "text": "7. A HUD",
     "depth": 2
    },
    {
     "id": "8-cleaning-up",
     "text": "8. Cleaning up",
     "depth": 2
    },
    {
     "id": "9-running-it-headless-and-testing-it",
     "text": "9. Running it headless, and testing it",
     "depth": 2
    },
    {
     "id": "where-to-go-next",
     "text": "Where to go next",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/examples/first-game/",
   "md": "/docs/examples/first-game.md",
   "title": "First game: complete source",
   "section": "Start",
   "source": "examples/first_game/",
   "summary": "The finished code of the tutorial, copied verbatim from examples/first_game/ in the engine repository. The engine's test tests/examples/test_first_game.mojo compiles it and runs it headless, so it builds under the pinned toolchain (Mojo 1.2.0). Each # Step N comment marks…",
   "headings": [
    {
     "id": "examplesfirst_gamemainmojo",
     "text": "examples/first_game/main.mojo",
     "depth": 2
    },
    {
     "id": "examplesfirst_gamegamemojo",
     "text": "examples/first_game/game.mojo",
     "depth": 2
    },
    {
     "id": "examplesfirst_game__init__mojo",
     "text": "examples/first_game/__init__.mojo",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/examples/sample-game/",
   "md": "/docs/examples/sample-game.md",
   "title": "Sample game entry point",
   "section": "Start",
   "source": "sample/main.mojo",
   "summary": "sample/main.mojo from the engine repository, verbatim: the entry point of the third-person sample game (ADR-0014). The game itself lives in sample/game/ (components, levels, settings, gameplay) and is built only on public engine APIs.",
   "headings": [
    {
     "id": "samplemainmojo",
     "text": "sample/main.mojo",
     "depth": 2
    }
   ]
  },
  {
   "path": "/agents/",
   "md": "/agents.md",
   "title": "Using Cinder with AI coding agents",
   "section": "Start",
   "source": null,
   "summary": "A ready-to-use AGENTS.md / CLAUDE.md brief, the llms.txt and JSON indexes, raw Markdown URLs, the MCP endpoint and prompts that work.",
   "headings": [
    {
     "id": "1-drop-the-agent-brief-into-your-repository",
     "text": "1. Drop the agent brief into your repository",
     "depth": 2
    },
    {
     "id": "2-point-the-agent-at-the-docs",
     "text": "2. Point the agent at the docs",
     "depth": 2
    },
    {
     "id": "3-connect-the-mcp-server",
     "text": "3. Connect the MCP server",
     "depth": 2
    },
    {
     "id": "4-prompts-that-work",
     "text": "4. Prompts that work",
     "depth": 2
    },
    {
     "id": "5-ground-rules-to-give-any-agent",
     "text": "5. Ground rules to give any agent",
     "depth": 2
    },
    {
     "id": "the-brief",
     "text": "The brief",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/",
   "md": "/docs/guides.md",
   "title": "Subsystem guides",
   "section": "Guides",
   "source": null,
   "summary": "One guide per engine module: key types and ownership, setup, per-frame use, threading rules and pitfalls. Each links to its generated API reference.",
   "headings": []
  },
  {
   "path": "/docs/guides/anim/",
   "md": "/docs/guides/anim.md",
   "title": "Animation guide (cinder/anim)",
   "section": "Guides",
   "source": "docs/guides/anim.md",
   "summary": "cinder/anim is skeletal animation written in Mojo: skeletons built from glTF skins or read from cooked .cskel files, clip sampling into local poses, blend trees evaluated on a shared phase, animators with states, crossfades, events and root motion, and an AnimationSystem that…",
   "headings": [
    {
     "id": "units-and-conventions",
     "text": "Units and conventions",
     "depth": 2
    },
    {
     "id": "skeletons",
     "text": "Skeletons",
     "depth": 2
    },
    {
     "id": "poses-and-clip-sampling",
     "text": "Poses and clip sampling",
     "depth": 2
    },
    {
     "id": "blend-trees",
     "text": "Blend trees",
     "depth": 2
    },
    {
     "id": "the-animator",
     "text": "The animator",
     "depth": 2
    },
    {
     "id": "the-animation-system-and-the-render-bridge",
     "text": "The animation system and the render bridge",
     "depth": 2
    },
    {
     "id": "threading-one-job-per-animator",
     "text": "Threading: one job per animator",
     "depth": 2
    },
    {
     "id": "pitfalls",
     "text": "Pitfalls",
     "depth": 2
    },
    {
     "id": "see-also",
     "text": "See also",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/app/",
   "md": "/docs/guides/app.md",
   "title": "Application runtime (cinder/app)",
   "section": "Guides",
   "source": "docs/guides/app.md",
   "summary": "cinder/app is the top of the engine: App owns every subsystem, runs the fixed-step game loop and renders, either into an SDL window or, with --headless, into an offscreen texture that can be read back. Gameplay implements the Game trait and is called from App.run_frame. The…",
   "headings": [
    {
     "id": "appconfig",
     "text": "AppConfig",
     "depth": 2
    },
    {
     "id": "the-game-trait",
     "text": "The Game trait",
     "depth": 2
    },
    {
     "id": "app-ownership-and-destruction-order",
     "text": "App ownership and destruction order",
     "depth": 2
    },
    {
     "id": "construction",
     "text": "Construction",
     "depth": 2
    },
    {
     "id": "run_frame-and-the-loop-order",
     "text": "run_frame and the loop order",
     "depth": 2
    },
    {
     "id": "windowed-vs-headless-read_frame",
     "text": "Windowed vs headless; read_frame",
     "depth": 2
    },
    {
     "id": "command-line-parse_app_args",
     "text": "Command line: parse_app_args",
     "depth": 2
    },
    {
     "id": "timing-and-allocation-accounting",
     "text": "Timing and allocation accounting",
     "depth": 2
    },
    {
     "id": "logging",
     "text": "Logging",
     "depth": 2
    },
    {
     "id": "threading",
     "text": "Threading",
     "depth": 2
    },
    {
     "id": "pitfalls",
     "text": "Pitfalls",
     "depth": 2
    },
    {
     "id": "tests-and-references",
     "text": "Tests and references",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/assets/",
   "md": "/docs/guides/assets.md",
   "title": "Assets guide (cinder/assets)",
   "section": "Guides",
   "source": "docs/guides/assets.md",
   "summary": "cinder/assets gets content from disk into the renderer. It has two paths:",
   "headings": [
    {
     "id": "gltf-import",
     "text": "glTF import",
     "depth": 2
    },
    {
     "id": "cooked-formats-cookedmojo",
     "text": "Cooked formats (cooked.mojo)",
     "depth": 2
    },
    {
     "id": "the-cooker-cookmojo-toolscinder_cookmojo",
     "text": "The cooker (cook.mojo, tools/cinder_cook.mojo)",
     "depth": 2
    },
    {
     "id": "ktx2-textures-texturesmojo",
     "text": "KTX2 textures (textures.mojo)",
     "depth": 2
    },
    {
     "id": "the-asset-server-runtimemojo",
     "text": "The asset server (runtime.mojo)",
     "depth": 2
    },
    {
     "id": "threading-rules",
     "text": "Threading rules",
     "depth": 2
    },
    {
     "id": "pitfalls",
     "text": "Pitfalls",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/audio/",
   "md": "/docs/guides/audio.md",
   "title": "Audio (cinder/audio)",
   "section": "Guides",
   "source": "docs/guides/audio.md",
   "summary": "cinder/audio is the engine's sound layer over miniaudio. It provides mixing buses, decoded and streamed sounds, one-shots that clean up after themselves, 3D spatialisation with distance attenuation, a single listener, and an ECS bridge that moves sounds with entities and the…",
   "headings": [
    {
     "id": "key-types-and-ownership",
     "text": "Key types and ownership",
     "depth": 2
    },
    {
     "id": "creating-an-engine",
     "text": "Creating an engine",
     "depth": 2
    },
    {
     "id": "loading-and-playing",
     "text": "Loading and playing",
     "depth": 2
    },
    {
     "id": "one-shots",
     "text": "One-shots",
     "depth": 3
    },
    {
     "id": "3d-position-attenuation-and-the-listener",
     "text": "3D position, attenuation and the listener",
     "depth": 2
    },
    {
     "id": "the-ecs-bridge",
     "text": "The ECS bridge",
     "depth": 2
    },
    {
     "id": "per-frame-work-update-take_ended-read_frames",
     "text": "Per-frame work: update, take_ended, read_frames",
     "depth": 2
    },
    {
     "id": "threading",
     "text": "Threading",
     "depth": 2
    },
    {
     "id": "pitfalls",
     "text": "Pitfalls",
     "depth": 2
    },
    {
     "id": "tests-and-references",
     "text": "Tests and references",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/core/",
   "md": "/docs/guides/core.md",
   "title": "cinder/core guide",
   "section": "Guides",
   "source": "docs/guides/core.md",
   "summary": "cinder/core is the lowest Mojo layer of the engine: logging, assertions, a bump arena, generational handles and pools, a bounded ring, byte packing and hashing, file helpers, a monotonic clock with a fixed-step accumulator, CPU images, the job system, Tracy zones, Boxed heap…",
   "headings": [
    {
     "id": "key-types",
     "text": "Key types",
     "depth": 2
    },
    {
     "id": "logging",
     "text": "Logging",
     "depth": 2
    },
    {
     "id": "assertions",
     "text": "Assertions",
     "depth": 2
    },
    {
     "id": "arena",
     "text": "Arena",
     "depth": 2
    },
    {
     "id": "handles-and-pools",
     "text": "Handles and pools",
     "depth": 2
    },
    {
     "id": "ring-buffer-bytes-hashing",
     "text": "Ring buffer, bytes, hashing",
     "depth": 2
    },
    {
     "id": "filesystem-and-time",
     "text": "Filesystem and time",
     "depth": 2
    },
    {
     "id": "images",
     "text": "Images",
     "depth": 2
    },
    {
     "id": "job-system",
     "text": "Job system",
     "depth": 2
    },
    {
     "id": "profiling",
     "text": "Profiling",
     "depth": 2
    },
    {
     "id": "c-strings",
     "text": "C strings",
     "depth": 2
    },
    {
     "id": "boxed",
     "text": "Boxed",
     "depth": 2
    },
    {
     "id": "math",
     "text": "Math",
     "depth": 2
    },
    {
     "id": "threading-and-error-handling",
     "text": "Threading and error handling",
     "depth": 2
    },
    {
     "id": "pitfalls",
     "text": "Pitfalls",
     "depth": 2
    },
    {
     "id": "related-documents",
     "text": "Related documents",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/ecs/",
   "md": "/docs/guides/ecs.md",
   "title": "ECS guide (cinder/ecs)",
   "section": "Guides",
   "source": "docs/guides/ecs.md",
   "summary": "cinder/ecs is the archetype entity component system every gameplay-facing module builds on. It sits directly above cinder/core (it uses core/math for Mat4 and core/jobs for the scheduler) and below render, physics, anim, audio, assets and scene, which define their own…",
   "headings": [
    {
     "id": "model",
     "text": "Model",
     "depth": 2
    },
    {
     "id": "component-ids-in-use",
     "text": "Component ids in use",
     "depth": 3
    },
    {
     "id": "entities-and-components",
     "text": "Entities and components",
     "depth": 2
    },
    {
     "id": "queries-and-chunks",
     "text": "Queries and chunks",
     "depth": 2
    },
    {
     "id": "change-detection",
     "text": "Change detection",
     "depth": 2
    },
    {
     "id": "command-buffers",
     "text": "Command buffers",
     "depth": 2
    },
    {
     "id": "hierarchy-and-transforms",
     "text": "Hierarchy and transforms",
     "depth": 2
    },
    {
     "id": "schedule",
     "text": "Schedule",
     "depth": 2
    },
    {
     "id": "threading-rules",
     "text": "Threading rules",
     "depth": 2
    },
    {
     "id": "pitfalls",
     "text": "Pitfalls",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/gfx/",
   "md": "/docs/guides/gfx.md",
   "title": "cinder/gfx guide",
   "section": "Guides",
   "source": "docs/guides/gfx.md",
   "summary": "cinder/gfx is the safe, typed layer over wgpu-native. It owns the wgpu instance, adapter, device and queue (Gfx), keeps every GPU object the engine creates in generational pools behind typed handles (Resources), compiles WGSL with editor-friendly diagnostics and hot reload…",
   "headings": [
    {
     "id": "key-types-and-ownership",
     "text": "Key types and ownership",
     "depth": 2
    },
    {
     "id": "creating-a-device",
     "text": "Creating a device",
     "depth": 2
    },
    {
     "id": "pulling-callbacks",
     "text": "Pulling callbacks",
     "depth": 2
    },
    {
     "id": "resources",
     "text": "Resources",
     "depth": 2
    },
    {
     "id": "shaders",
     "text": "Shaders",
     "depth": 2
    },
    {
     "id": "pipelines-commands-readback",
     "text": "Pipelines, commands, readback",
     "depth": 2
    },
    {
     "id": "swapchain",
     "text": "Swapchain",
     "depth": 2
    },
    {
     "id": "debug-draw",
     "text": "Debug draw",
     "depth": 2
    },
    {
     "id": "threading-and-error-handling",
     "text": "Threading and error handling",
     "depth": 2
    },
    {
     "id": "pitfalls",
     "text": "Pitfalls",
     "depth": 2
    },
    {
     "id": "related-documents",
     "text": "Related documents",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/input/",
   "md": "/docs/guides/input.md",
   "title": "Input (cinder/input)",
   "section": "Guides",
   "source": "docs/guides/input.md",
   "summary": "cinder/input maps raw platform events to named gameplay controls. A game asks pressed(\"jump\") or axis(\"move_x\") instead of testing scancodes, players can rebind controls at runtime, and the whole map saves to a small text file. The package sits beside audio, physics, anim and…",
   "headings": [
    {
     "id": "model",
     "text": "Model",
     "depth": 2
    },
    {
     "id": "defining-a-map",
     "text": "Defining a map",
     "depth": 2
    },
    {
     "id": "feeding-events-and-reading-state",
     "text": "Feeding events and reading state",
     "depth": 2
    },
    {
     "id": "dead-zones",
     "text": "Dead zones",
     "depth": 3
    },
    {
     "id": "runtime-rebinding-by-listening",
     "text": "Runtime rebinding by listening",
     "depth": 2
    },
    {
     "id": "file-format",
     "text": "File format",
     "depth": 2
    },
    {
     "id": "threading",
     "text": "Threading",
     "depth": 2
    },
    {
     "id": "pitfalls",
     "text": "Pitfalls",
     "depth": 2
    },
    {
     "id": "tests-and-references",
     "text": "Tests and references",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/physics/",
   "md": "/docs/guides/physics.md",
   "title": "Physics guide (cinder/physics)",
   "section": "Guides",
   "source": "docs/guides/physics.md",
   "summary": "cinder/physics is the safe Mojo layer over Jolt. Jolt is reached through joltc inside libcinder_native; the parts of the shim that need C callbacks live in native/src/physics_shim.c (query filters, closest-hit collectors, CharacterVirtual extended update defaults) and…",
   "headings": [
    {
     "id": "units-and-conventions",
     "text": "Units and conventions",
     "depth": 2
    },
    {
     "id": "creating-a-world",
     "text": "Creating a world",
     "depth": 2
    },
    {
     "id": "layers-are-bits",
     "text": "Layers are bits",
     "depth": 3
    },
    {
     "id": "ownership-and-lifetimes",
     "text": "Ownership and lifetimes",
     "depth": 3
    },
    {
     "id": "shapes-and-bodies",
     "text": "Shapes and bodies",
     "depth": 2
    },
    {
     "id": "stepping-and-events",
     "text": "Stepping and events",
     "depth": 2
    },
    {
     "id": "queries",
     "text": "Queries",
     "depth": 2
    },
    {
     "id": "the-character-controller",
     "text": "The character controller",
     "depth": 2
    },
    {
     "id": "ecs-synchronisation-and-the-fixed-step-loop",
     "text": "ECS synchronisation and the fixed-step loop",
     "depth": 2
    },
    {
     "id": "threading",
     "text": "Threading",
     "depth": 2
    },
    {
     "id": "determinism",
     "text": "Determinism",
     "depth": 2
    },
    {
     "id": "pitfalls",
     "text": "Pitfalls",
     "depth": 2
    },
    {
     "id": "see-also",
     "text": "See also",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/platform/",
   "md": "/docs/guides/platform.md",
   "title": "cinder/platform guide",
   "section": "Guides",
   "source": "docs/guides/platform.md",
   "summary": "cinder/platform is the thin Mojo layer over SDL3 and the native shim's surface helpers. It loads libcinder_native exactly once, initialises SDL, creates windows, drains SDL's event queue into engine-level Events, opens and closes gamepads as they appear, creates the wgpu…",
   "headings": [
    {
     "id": "key-types",
     "text": "Key types",
     "depth": 2
    },
    {
     "id": "loading-the-library",
     "text": "Loading the library",
     "depth": 2
    },
    {
     "id": "windows-and-events",
     "text": "Windows and events",
     "depth": 2
    },
    {
     "id": "injecting-events",
     "text": "Injecting events",
     "depth": 2
    },
    {
     "id": "surfaces",
     "text": "Surfaces",
     "depth": 2
    },
    {
     "id": "imgui-event-forwarding",
     "text": "ImGui event forwarding",
     "depth": 2
    },
    {
     "id": "threading-and-error-handling",
     "text": "Threading and error handling",
     "depth": 2
    },
    {
     "id": "pitfalls",
     "text": "Pitfalls",
     "depth": 2
    },
    {
     "id": "related-documents",
     "text": "Related documents",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/render/",
   "md": "/docs/guides/render.md",
   "title": "cinder/render: the renderer",
   "section": "Guides",
   "source": "docs/guides/render.md",
   "summary": "cinder/render turns a RenderScene (camera, lights, instances, joint palettes, environment) into one submitted command buffer per frame. It is a clustered forward+ renderer with cascaded and atlas shadow maps, GPU-baked image-based lighting, GTAO, physically based bloom, AgX…",
   "headings": [
    {
     "id": "key-types-and-ownership",
     "text": "Key types and ownership",
     "depth": 2
    },
    {
     "id": "setting-up-a-renderer",
     "text": "Setting up a renderer",
     "depth": 2
    },
    {
     "id": "the-frame-in-order",
     "text": "The frame, in order",
     "depth": 2
    },
    {
     "id": "render-settings-and-defaults",
     "text": "Render settings and defaults",
     "depth": 2
    },
    {
     "id": "conventions",
     "text": "Conventions",
     "depth": 2
    },
    {
     "id": "camera-and-culling",
     "text": "Camera and culling",
     "depth": 2
    },
    {
     "id": "meshes-lods-skinning-morph-targets",
     "text": "Meshes, LODs, skinning, morph targets",
     "depth": 2
    },
    {
     "id": "materials-and-textures",
     "text": "Materials and textures",
     "depth": 2
    },
    {
     "id": "lights-and-clustered-culling",
     "text": "Lights and clustered culling",
     "depth": 2
    },
    {
     "id": "shadows",
     "text": "Shadows",
     "depth": 2
    },
    {
     "id": "the-frame-graph",
     "text": "The frame graph",
     "depth": 2
    },
    {
     "id": "adding-a-pass",
     "text": "Adding a pass",
     "depth": 3
    },
    {
     "id": "shaders-assembly-errors-hot-reload",
     "text": "Shaders: assembly, errors, hot reload",
     "depth": 2
    },
    {
     "id": "adding-a-shader-include",
     "text": "Adding a shader include",
     "depth": 3
    },
    {
     "id": "how-validation-errors-surface",
     "text": "How validation errors surface",
     "depth": 2
    },
    {
     "id": "golden-tests",
     "text": "Golden tests",
     "depth": 2
    },
    {
     "id": "render-stats",
     "text": "Render stats",
     "depth": 2
    },
    {
     "id": "zero-allocation-rules",
     "text": "Zero-allocation rules",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/scene/",
   "md": "/docs/guides/scene.md",
   "title": "Scene guide (cinder/scene)",
   "section": "Guides",
   "source": "docs/guides/scene.md",
   "summary": "cinder/scene is the layer between the ECS and the rest of the engine's content pipeline. It has three independent parts:",
   "headings": [
    {
     "id": "scene-components-and-the-registry",
     "text": "Scene components and the registry",
     "depth": 2
    },
    {
     "id": "documents-text-and-binary",
     "text": "Documents, text and binary",
     "depth": 2
    },
    {
     "id": "text-format-version-2",
     "text": "Text format (version 2)",
     "depth": 3
    },
    {
     "id": "binary-format",
     "text": "Binary format",
     "depth": 3
    },
    {
     "id": "versioning-and-migrations",
     "text": "Versioning and migrations",
     "depth": 2
    },
    {
     "id": "render-bridge",
     "text": "Render bridge",
     "depth": 2
    },
    {
     "id": "spawning-gltf",
     "text": "Spawning glTF",
     "depth": 2
    },
    {
     "id": "threading-rules",
     "text": "Threading rules",
     "depth": 2
    },
    {
     "id": "pitfalls",
     "text": "Pitfalls",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/guides/tools/",
   "md": "/docs/guides/tools.md",
   "title": "Tools: debug overlay, Tracy profiling, headless mode",
   "section": "Guides",
   "source": "docs/guides/tools.md",
   "summary": "Cinder's developer tooling is three things: the Dear ImGui debug overlay in cinder/tools, the Tracy client wrapper in cinder/core/profile.mojo, and the --headless mode of cinder/app that lets the same executables run without a display for tests, benchmarks and captures.",
   "headings": [
    {
     "id": "the-debug-overlay-debugui",
     "text": "The debug overlay (DebugUi)",
     "depth": 2
    },
    {
     "id": "ownership-and-lifetime",
     "text": "Ownership and lifetime",
     "depth": 3
    },
    {
     "id": "tabs",
     "text": "Tabs",
     "depth": 3
    },
    {
     "id": "what-the-inspector-edits-and-through-what",
     "text": "What the inspector edits, and through what",
     "depth": 3
    },
    {
     "id": "input-capture",
     "text": "Input capture",
     "depth": 3
    },
    {
     "id": "cstrings",
     "text": "CStrings",
     "depth": 3
    },
    {
     "id": "tracy-profiling-cindercoreprofilemojo",
     "text": "Tracy profiling (cinder/core/profile.mojo)",
     "depth": 2
    },
    {
     "id": "profiler-and-zone",
     "text": "Profiler and Zone",
     "depth": 3
    },
    {
     "id": "attaching-the-tracy-server",
     "text": "Attaching the Tracy server",
     "depth": 3
    },
    {
     "id": "--headless-as-a-tooling-feature",
     "text": "--headless as a tooling feature",
     "depth": 2
    },
    {
     "id": "threading",
     "text": "Threading",
     "depth": 2
    },
    {
     "id": "pitfalls",
     "text": "Pitfalls",
     "depth": 2
    },
    {
     "id": "tests-and-references",
     "text": "Tests and references",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/architecture/",
   "md": "/docs/architecture.md",
   "title": "Cinder architecture",
   "section": "Engine design",
   "source": "docs/ARCHITECTURE.md",
   "summary": "Dependencies point downward only. A module may import from the layers below it, never from the same layer except where noted, and never from above.",
   "headings": [
    {
     "id": "module-map",
     "text": "Module map",
     "depth": 2
    },
    {
     "id": "the-c-boundary",
     "text": "The C boundary",
     "depth": 2
    },
    {
     "id": "threading-model",
     "text": "Threading model",
     "depth": 2
    },
    {
     "id": "frame-loop",
     "text": "Frame loop",
     "depth": 2
    },
    {
     "id": "conventions-fixed",
     "text": "Conventions (fixed)",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/threading/",
   "md": "/docs/threading.md",
   "title": "Threading model",
   "section": "Engine design",
   "source": "docs/THREADING.md",
   "summary": "Fixed by section 4 of the brief; this page records how it is realised and which shared state exists.",
   "headings": [
    {
     "id": "threads",
     "text": "Threads",
     "depth": 2
    },
    {
     "id": "shared-state-and-how-it-is-protected",
     "text": "Shared state and how it is protected",
     "depth": 2
    },
    {
     "id": "rules",
     "text": "Rules",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/mojo-notes/",
   "md": "/docs/mojo-notes.md",
   "title": "Mojo 1.2.0 notes for Cinder",
   "section": "Engine design",
   "source": "docs/MOJO_NOTES.md",
   "summary": "Source of truth: https://mojolang.org/docs (manual and std reference for 1.2.0) and the release notes for 1.0.0, 1.1.0 and 1.2.0. Everything below was read from those pages on 2026-11-08 and confirmed by compiling spikes/hello/ under the pinned toolchain. When the compiler…",
   "headings": [
    {
     "id": "forms-we-use",
     "text": "Forms we use",
     "depth": 2
    },
    {
     "id": "functions-and-conventions",
     "text": "Functions and conventions",
     "depth": 3
    },
    {
     "id": "compile-time",
     "text": "Compile time",
     "depth": 3
    },
    {
     "id": "variables",
     "text": "Variables",
     "depth": 3
    },
    {
     "id": "structs-traits-lifecycle",
     "text": "Structs, traits, lifecycle",
     "depth": 3
    },
    {
     "id": "strings-and-formatting",
     "text": "Strings and formatting",
     "depth": 3
    },
    {
     "id": "pointers-and-memory-stdmemory",
     "text": "Pointers and memory (std.memory)",
     "depth": 3
    },
    {
     "id": "collections",
     "text": "Collections",
     "depth": 3
    },
    {
     "id": "simd-and-numerics",
     "text": "SIMD and numerics",
     "depth": 3
    },
    {
     "id": "ffi-stdffi",
     "text": "FFI (std.ffi)",
     "depth": 3
    },
    {
     "id": "testing-stdtesting",
     "text": "Testing (std.testing)",
     "depth": 3
    },
    {
     "id": "gpu",
     "text": "GPU",
     "depth": 3
    },
    {
     "id": "build",
     "text": "Build",
     "depth": 3
    },
    {
     "id": "facts-established-by-compiling-under-120-spikesapi_probe-2026-11-08",
     "text": "Facts established by compiling under 1.2.0 (spikes/api_probe, 2026-11-08)",
     "depth": 2
    },
    {
     "id": "compiler-limits-met-so-far",
     "text": "Compiler limits met so far",
     "depth": 2
    },
    {
     "id": "legacy-forms-that-are-banned-in-this-repository",
     "text": "Legacy forms that are banned in this repository",
     "depth": 2
    },
    {
     "id": "open-questions-to-verify-by-compiling",
     "text": "Open questions to verify by compiling",
     "depth": 2
    },
    {
     "id": "wgpu-native-behaviour-worth-knowing-verified-2026-11-08",
     "text": "wgpu-native behaviour worth knowing (verified 2026-11-08)",
     "depth": 2
    },
    {
     "id": "more-lifetime-pitfalls-seen-in-phase-4-verified-2026-11-08",
     "text": "More lifetime pitfalls seen in Phase 4 (verified 2026-11-08)",
     "depth": 2
    },
    {
     "id": "pitfalls-seen-in-phase-6-verified-2026-11-09",
     "text": "Pitfalls seen in Phase 6 (verified 2026-11-09)",
     "depth": 2
    },
    {
     "id": "pitfalls-seen-in-phase-7-verified-2026-11-09",
     "text": "Pitfalls seen in Phase 7 (verified 2026-11-09)",
     "depth": 2
    },
    {
     "id": "allocation-facts-measured-in-phase-8-verified-2026-11-09-with-libcinder_alloccount",
     "text": "Allocation facts measured in Phase 8 (verified 2026-11-09 with libcinder_alloccount)",
     "depth": 2
    },
    {
     "id": "phase-9-defect-sweep",
     "text": "Phase 9 (defect sweep)",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/toolchain/",
   "md": "/docs/toolchain.md",
   "title": "Toolchain",
   "section": "Engine design",
   "source": "docs/TOOLCHAIN.md",
   "summary": "Every version below is pinned. Changing one requires an ADR and a green CI run.",
   "headings": [
    {
     "id": "mojo",
     "text": "Mojo",
     "depth": 2
    },
    {
     "id": "environment-and-native-build",
     "text": "Environment and native build",
     "depth": 2
    },
    {
     "id": "development-host",
     "text": "Development host",
     "depth": 2
    },
    {
     "id": "third-party-sources",
     "text": "Third-party sources",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/render-validation/",
   "md": "/docs/render-validation.md",
   "title": "Render validation",
   "section": "Engine design",
   "source": "docs/RENDER_VALIDATION.md",
   "summary": "Golden-image tests (tests/golden/test_golden_gltf.mojo) render Khronos glTF-Sample-Assets models headless and compare them with committed references per platform. This file records how the references were produced and reviewed, and the tolerances.",
   "headings": [
    {
     "id": "setup",
     "text": "Setup",
     "depth": 2
    },
    {
     "id": "tolerances",
     "text": "Tolerances",
     "depth": 2
    },
    {
     "id": "review-of-the-linux-lavapipe-references",
     "text": "Review of the Linux (lavapipe) references",
     "depth": 2
    },
    {
     "id": "macos-metal",
     "text": "macOS (Metal)",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/benchmarks/",
   "md": "/docs/benchmarks.md",
   "title": "Benchmarks",
   "section": "Engine design",
   "source": "docs/BENCHMARKS.md",
   "summary": "How Cinder measures performance, what the numbers mean, and how regressions are caught. The measured results for each run live in REPORT.md (section 4); this page is the method.",
   "headings": [
    {
     "id": "programs",
     "text": "Programs",
     "depth": 2
    },
    {
     "id": "what-is-measured",
     "text": "What is measured",
     "depth": 2
    },
    {
     "id": "budgets-section-8-of-the-brief",
     "text": "Budgets (section 8 of the brief)",
     "depth": 2
    },
    {
     "id": "regression-checking",
     "text": "Regression checking",
     "depth": 2
    },
    {
     "id": "counting-allocations",
     "text": "Counting allocations",
     "depth": 2
    },
    {
     "id": "interpreting-a-run-on-lavapipe",
     "text": "Interpreting a run on lavapipe",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/",
   "md": "/docs/adr.md",
   "title": "Architecture decision records",
   "section": "Decisions",
   "source": null,
   "summary": "Every significant build-versus-reuse, layering and deviation decision, with context and consequences. Deviations from the original brief each point to one of these.",
   "headings": []
  },
  {
   "path": "/docs/adr/0001-dependency-stack/",
   "md": "/docs/adr/0001-dependency-stack.md",
   "title": "ADR-0001: Build-versus-reuse decisions for the dependency stack",
   "section": "Decisions",
   "source": "docs/adr/0001-dependency-stack.md",
   "summary": "Status: Accepted, 2026-11-08",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "decisions",
     "text": "Decisions",
     "depth": 2
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0002-no-max-gpu/",
   "md": "/docs/adr/0002-no-max-gpu.md",
   "title": "ADR-0002: No MAX / max.gpu for rendering; GPU compute is WGSL",
   "section": "Decisions",
   "source": "docs/adr/0002-no-max-gpu.md",
   "summary": "Status: Accepted, 2026-11-08",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "decision",
     "text": "Decision",
     "depth": 2
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0003-native-shim-pull-model/",
   "md": "/docs/adr/0003-native-shim-pull-model.md",
   "title": "ADR-0003: One C11 shim owning every callback; Mojo pulls events",
   "section": "Decisions",
   "source": "docs/adr/0003-native-shim-pull-model.md",
   "summary": "Status: Accepted, 2026-11-08 (callback-in-Mojo question deferred to spike 4)",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "decision",
     "text": "Decision",
     "depth": 2
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    },
    {
     "id": "amendments-2026-11-08-after-spikes-1-2-and-4",
     "text": "Amendments (2026-11-08, after spikes 1, 2 and 4)",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0004-wgpu-native-build/",
   "md": "/docs/adr/0004-wgpu-native-build.md",
   "title": "ADR-0004: Building wgpu-native from source through CMake",
   "section": "Decisions",
   "source": "docs/adr/0004-wgpu-native-build.md",
   "summary": "Status: Accepted, 2026-11-08",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "decision",
     "text": "Decision",
     "depth": 2
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0005-bindings-generation/",
   "md": "/docs/adr/0005-bindings-generation.md",
   "title": "ADR-0005: Generating the Mojo bindings",
   "section": "Decisions",
   "source": "docs/adr/0005-bindings-generation.md",
   "summary": "Status: Accepted, 2026-11-08 (decided by spike 9; supersedes the \"Proposed\" version of the same day)",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "evidence-gathered-in-spike-9-2026-11-08-pinned-toolchain",
     "text": "Evidence gathered in spike 9 (2026-11-08, pinned toolchain)",
     "depth": 2
    },
    {
     "id": "decision",
     "text": "Decision",
     "depth": 2
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    },
    {
     "id": "amendment-2026-11-08-compile-time-cost",
     "text": "Amendment (2026-11-08): compile-time cost",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0006-no-fork-of-stargine/",
   "md": "/docs/adr/0006-no-fork-of-stargine.md",
   "title": "ADR-0006: Start from scratch rather than fork stargine",
   "section": "Decisions",
   "source": "docs/adr/0006-no-fork-of-stargine.md",
   "summary": "Status: Accepted, 2026-11-08",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "decision",
     "text": "Decision",
     "depth": 2
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0007-dev-environment-container/",
   "md": "/docs/adr/0007-dev-environment-container.md",
   "title": "ADR-0007: Development host is a Linux container; Windows host is a file server",
   "section": "Decisions",
   "source": "docs/adr/0007-dev-environment-container.md",
   "summary": "Status: Accepted, 2026-11-08",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "decision",
     "text": "Decision",
     "depth": 2
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0008-job-system-threads/",
   "md": "/docs/adr/0008-job-system-threads.md",
   "title": "ADR-0008: Job system scheduling in Mojo, threads and parking from the shim",
   "section": "Decisions",
   "source": "docs/adr/0008-job-system-threads.md",
   "summary": "Status: Accepted, 2026-11-08",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "decision",
     "text": "Decision",
     "depth": 2
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0009-gfx-layer/",
   "md": "/docs/adr/0009-gfx-layer.md",
   "title": "ADR-0009: Graphics layer shape (typed handles, error scopes for shader diagnostics)",
   "section": "Decisions",
   "source": "docs/adr/0009-gfx-layer.md",
   "summary": "Status: accepted, 2026-11-08.",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "decisions",
     "text": "Decisions",
     "depth": 2
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0010-renderer/",
   "md": "/docs/adr/0010-renderer.md",
   "title": "ADR-0010: Renderer architecture (forward+, frame graph, shader assembly)",
   "section": "Decisions",
   "source": "docs/adr/0010-renderer.md",
   "summary": "Status: accepted, 2026-11-08.",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "decisions",
     "text": "Decisions",
     "depth": 2
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0011-ecs-mojo-vs-flecs/",
   "md": "/docs/adr/0011-ecs-mojo-vs-flecs.md",
   "title": "ADR-0011: Keep the Mojo archetype ECS (benchmarked against flecs)",
   "section": "Decisions",
   "source": "docs/adr/0011-ecs-mojo-vs-flecs.md",
   "summary": "Status: accepted, 2026-11-08.",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "benchmark",
     "text": "Benchmark",
     "depth": 2
    },
    {
     "id": "decision",
     "text": "Decision",
     "depth": 2
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0012-physics-animation-audio-input/",
   "md": "/docs/adr/0012-physics-animation-audio-input.md",
   "title": "ADR-0012: Phase 6 subsystems: physics, animation, audio and input",
   "section": "Decisions",
   "source": "docs/adr/0012-physics-animation-audio-input.md",
   "summary": "Status: accepted, 2026-11-09.",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "decisions",
     "text": "Decisions",
     "depth": 2
    },
    {
     "id": "physics-cinderphysics",
     "text": "Physics (cinder/physics)",
     "depth": 3
    },
    {
     "id": "animation-cinderanim",
     "text": "Animation (cinder/anim)",
     "depth": 3
    },
    {
     "id": "audio-cinderaudio",
     "text": "Audio (cinder/audio)",
     "depth": 3
    },
    {
     "id": "input-cinderinput",
     "text": "Input (cinder/input)",
     "depth": 3
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0013-tools-and-app-runtime/",
   "md": "/docs/adr/0013-tools-and-app-runtime.md",
   "title": "ADR-0013: Tools and the application runtime (Phase 7)",
   "section": "Decisions",
   "source": "docs/adr/0013-tools-and-app-runtime.md",
   "summary": "Status: accepted, 2026-11-09.",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "decisions",
     "text": "Decisions",
     "depth": 2
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/adr/0014-sample-game-and-performance/",
   "md": "/docs/adr/0014-sample-game-and-performance.md",
   "title": "ADR-0014: Sample game, benchmarks and the zero-allocation frame (Phase 8)",
   "section": "Decisions",
   "source": "docs/adr/0014-sample-game-and-performance.md",
   "summary": "Status: accepted, 2026-11-09.",
   "headings": [
    {
     "id": "context",
     "text": "Context",
     "depth": 2
    },
    {
     "id": "decisions",
     "text": "Decisions",
     "depth": 2
    },
    {
     "id": "sample-game-sample",
     "text": "Sample game (sample/)",
     "depth": 3
    },
    {
     "id": "benchmarks-bench",
     "text": "Benchmarks (bench/)",
     "depth": 3
    },
    {
     "id": "zero-allocations-per-frame",
     "text": "Zero allocations per frame",
     "depth": 3
    },
    {
     "id": "consequences",
     "text": "Consequences",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/api/",
   "md": "/docs/api.md",
   "title": "API reference",
   "section": "API reference",
   "source": "docs/api/README.md",
   "summary": "Generated by tools/gen_api_docs.py from the docstrings in cinder/; do not edit by hand.",
   "headings": [
    {
     "id": "cinderanim",
     "text": "cinder.anim",
     "depth": 2
    },
    {
     "id": "cinderapp",
     "text": "cinder.app",
     "depth": 2
    },
    {
     "id": "cinderassets",
     "text": "cinder.assets",
     "depth": 2
    },
    {
     "id": "cinderaudio",
     "text": "cinder.audio",
     "depth": 2
    },
    {
     "id": "cindercore",
     "text": "cinder.core",
     "depth": 2
    },
    {
     "id": "cinderecs",
     "text": "cinder.ecs",
     "depth": 2
    },
    {
     "id": "cindergfx",
     "text": "cinder.gfx",
     "depth": 2
    },
    {
     "id": "cinderinput",
     "text": "cinder.input",
     "depth": 2
    },
    {
     "id": "cinderphysics",
     "text": "cinder.physics",
     "depth": 2
    },
    {
     "id": "cinderplatform",
     "text": "cinder.platform",
     "depth": 2
    },
    {
     "id": "cinderrender",
     "text": "cinder.render",
     "depth": 2
    },
    {
     "id": "cinderscene",
     "text": "cinder.scene",
     "depth": 2
    },
    {
     "id": "cindertools",
     "text": "cinder.tools",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/api/anim/",
   "md": "/docs/api/anim.md",
   "title": "cinder.anim API",
   "section": "API reference",
   "source": "docs/api/anim.md",
   "summary": "Source: cinder/anim/__init__.mojo",
   "headings": [
    {
     "id": "cinderanim-1",
     "text": "cinder.anim",
     "depth": 2
    },
    {
     "id": "cinderanimanimator",
     "text": "cinder.anim.animator",
     "depth": 2
    },
    {
     "id": "struct-animationevent",
     "text": "struct AnimationEvent",
     "depth": 3
    },
    {
     "id": "struct-animationstate",
     "text": "struct AnimationState",
     "depth": 3
    },
    {
     "id": "struct-animator",
     "text": "struct Animator",
     "depth": 3
    },
    {
     "id": "cinderanimblend",
     "text": "cinder.anim.blend",
     "depth": 2
    },
    {
     "id": "struct-blendnode",
     "text": "struct BlendNode",
     "depth": 3
    },
    {
     "id": "struct-blendtree",
     "text": "struct BlendTree",
     "depth": 3
    },
    {
     "id": "cinderanimsampling",
     "text": "cinder.anim.sampling",
     "depth": 2
    },
    {
     "id": "struct-pose",
     "text": "struct Pose",
     "depth": 3
    },
    {
     "id": "def-sample_component",
     "text": "def sample_component",
     "depth": 3
    },
    {
     "id": "def-sample_rotation",
     "text": "def sample_rotation",
     "depth": 3
    },
    {
     "id": "def-sample_clip",
     "text": "def sample_clip",
     "depth": 3
    },
    {
     "id": "def-wrap_time",
     "text": "def wrap_time",
     "depth": 3
    },
    {
     "id": "cinderanimskeleton",
     "text": "cinder.anim.skeleton",
     "depth": 2
    },
    {
     "id": "struct-skeleton",
     "text": "struct Skeleton",
     "depth": 3
    },
    {
     "id": "def-skeleton_from_gltf",
     "text": "def skeleton_from_gltf",
     "depth": 3
    },
    {
     "id": "def-write_skeleton",
     "text": "def write_skeleton",
     "depth": 3
    },
    {
     "id": "def-read_skeleton",
     "text": "def read_skeleton",
     "depth": 3
    },
    {
     "id": "cinderanimsystem",
     "text": "cinder.anim.system",
     "depth": 2
    },
    {
     "id": "struct-animatorref",
     "text": "struct AnimatorRef",
     "depth": 3
    },
    {
     "id": "struct-animationsystem",
     "text": "struct AnimationSystem",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/api/app/",
   "md": "/docs/api/app.md",
   "title": "cinder.app API",
   "section": "API reference",
   "source": "docs/api/app.md",
   "summary": "Source: cinder/app/__init__.mojo",
   "headings": [
    {
     "id": "cinderapp-1",
     "text": "cinder.app",
     "depth": 2
    },
    {
     "id": "cinderappapp",
     "text": "cinder.app.app",
     "depth": 2
    },
    {
     "id": "def-ui_consumes_event",
     "text": "def ui_consumes_event",
     "depth": 3
    },
    {
     "id": "struct-appconfig",
     "text": "struct AppConfig",
     "depth": 3
    },
    {
     "id": "trait-game",
     "text": "trait Game",
     "depth": 3
    },
    {
     "id": "struct-app",
     "text": "struct App",
     "depth": 3
    },
    {
     "id": "cinderappcli",
     "text": "cinder.app.cli",
     "depth": 2
    },
    {
     "id": "def-parse_app_args",
     "text": "def parse_app_args",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/api/assets/",
   "md": "/docs/api/assets.md",
   "title": "cinder.assets API",
   "section": "API reference",
   "source": "docs/api/assets.md",
   "summary": "Source: cinder/assets/__init__.mojo",
   "headings": [
    {
     "id": "cinderassets-1",
     "text": "cinder.assets",
     "depth": 2
    },
    {
     "id": "cinderassetscook",
     "text": "cinder.assets.cook",
     "depth": 2
    },
    {
     "id": "struct-manifestentry",
     "text": "struct ManifestEntry",
     "depth": 3
    },
    {
     "id": "struct-cookmanifest",
     "text": "struct CookManifest",
     "depth": 3
    },
    {
     "id": "struct-cookreport",
     "text": "struct CookReport",
     "depth": 3
    },
    {
     "id": "def-cook_gltf",
     "text": "def cook_gltf",
     "depth": 3
    },
    {
     "id": "cinderassetscooked",
     "text": "cinder.assets.cooked",
     "depth": 2
    },
    {
     "id": "def-asset_id",
     "text": "def asset_id",
     "depth": 3
    },
    {
     "id": "def-asset_file_name",
     "text": "def asset_file_name",
     "depth": 3
    },
    {
     "id": "struct-cookedmesh",
     "text": "struct CookedMesh",
     "depth": 3
    },
    {
     "id": "def-cook_mesh",
     "text": "def cook_mesh",
     "depth": 3
    },
    {
     "id": "def-write_mesh",
     "text": "def write_mesh",
     "depth": 3
    },
    {
     "id": "struct-cursor",
     "text": "struct Cursor",
     "depth": 3
    },
    {
     "id": "def-read_mesh",
     "text": "def read_mesh",
     "depth": 3
    },
    {
     "id": "struct-clipchannel",
     "text": "struct ClipChannel",
     "depth": 3
    },
    {
     "id": "struct-clip",
     "text": "struct Clip",
     "depth": 3
    },
    {
     "id": "def-write_clip",
     "text": "def write_clip",
     "depth": 3
    },
    {
     "id": "def-read_clip",
     "text": "def read_clip",
     "depth": 3
    },
    {
     "id": "struct-cookedmaterial",
     "text": "struct CookedMaterial",
     "depth": 3
    },
    {
     "id": "def-write_material",
     "text": "def write_material",
     "depth": 3
    },
    {
     "id": "def-read_material",
     "text": "def read_material",
     "depth": 3
    },
    {
     "id": "cinderassetsgltf",
     "text": "cinder.assets.gltf",
     "depth": 2
    },
    {
     "id": "struct-gltfimage",
     "text": "struct GltfImage",
     "depth": 3
    },
    {
     "id": "struct-gltftexture",
     "text": "struct GltfTexture",
     "depth": 3
    },
    {
     "id": "struct-gltfmaterial",
     "text": "struct GltfMaterial",
     "depth": 3
    },
    {
     "id": "struct-gltfprimitive",
     "text": "struct GltfPrimitive",
     "depth": 3
    },
    {
     "id": "struct-gltfmesh",
     "text": "struct GltfMesh",
     "depth": 3
    },
    {
     "id": "struct-gltfnode",
     "text": "struct GltfNode",
     "depth": 3
    },
    {
     "id": "struct-gltfskin",
     "text": "struct GltfSkin",
     "depth": 3
    },
    {
     "id": "struct-gltfchannel",
     "text": "struct GltfChannel",
     "depth": 3
    },
    {
     "id": "struct-gltfanimation",
     "text": "struct GltfAnimation",
     "depth": 3
    },
    {
     "id": "struct-scenebounds",
     "text": "struct SceneBounds",
     "depth": 3
    },
    {
     "id": "struct-gltfasset",
     "text": "struct GltfAsset",
     "depth": 3
    },
    {
     "id": "def-load_gltf",
     "text": "def load_gltf",
     "depth": 3
    },
    {
     "id": "struct-uploadedgltf",
     "text": "struct UploadedGltf",
     "depth": 3
    },
    {
     "id": "def-upload_gltf",
     "text": "def upload_gltf",
     "depth": 3
    },
    {
     "id": "def-instantiate",
     "text": "def instantiate",
     "depth": 3
    },
    {
     "id": "cinderassetsruntime",
     "text": "cinder.assets.runtime",
     "depth": 2
    },
    {
     "id": "struct-assetstate",
     "text": "struct AssetState",
     "depth": 3
    },
    {
     "id": "struct-assetrecord",
     "text": "struct AssetRecord",
     "depth": 3
    },
    {
     "id": "struct-assetserver",
     "text": "struct AssetServer",
     "depth": 3
    },
    {
     "id": "cinderassetstextures",
     "text": "cinder.assets.textures",
     "depth": 2
    },
    {
     "id": "def-cook_texture_ktx2",
     "text": "def cook_texture_ktx2",
     "depth": 3
    },
    {
     "id": "struct-loadedtexture",
     "text": "struct LoadedTexture",
     "depth": 3
    },
    {
     "id": "def-load_ktx2",
     "text": "def load_ktx2",
     "depth": 3
    },
    {
     "id": "def-upload_loaded",
     "text": "def upload_loaded",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/api/audio/",
   "md": "/docs/api/audio.md",
   "title": "cinder.audio API",
   "section": "API reference",
   "source": "docs/api/audio.md",
   "summary": "Source: cinder/audio/__init__.mojo",
   "headings": [
    {
     "id": "cinderaudio-1",
     "text": "cinder.audio",
     "depth": 2
    },
    {
     "id": "cinderaudioengine",
     "text": "cinder.audio.engine",
     "depth": 2
    },
    {
     "id": "struct-soundhandle",
     "text": "struct SoundHandle",
     "depth": 3
    },
    {
     "id": "struct-attenuation",
     "text": "struct Attenuation",
     "depth": 3
    },
    {
     "id": "struct-sounddesc",
     "text": "struct SoundDesc",
     "depth": 3
    },
    {
     "id": "struct-audioengine",
     "text": "struct AudioEngine",
     "depth": 3
    },
    {
     "id": "cinderaudiosync",
     "text": "cinder.audio.sync",
     "depth": 2
    },
    {
     "id": "struct-audiosource",
     "text": "struct AudioSource",
     "depth": 3
    },
    {
     "id": "struct-audiolistener",
     "text": "struct AudioListener",
     "depth": 3
    },
    {
     "id": "def-sync_audio",
     "text": "def sync_audio",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/api/core/",
   "md": "/docs/api/core.md",
   "title": "cinder.core API",
   "section": "API reference",
   "source": "docs/api/core.md",
   "summary": "Source: cinder/core/__init__.mojo",
   "headings": [
    {
     "id": "cindercore-1",
     "text": "cinder.core",
     "depth": 2
    },
    {
     "id": "cindercorearena",
     "text": "cinder.core.arena",
     "depth": 2
    },
    {
     "id": "struct-lineararena",
     "text": "struct LinearArena",
     "depth": 3
    },
    {
     "id": "cindercoreassertions",
     "text": "cinder.core.assertions",
     "depth": 2
    },
    {
     "id": "def-cinder_assert",
     "text": "def cinder_assert",
     "depth": 3
    },
    {
     "id": "def-cinder_check",
     "text": "def cinder_check",
     "depth": 3
    },
    {
     "id": "cindercorebase64",
     "text": "cinder.core.base64",
     "depth": 2
    },
    {
     "id": "def-decode_base64",
     "text": "def decode_base64",
     "depth": 3
    },
    {
     "id": "cindercoreboxed",
     "text": "cinder.core.boxed",
     "depth": 2
    },
    {
     "id": "struct-boxed",
     "text": "struct Boxed",
     "depth": 3
    },
    {
     "id": "cindercorebytes",
     "text": "cinder.core.bytes",
     "depth": 2
    },
    {
     "id": "struct-bytewriter",
     "text": "struct ByteWriter",
     "depth": 3
    },
    {
     "id": "cindercorecstring",
     "text": "cinder.core.cstring",
     "depth": 2
    },
    {
     "id": "def-string_from_c",
     "text": "def string_from_c",
     "depth": 3
    },
    {
     "id": "cindercorefs",
     "text": "cinder.core.fs",
     "depth": 2
    },
    {
     "id": "struct-fileerror",
     "text": "struct FileError",
     "depth": 3
    },
    {
     "id": "def-file_exists",
     "text": "def file_exists",
     "depth": 3
    },
    {
     "id": "def-read_bytes",
     "text": "def read_bytes",
     "depth": 3
    },
    {
     "id": "def-read_text",
     "text": "def read_text",
     "depth": 3
    },
    {
     "id": "def-write_bytes",
     "text": "def write_bytes",
     "depth": 3
    },
    {
     "id": "def-write_text",
     "text": "def write_text",
     "depth": 3
    },
    {
     "id": "cindercorehandles",
     "text": "cinder.core.handles",
     "depth": 2
    },
    {
     "id": "struct-handle",
     "text": "struct Handle",
     "depth": 3
    },
    {
     "id": "struct-pool",
     "text": "struct Pool",
     "depth": 3
    },
    {
     "id": "cindercorehash",
     "text": "cinder.core.hash",
     "depth": 2
    },
    {
     "id": "def-fnv1a64",
     "text": "def fnv1a64",
     "depth": 3
    },
    {
     "id": "def-fnv1a64_string",
     "text": "def fnv1a64_string",
     "depth": 3
    },
    {
     "id": "def-hex64",
     "text": "def hex64",
     "depth": 3
    },
    {
     "id": "cindercoreimage",
     "text": "cinder.core.image",
     "depth": 2
    },
    {
     "id": "struct-image",
     "text": "struct Image",
     "depth": 3
    },
    {
     "id": "def-load_image",
     "text": "def load_image",
     "depth": 3
    },
    {
     "id": "def-decode_image",
     "text": "def decode_image",
     "depth": 3
    },
    {
     "id": "def-save_png",
     "text": "def save_png",
     "depth": 3
    },
    {
     "id": "struct-imagediff",
     "text": "struct ImageDiff",
     "depth": 3
    },
    {
     "id": "def-compare",
     "text": "def compare",
     "depth": 3
    },
    {
     "id": "cindercorejobs",
     "text": "cinder.core.jobs",
     "depth": 2
    },
    {
     "id": "struct-counter",
     "text": "struct Counter",
     "depth": 3
    },
    {
     "id": "struct-job",
     "text": "struct Job",
     "depth": 3
    },
    {
     "id": "struct-deque",
     "text": "struct Deque",
     "depth": 3
    },
    {
     "id": "struct-shared",
     "text": "struct Shared",
     "depth": 3
    },
    {
     "id": "struct-workercontext",
     "text": "struct WorkerContext",
     "depth": 3
    },
    {
     "id": "struct-jobsystem",
     "text": "struct JobSystem",
     "depth": 3
    },
    {
     "id": "cindercorelog",
     "text": "cinder.core.log",
     "depth": 2
    },
    {
     "id": "struct-loglevel",
     "text": "struct LogLevel",
     "depth": 3
    },
    {
     "id": "struct-logfield",
     "text": "struct LogField",
     "depth": 3
    },
    {
     "id": "struct-logrecord",
     "text": "struct LogRecord",
     "depth": 3
    },
    {
     "id": "trait-logsink",
     "text": "trait LogSink",
     "depth": 3
    },
    {
     "id": "struct-printsink",
     "text": "struct PrintSink",
     "depth": 3
    },
    {
     "id": "struct-memorysink",
     "text": "struct MemorySink",
     "depth": 3
    },
    {
     "id": "struct-logger",
     "text": "struct Logger",
     "depth": 3
    },
    {
     "id": "cindercoremath",
     "text": "cinder.core.math",
     "depth": 2
    },
    {
     "id": "cindercoremathmat4",
     "text": "cinder.core.math.mat4",
     "depth": 2
    },
    {
     "id": "struct-mat4",
     "text": "struct Mat4",
     "depth": 3
    },
    {
     "id": "cindercoremathquat",
     "text": "cinder.core.math.quat",
     "depth": 2
    },
    {
     "id": "struct-quat",
     "text": "struct Quat",
     "depth": 3
    },
    {
     "id": "cindercoremathscalar",
     "text": "cinder.core.math.scalar",
     "depth": 2
    },
    {
     "id": "def-radians",
     "text": "def radians",
     "depth": 3
    },
    {
     "id": "def-degrees",
     "text": "def degrees",
     "depth": 3
    },
    {
     "id": "def-clamp",
     "text": "def clamp",
     "depth": 3
    },
    {
     "id": "def-saturate",
     "text": "def saturate",
     "depth": 3
    },
    {
     "id": "def-lerp",
     "text": "def lerp",
     "depth": 3
    },
    {
     "id": "def-approx_eq",
     "text": "def approx_eq",
     "depth": 3
    },
    {
     "id": "cindercoremathtransform",
     "text": "cinder.core.math.transform",
     "depth": 2
    },
    {
     "id": "struct-transform",
     "text": "struct Transform",
     "depth": 3
    },
    {
     "id": "cindercoremathvec",
     "text": "cinder.core.math.vec",
     "depth": 2
    },
    {
     "id": "struct-vec2",
     "text": "struct Vec2",
     "depth": 3
    },
    {
     "id": "struct-vec3",
     "text": "struct Vec3",
     "depth": 3
    },
    {
     "id": "struct-vec4",
     "text": "struct Vec4",
     "depth": 3
    },
    {
     "id": "cindercoreprofile",
     "text": "cinder.core.profile",
     "depth": 2
    },
    {
     "id": "struct-profiler",
     "text": "struct Profiler",
     "depth": 3
    },
    {
     "id": "struct-zone",
     "text": "struct Zone",
     "depth": 3
    },
    {
     "id": "cindercorering",
     "text": "cinder.core.ring",
     "depth": 2
    },
    {
     "id": "struct-ringbuffer",
     "text": "struct RingBuffer",
     "depth": 3
    },
    {
     "id": "cindercoretime",
     "text": "cinder.core.time",
     "depth": 2
    },
    {
     "id": "struct-clock",
     "text": "struct Clock",
     "depth": 3
    },
    {
     "id": "struct-fixedstep",
     "text": "struct FixedStep",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/api/ecs/",
   "md": "/docs/api/ecs.md",
   "title": "cinder.ecs API",
   "section": "API reference",
   "source": "docs/api/ecs.md",
   "summary": "Source: cinder/ecs/__init__.mojo",
   "headings": [
    {
     "id": "cinderecs-1",
     "text": "cinder.ecs",
     "depth": 2
    },
    {
     "id": "cinderecscommands",
     "text": "cinder.ecs.commands",
     "depth": 2
    },
    {
     "id": "struct-commandbuffer",
     "text": "struct CommandBuffer",
     "depth": 3
    },
    {
     "id": "cinderecshierarchy",
     "text": "cinder.ecs.hierarchy",
     "depth": 2
    },
    {
     "id": "struct-parent",
     "text": "struct Parent",
     "depth": 3
    },
    {
     "id": "struct-localtransform",
     "text": "struct LocalTransform",
     "depth": 3
    },
    {
     "id": "struct-worldtransform",
     "text": "struct WorldTransform",
     "depth": 3
    },
    {
     "id": "def-propagate_transforms",
     "text": "def propagate_transforms",
     "depth": 3
    },
    {
     "id": "cinderecsschedule",
     "text": "cinder.ecs.schedule",
     "depth": 2
    },
    {
     "id": "struct-systemdesc",
     "text": "struct SystemDesc",
     "depth": 3
    },
    {
     "id": "struct-schedule",
     "text": "struct Schedule",
     "depth": 3
    },
    {
     "id": "cinderecsworld",
     "text": "cinder.ecs.world",
     "depth": 2
    },
    {
     "id": "trait-component",
     "text": "trait Component",
     "depth": 3
    },
    {
     "id": "struct-entity",
     "text": "struct Entity",
     "depth": 3
    },
    {
     "id": "def-component_stride",
     "text": "def component_stride",
     "depth": 3
    },
    {
     "id": "struct-componentinfo",
     "text": "struct ComponentInfo",
     "depth": 3
    },
    {
     "id": "struct-column",
     "text": "struct Column",
     "depth": 3
    },
    {
     "id": "struct-archetype",
     "text": "struct Archetype",
     "depth": 3
    },
    {
     "id": "struct-world",
     "text": "struct World",
     "depth": 3
    },
    {
     "id": "def-pass_through",
     "text": "def pass_through",
     "depth": 3
    },
    {
     "id": "struct-chunk",
     "text": "struct Chunk",
     "depth": 3
    },
    {
     "id": "struct-queryspec",
     "text": "struct QuerySpec",
     "depth": 3
    },
    {
     "id": "struct-query",
     "text": "struct Query",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/api/gfx/",
   "md": "/docs/api/gfx.md",
   "title": "cinder.gfx API",
   "section": "API reference",
   "source": "docs/api/gfx.md",
   "summary": "Source: cinder/gfx/__init__.mojo",
   "headings": [
    {
     "id": "cindergfx-1",
     "text": "cinder.gfx",
     "depth": 2
    },
    {
     "id": "cindergfxcommands",
     "text": "cinder.gfx.commands",
     "depth": 2
    },
    {
     "id": "struct-colorattachment",
     "text": "struct ColorAttachment",
     "depth": 3
    },
    {
     "id": "struct-depthattachment",
     "text": "struct DepthAttachment",
     "depth": 3
    },
    {
     "id": "struct-renderpass",
     "text": "struct RenderPass",
     "depth": 3
    },
    {
     "id": "struct-computepass",
     "text": "struct ComputePass",
     "depth": 3
    },
    {
     "id": "def-command_encoder_descriptor",
     "text": "def command_encoder_descriptor",
     "depth": 3
    },
    {
     "id": "struct-commandencoder",
     "text": "struct CommandEncoder",
     "depth": 3
    },
    {
     "id": "def-wait_for_queue",
     "text": "def wait_for_queue",
     "depth": 3
    },
    {
     "id": "def-read_buffer",
     "text": "def read_buffer",
     "depth": 3
    },
    {
     "id": "cindergfxdebug_draw",
     "text": "cinder.gfx.debug_draw",
     "depth": 2
    },
    {
     "id": "struct-color8",
     "text": "struct Color8",
     "depth": 3
    },
    {
     "id": "struct-debugdraw",
     "text": "struct DebugDraw",
     "depth": 3
    },
    {
     "id": "cindergfxdevice",
     "text": "cinder.gfx.device",
     "depth": 2
    },
    {
     "id": "struct-gfxerror",
     "text": "struct GfxError",
     "depth": 3
    },
    {
     "id": "struct-gfx",
     "text": "struct Gfx",
     "depth": 3
    },
    {
     "id": "cindergfxpipeline",
     "text": "cinder.gfx.pipeline",
     "depth": 2
    },
    {
     "id": "struct-bindingkind",
     "text": "struct BindingKind",
     "depth": 3
    },
    {
     "id": "struct-layoutentry",
     "text": "struct LayoutEntry",
     "depth": 3
    },
    {
     "id": "struct-bindingresource",
     "text": "struct BindingResource",
     "depth": 3
    },
    {
     "id": "struct-vertexattribute",
     "text": "struct VertexAttribute",
     "depth": 3
    },
    {
     "id": "struct-vertexlayout",
     "text": "struct VertexLayout",
     "depth": 3
    },
    {
     "id": "struct-depthstate",
     "text": "struct DepthState",
     "depth": 3
    },
    {
     "id": "struct-blendmode",
     "text": "struct BlendMode",
     "depth": 3
    },
    {
     "id": "struct-colortarget",
     "text": "struct ColorTarget",
     "depth": 3
    },
    {
     "id": "struct-renderpipelinedesc",
     "text": "struct RenderPipelineDesc",
     "depth": 3
    },
    {
     "id": "def-create_bind_group_layout",
     "text": "def create_bind_group_layout",
     "depth": 3
    },
    {
     "id": "def-create_pipeline_layout",
     "text": "def create_pipeline_layout",
     "depth": 3
    },
    {
     "id": "def-create_bind_group",
     "text": "def create_bind_group",
     "depth": 3
    },
    {
     "id": "def-build_render_pipeline",
     "text": "def build_render_pipeline",
     "depth": 3
    },
    {
     "id": "def-create_render_pipeline",
     "text": "def create_render_pipeline",
     "depth": 3
    },
    {
     "id": "def-build_compute_pipeline",
     "text": "def build_compute_pipeline",
     "depth": 3
    },
    {
     "id": "def-create_compute_pipeline",
     "text": "def create_compute_pipeline",
     "depth": 3
    },
    {
     "id": "cindergfxresources",
     "text": "cinder.gfx.resources",
     "depth": 2
    },
    {
     "id": "struct-buffertag",
     "text": "struct BufferTag",
     "depth": 3
    },
    {
     "id": "struct-texturetag",
     "text": "struct TextureTag",
     "depth": 3
    },
    {
     "id": "struct-textureviewtag",
     "text": "struct TextureViewTag",
     "depth": 3
    },
    {
     "id": "struct-samplertag",
     "text": "struct SamplerTag",
     "depth": 3
    },
    {
     "id": "struct-shadertag",
     "text": "struct ShaderTag",
     "depth": 3
    },
    {
     "id": "struct-bindgrouplayouttag",
     "text": "struct BindGroupLayoutTag",
     "depth": 3
    },
    {
     "id": "struct-pipelinelayouttag",
     "text": "struct PipelineLayoutTag",
     "depth": 3
    },
    {
     "id": "struct-bindgrouptag",
     "text": "struct BindGroupTag",
     "depth": 3
    },
    {
     "id": "struct-renderpipelinetag",
     "text": "struct RenderPipelineTag",
     "depth": 3
    },
    {
     "id": "struct-computepipelinetag",
     "text": "struct ComputePipelineTag",
     "depth": 3
    },
    {
     "id": "struct-bufferdesc",
     "text": "struct BufferDesc",
     "depth": 3
    },
    {
     "id": "struct-texturedesc",
     "text": "struct TextureDesc",
     "depth": 3
    },
    {
     "id": "struct-samplerdesc",
     "text": "struct SamplerDesc",
     "depth": 3
    },
    {
     "id": "struct-bufferrecord",
     "text": "struct BufferRecord",
     "depth": 3
    },
    {
     "id": "struct-texturerecord",
     "text": "struct TextureRecord",
     "depth": 3
    },
    {
     "id": "struct-textureviewrecord",
     "text": "struct TextureViewRecord",
     "depth": 3
    },
    {
     "id": "struct-samplerrecord",
     "text": "struct SamplerRecord",
     "depth": 3
    },
    {
     "id": "struct-shaderrecord",
     "text": "struct ShaderRecord",
     "depth": 3
    },
    {
     "id": "struct-bindgrouplayoutrecord",
     "text": "struct BindGroupLayoutRecord",
     "depth": 3
    },
    {
     "id": "struct-pipelinelayoutrecord",
     "text": "struct PipelineLayoutRecord",
     "depth": 3
    },
    {
     "id": "struct-bindgrouprecord",
     "text": "struct BindGroupRecord",
     "depth": 3
    },
    {
     "id": "struct-renderpipelinerecord",
     "text": "struct RenderPipelineRecord",
     "depth": 3
    },
    {
     "id": "struct-computepipelinerecord",
     "text": "struct ComputePipelineRecord",
     "depth": 3
    },
    {
     "id": "struct-livecounts",
     "text": "struct LiveCounts",
     "depth": 3
    },
    {
     "id": "struct-resources",
     "text": "struct Resources",
     "depth": 3
    },
    {
     "id": "cindergfxshaders",
     "text": "cinder.gfx.shaders",
     "depth": 2
    },
    {
     "id": "struct-shadermessage",
     "text": "struct ShaderMessage",
     "depth": 3
    },
    {
     "id": "struct-shadererror",
     "text": "struct ShaderError",
     "depth": 3
    },
    {
     "id": "struct-shadersource",
     "text": "struct ShaderSource",
     "depth": 3
    },
    {
     "id": "struct-reloadresult",
     "text": "struct ReloadResult",
     "depth": 3
    },
    {
     "id": "def-parse_wgsl_report",
     "text": "def parse_wgsl_report",
     "depth": 3
    },
    {
     "id": "struct-shadermanager",
     "text": "struct ShaderManager",
     "depth": 3
    },
    {
     "id": "cindergfxswapchain",
     "text": "cinder.gfx.swapchain",
     "depth": 2
    },
    {
     "id": "struct-surfaceframe",
     "text": "struct SurfaceFrame",
     "depth": 3
    },
    {
     "id": "struct-swapchain",
     "text": "struct Swapchain",
     "depth": 3
    },
    {
     "id": "cindergfxutil",
     "text": "cinder.gfx.util",
     "depth": 2
    },
    {
     "id": "def-string_view",
     "text": "def string_view",
     "depth": 3
    },
    {
     "id": "def-empty_string_view",
     "text": "def empty_string_view",
     "depth": 3
    },
    {
     "id": "def-c_message",
     "text": "def c_message",
     "depth": 3
    },
    {
     "id": "def-zero_event",
     "text": "def zero_event",
     "depth": 3
    },
    {
     "id": "def-ptr_to",
     "text": "def ptr_to",
     "depth": 3
    },
    {
     "id": "def-opaque_to",
     "text": "def opaque_to",
     "depth": 3
    },
    {
     "id": "def-handle_from",
     "text": "def handle_from",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/api/input/",
   "md": "/docs/api/input.md",
   "title": "cinder.input API",
   "section": "API reference",
   "source": "docs/api/input.md",
   "summary": "Source: cinder/input/__init__.mojo",
   "headings": [
    {
     "id": "cinderinput-1",
     "text": "cinder.input",
     "depth": 2
    },
    {
     "id": "cinderinputmap",
     "text": "cinder.input.map",
     "depth": 2
    },
    {
     "id": "struct-binding",
     "text": "struct Binding",
     "depth": 3
    },
    {
     "id": "struct-inputmap",
     "text": "struct InputMap",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/api/physics/",
   "md": "/docs/api/physics.md",
   "title": "cinder.physics API",
   "section": "API reference",
   "source": "docs/api/physics.md",
   "summary": "Source: cinder/physics/__init__.mojo",
   "headings": [
    {
     "id": "cinderphysics-1",
     "text": "cinder.physics",
     "depth": 2
    },
    {
     "id": "cinderphysicscharacter",
     "text": "cinder.physics.character",
     "depth": 2
    },
    {
     "id": "struct-groundstate",
     "text": "struct GroundState",
     "depth": 3
    },
    {
     "id": "struct-characterdesc",
     "text": "struct CharacterDesc",
     "depth": 3
    },
    {
     "id": "struct-charactercontroller",
     "text": "struct CharacterController",
     "depth": 3
    },
    {
     "id": "cinderphysicssync",
     "text": "cinder.physics.sync",
     "depth": 2
    },
    {
     "id": "struct-rigidbody",
     "text": "struct RigidBody",
     "depth": 3
    },
    {
     "id": "struct-physicssync",
     "text": "struct PhysicsSync",
     "depth": 3
    },
    {
     "id": "def-pull_bodies",
     "text": "def pull_bodies",
     "depth": 3
    },
    {
     "id": "def-push_kinematics",
     "text": "def push_kinematics",
     "depth": 3
    },
    {
     "id": "def-write_transforms",
     "text": "def write_transforms",
     "depth": 3
    },
    {
     "id": "cinderphysicsworld",
     "text": "cinder.physics.world",
     "depth": 2
    },
    {
     "id": "def-to_jolt",
     "text": "def to_jolt",
     "depth": 3
    },
    {
     "id": "def-from_jolt",
     "text": "def from_jolt",
     "depth": 3
    },
    {
     "id": "def-quat_to_jolt",
     "text": "def quat_to_jolt",
     "depth": 3
    },
    {
     "id": "def-quat_from_jolt",
     "text": "def quat_from_jolt",
     "depth": 3
    },
    {
     "id": "def-mat_to_jolt",
     "text": "def mat_to_jolt",
     "depth": 3
    },
    {
     "id": "struct-layerconfig",
     "text": "struct LayerConfig",
     "depth": 3
    },
    {
     "id": "struct-motiontype",
     "text": "struct MotionType",
     "depth": 3
    },
    {
     "id": "struct-shape",
     "text": "struct Shape",
     "depth": 3
    },
    {
     "id": "struct-bodydesc",
     "text": "struct BodyDesc",
     "depth": 3
    },
    {
     "id": "struct-physicseventkind",
     "text": "struct PhysicsEventKind",
     "depth": 3
    },
    {
     "id": "struct-physicsevent",
     "text": "struct PhysicsEvent",
     "depth": 3
    },
    {
     "id": "struct-rayhit",
     "text": "struct RayHit",
     "depth": 3
    },
    {
     "id": "struct-shapehit",
     "text": "struct ShapeHit",
     "depth": 3
    },
    {
     "id": "struct-physicsworld",
     "text": "struct PhysicsWorld",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/api/platform/",
   "md": "/docs/api/platform.md",
   "title": "cinder.platform API",
   "section": "API reference",
   "source": "docs/api/platform.md",
   "summary": "Source: cinder/platform/__init__.mojo",
   "headings": [
    {
     "id": "cinderplatform-1",
     "text": "cinder.platform",
     "depth": 2
    },
    {
     "id": "cinderplatformevents",
     "text": "cinder.platform.events",
     "depth": 2
    },
    {
     "id": "struct-eventkind",
     "text": "struct EventKind",
     "depth": 3
    },
    {
     "id": "struct-event",
     "text": "struct Event",
     "depth": 3
    },
    {
     "id": "def-translate_event",
     "text": "def translate_event",
     "depth": 3
    },
    {
     "id": "cinderplatformnative",
     "text": "cinder.platform.native",
     "depth": 2
    },
    {
     "id": "def-default_library_path",
     "text": "def default_library_path",
     "depth": 3
    },
    {
     "id": "struct-nativelibrary",
     "text": "struct NativeLibrary",
     "depth": 3
    },
    {
     "id": "cinderplatformwindow",
     "text": "cinder.platform.window",
     "depth": 2
    },
    {
     "id": "struct-gamepadslot",
     "text": "struct GamepadSlot",
     "depth": 3
    },
    {
     "id": "struct-platform",
     "text": "struct Platform",
     "depth": 3
    },
    {
     "id": "struct-window",
     "text": "struct Window",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/api/render/",
   "md": "/docs/api/render.md",
   "title": "cinder.render API",
   "section": "API reference",
   "source": "docs/api/render.md",
   "summary": "Source: cinder/render/__init__.mojo",
   "headings": [
    {
     "id": "cinderrender-1",
     "text": "cinder.render",
     "depth": 2
    },
    {
     "id": "cinderrendercamera",
     "text": "cinder.render.camera",
     "depth": 2
    },
    {
     "id": "struct-plane",
     "text": "struct Plane",
     "depth": 3
    },
    {
     "id": "struct-frustum",
     "text": "struct Frustum",
     "depth": 3
    },
    {
     "id": "struct-camera",
     "text": "struct Camera",
     "depth": 3
    },
    {
     "id": "cinderrenderframe_graph",
     "text": "cinder.render.frame_graph",
     "depth": 2
    },
    {
     "id": "struct-transientdesc",
     "text": "struct TransientDesc",
     "depth": 3
    },
    {
     "id": "struct-framegraph",
     "text": "struct FrameGraph",
     "depth": 3
    },
    {
     "id": "cinderrenderlights",
     "text": "cinder.render.lights",
     "depth": 2
    },
    {
     "id": "struct-lightkind",
     "text": "struct LightKind",
     "depth": 3
    },
    {
     "id": "struct-light",
     "text": "struct Light",
     "depth": 3
    },
    {
     "id": "def-pack_lights_into",
     "text": "def pack_lights_into",
     "depth": 3
    },
    {
     "id": "def-pack_lights",
     "text": "def pack_lights",
     "depth": 3
    },
    {
     "id": "struct-clusterparams",
     "text": "struct ClusterParams",
     "depth": 3
    },
    {
     "id": "cinderrendermaterial",
     "text": "cinder.render.material",
     "depth": 2
    },
    {
     "id": "struct-alphamode",
     "text": "struct AlphaMode",
     "depth": 3
    },
    {
     "id": "struct-material",
     "text": "struct Material",
     "depth": 3
    },
    {
     "id": "def-material_bind_group_layout",
     "text": "def material_bind_group_layout",
     "depth": 3
    },
    {
     "id": "struct-gpumaterial",
     "text": "struct GpuMaterial",
     "depth": 3
    },
    {
     "id": "def-upload_material",
     "text": "def upload_material",
     "depth": 3
    },
    {
     "id": "def-update_material",
     "text": "def update_material",
     "depth": 3
    },
    {
     "id": "cinderrendermesh",
     "text": "cinder.render.mesh",
     "depth": 2
    },
    {
     "id": "def-vertex_layout",
     "text": "def vertex_layout",
     "depth": 3
    },
    {
     "id": "def-skin_vertex_layout",
     "text": "def skin_vertex_layout",
     "depth": 3
    },
    {
     "id": "struct-bounds",
     "text": "struct Bounds",
     "depth": 3
    },
    {
     "id": "struct-morphtarget",
     "text": "struct MorphTarget",
     "depth": 3
    },
    {
     "id": "struct-meshlod",
     "text": "struct MeshLod",
     "depth": 3
    },
    {
     "id": "struct-meshdata",
     "text": "struct MeshData",
     "depth": 3
    },
    {
     "id": "struct-gpumesh",
     "text": "struct GpuMesh",
     "depth": 3
    },
    {
     "id": "def-upload_mesh",
     "text": "def upload_mesh",
     "depth": 3
    },
    {
     "id": "def-upload_mesh_lods",
     "text": "def upload_mesh_lods",
     "depth": 3
    },
    {
     "id": "def-upload_mesh_bytes",
     "text": "def upload_mesh_bytes",
     "depth": 3
    },
    {
     "id": "def-destroy_mesh",
     "text": "def destroy_mesh",
     "depth": 3
    },
    {
     "id": "def-cube",
     "text": "def cube",
     "depth": 3
    },
    {
     "id": "def-uv_sphere",
     "text": "def uv_sphere",
     "depth": 3
    },
    {
     "id": "def-plane",
     "text": "def plane",
     "depth": 3
    },
    {
     "id": "cinderrenderrenderer",
     "text": "cinder.render.renderer",
     "depth": 2
    },
    {
     "id": "struct-tonemapper",
     "text": "struct Tonemapper",
     "depth": 3
    },
    {
     "id": "struct-debugmode",
     "text": "struct DebugMode",
     "depth": 3
    },
    {
     "id": "struct-rendersettings",
     "text": "struct RenderSettings",
     "depth": 3
    },
    {
     "id": "struct-environment",
     "text": "struct Environment",
     "depth": 3
    },
    {
     "id": "struct-renderinstance",
     "text": "struct RenderInstance",
     "depth": 3
    },
    {
     "id": "struct-renderscene",
     "text": "struct RenderScene",
     "depth": 3
    },
    {
     "id": "struct-framestats",
     "text": "struct FrameStats",
     "depth": 3
    },
    {
     "id": "struct-renderer",
     "text": "struct Renderer",
     "depth": 3
    },
    {
     "id": "cinderrendershader_library",
     "text": "cinder.render.shader_library",
     "depth": 2
    },
    {
     "id": "struct-assembledshader",
     "text": "struct AssembledShader",
     "depth": 3
    },
    {
     "id": "def-assemble",
     "text": "def assemble",
     "depth": 3
    },
    {
     "id": "struct-shaderlibrary",
     "text": "struct ShaderLibrary",
     "depth": 3
    },
    {
     "id": "cinderrendershadows",
     "text": "cinder.render.shadows",
     "depth": 2
    },
    {
     "id": "struct-cascade",
     "text": "struct Cascade",
     "depth": 3
    },
    {
     "id": "def-cascade_splits_into",
     "text": "def cascade_splits_into",
     "depth": 3
    },
    {
     "id": "def-cascade_splits",
     "text": "def cascade_splits",
     "depth": 3
    },
    {
     "id": "def-fit_cascade",
     "text": "def fit_cascade",
     "depth": 3
    },
    {
     "id": "def-fit_cascades_into",
     "text": "def fit_cascades_into",
     "depth": 3
    },
    {
     "id": "def-fit_cascades",
     "text": "def fit_cascades",
     "depth": 3
    },
    {
     "id": "struct-shadowview",
     "text": "struct ShadowView",
     "depth": 3
    },
    {
     "id": "struct-shadowatlas",
     "text": "struct ShadowAtlas",
     "depth": 3
    },
    {
     "id": "cinderrendertextures",
     "text": "cinder.render.textures",
     "depth": 2
    },
    {
     "id": "struct-gputexture",
     "text": "struct GpuTexture",
     "depth": 3
    },
    {
     "id": "def-mip_count",
     "text": "def mip_count",
     "depth": 3
    },
    {
     "id": "def-downsample",
     "text": "def downsample",
     "depth": 3
    },
    {
     "id": "def-upload_image",
     "text": "def upload_image",
     "depth": 3
    },
    {
     "id": "def-solid_image",
     "text": "def solid_image",
     "depth": 3
    },
    {
     "id": "struct-defaulttextures",
     "text": "struct DefaultTextures",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/api/scene/",
   "md": "/docs/api/scene.md",
   "title": "cinder.scene API",
   "section": "API reference",
   "source": "docs/api/scene.md",
   "summary": "Source: cinder/scene/__init__.mojo",
   "headings": [
    {
     "id": "cinderscene-1",
     "text": "cinder.scene",
     "depth": 2
    },
    {
     "id": "cindersceneformat",
     "text": "cinder.scene.format",
     "depth": 2
    },
    {
     "id": "struct-field",
     "text": "struct Field",
     "depth": 3
    },
    {
     "id": "struct-componentrecord",
     "text": "struct ComponentRecord",
     "depth": 3
    },
    {
     "id": "struct-entityrecord",
     "text": "struct EntityRecord",
     "depth": 3
    },
    {
     "id": "struct-scenedoc",
     "text": "struct SceneDoc",
     "depth": 3
    },
    {
     "id": "struct-fieldwriter",
     "text": "struct FieldWriter",
     "depth": 3
    },
    {
     "id": "struct-fieldreader",
     "text": "struct FieldReader",
     "depth": 3
    },
    {
     "id": "trait-scenecomponent",
     "text": "trait SceneComponent",
     "depth": 3
    },
    {
     "id": "struct-sceneregistry",
     "text": "struct SceneRegistry",
     "depth": 3
    },
    {
     "id": "def-format_float",
     "text": "def format_float",
     "depth": 3
    },
    {
     "id": "def-parse_float",
     "text": "def parse_float",
     "depth": 3
    },
    {
     "id": "def-bitcast_u32_to_f32",
     "text": "def bitcast_u32_to_f32",
     "depth": 3
    },
    {
     "id": "def-write_text",
     "text": "def write_text",
     "depth": 3
    },
    {
     "id": "def-read_text",
     "text": "def read_text",
     "depth": 3
    },
    {
     "id": "def-write_binary",
     "text": "def write_binary",
     "depth": 3
    },
    {
     "id": "def-read_binary",
     "text": "def read_binary",
     "depth": 3
    },
    {
     "id": "cinderscenegltf_spawn",
     "text": "cinder.scene.gltf_spawn",
     "depth": 2
    },
    {
     "id": "struct-spawnedgltf",
     "text": "struct SpawnedGltf",
     "depth": 3
    },
    {
     "id": "def-spawn_gltf",
     "text": "def spawn_gltf",
     "depth": 3
    },
    {
     "id": "def-collision_triangles",
     "text": "def collision_triangles",
     "depth": 3
    },
    {
     "id": "cinderscenerender_sync",
     "text": "cinder.scene.render_sync",
     "depth": 2
    },
    {
     "id": "struct-meshrenderer",
     "text": "struct MeshRenderer",
     "depth": 3
    },
    {
     "id": "struct-lightsource",
     "text": "struct LightSource",
     "depth": 3
    },
    {
     "id": "struct-cameracomponent",
     "text": "struct CameraComponent",
     "depth": 3
    },
    {
     "id": "struct-jointpalette",
     "text": "struct JointPalette",
     "depth": 3
    },
    {
     "id": "struct-renderbridge",
     "text": "struct RenderBridge",
     "depth": 3
    },
    {
     "id": "def-build_render_scene",
     "text": "def build_render_scene",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/api/tools/",
   "md": "/docs/api/tools.md",
   "title": "cinder.tools API",
   "section": "API reference",
   "source": "docs/api/tools.md",
   "summary": "Source: cinder/tools/__init__.mojo",
   "headings": [
    {
     "id": "cindertools-1",
     "text": "cinder.tools",
     "depth": 2
    },
    {
     "id": "cindertoolscstrings",
     "text": "cinder.tools.cstrings",
     "depth": 2
    },
    {
     "id": "struct-cstrings",
     "text": "struct CStrings",
     "depth": 3
    },
    {
     "id": "cindertoolsdebug_ui",
     "text": "cinder.tools.debug_ui",
     "depth": 2
    },
    {
     "id": "struct-debugui",
     "text": "struct DebugUi",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/report/",
   "md": "/docs/report.md",
   "title": "Deliverable report",
   "section": "Project",
   "source": "REPORT.md",
   "summary": "Living document. Every claim below was verified in this repository under the pinned toolchain on the date given; nothing is reported from memory or intention. Phases are those of the mission brief.",
   "headings": [
    {
     "id": "1-what-was-built-and-what-was-not",
     "text": "1. What was built (and what was not)",
     "depth": 2
    },
    {
     "id": "2-pinned-version-matrix",
     "text": "2. Pinned version matrix",
     "depth": 2
    },
    {
     "id": "3-test-results-linux-x86-64-lavapipe-2026-11-09",
     "text": "3. Test results (Linux x86-64, lavapipe, 2026-11-09)",
     "depth": 2
    },
    {
     "id": "4-benchmark-results",
     "text": "4. Benchmark results",
     "depth": 2
    },
    {
     "id": "section-8-budgets",
     "text": "Section 8 budgets",
     "depth": 3
    },
    {
     "id": "results-pixi-run-bench-all-1920x1080-high-preset-headless",
     "text": "Results (pixi run bench-all, 1920x1080, high preset, headless)",
     "depth": 3
    },
    {
     "id": "5-known-limitations-and-mojo-workarounds",
     "text": "5. Known limitations and Mojo workarounds",
     "depth": 2
    },
    {
     "id": "defect-sweep-before-v010-phase-9",
     "text": "Defect sweep before v0.1.0 (Phase 9)",
     "depth": 3
    },
    {
     "id": "6-deviations-from-the-brief-each-with-its-adr",
     "text": "6. Deviations from the brief, each with its ADR",
     "depth": 2
    },
    {
     "id": "7-blockers-escalated",
     "text": "7. Blockers escalated",
     "depth": 2
    },
    {
     "id": "8-exact-commands",
     "text": "8. Exact commands",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/status/",
   "md": "/docs/status.md",
   "title": "Status",
   "section": "Project",
   "source": "docs/STATUS.md",
   "summary": "Last updated: 2026-11-09. One row per phase; \"verified\" means executed in this repository under the pinned toolchain, with the command named. Nothing here is claimed from memory.",
   "headings": [
    {
     "id": "blockers-escalated-to-the-operator",
     "text": "Blockers escalated to the operator",
     "depth": 2
    },
    {
     "id": "decisions-log",
     "text": "Decisions log",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/changelog/",
   "md": "/docs/changelog.md",
   "title": "Changelog",
   "section": "Project",
   "source": "CHANGELOG.md",
   "summary": "All notable changes to Cinder. The format follows Keep a Changelog; versions follow semantic versioning. Dates are the day the phase gate passed on Linux x86-64 (REPORT.md has the runs).",
   "headings": [
    {
     "id": "010---2026-11-09",
     "text": "0.1.0 - 2026-11-09",
     "depth": 2
    },
    {
     "id": "added",
     "text": "Added",
     "depth": 3
    },
    {
     "id": "quality-gates",
     "text": "Quality gates",
     "depth": 3
    },
    {
     "id": "known-limitations",
     "text": "Known limitations",
     "depth": 3
    }
   ]
  },
  {
   "path": "/docs/readme/",
   "md": "/docs/readme.md",
   "title": "Engine README",
   "section": "Project",
   "source": "README.md",
   "summary": "A 3D game engine written in Mojo 1.2 over a single C11 native shim (wgpu-native, SDL3, Jolt, miniaudio, cgltf, Dear ImGui). Targets Linux x86-64 (Vulkan) and macOS Apple Silicon (Metal).",
   "headings": [
    {
     "id": "quick-start-linux-or-any-host-with-docker",
     "text": "Quick start (Linux, or any host with Docker)",
     "depth": 2
    },
    {
     "id": "the-sample-game",
     "text": "The sample game",
     "depth": 2
    },
    {
     "id": "benchmarks",
     "text": "Benchmarks",
     "depth": 2
    },
    {
     "id": "layout",
     "text": "Layout",
     "depth": 2
    },
    {
     "id": "documentation",
     "text": "Documentation",
     "depth": 2
    },
    {
     "id": "licence",
     "text": "Licence",
     "depth": 2
    }
   ]
  },
  {
   "path": "/docs/third-party-notices/",
   "md": "/docs/third-party-notices.md",
   "title": "Third-party notices",
   "section": "Project",
   "source": "THIRD_PARTY_NOTICES.md",
   "summary": "Every dependency is vendored as a git submodule under third_party/ at the exact ref below and built from source by native/. Licence texts are in each submodule at the path given. All licences are permissive; no copyleft code is linked into Cinder.",
   "headings": [
    {
     "id": "tools-not-linked-into-the-engine",
     "text": "Tools (not linked into the engine)",
     "depth": 2
    },
    {
     "id": "assets",
     "text": "Assets",
     "depth": 2
    }
   ]
  }
 ],
 "symbols": [
  {
   "name": "anim",
   "qualified": "cinder.anim",
   "kind": "module",
   "module": "cinder.anim",
   "signature": "",
   "summary": "Skeletal animation: skeletons, clip sampling, blend trees, animators with crossfades, root motion and events, and a job-parallel system publishing joint palettes to the ECS.",
   "url": "/docs/api/anim/#cinderanim-1",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "animator",
   "qualified": "cinder.anim.animator",
   "kind": "module",
   "module": "cinder.anim.animator",
   "signature": "",
   "summary": "Animator: states (blend trees) with crossfades, animation events and root motion. update(dt) advances the active state (and the one fading out), blends them, extracts root motion and collects events; pose then holds the local pose and palette() the skinning matrices. Events are authored per state at a normalised phase in [0, 1) and fire once each time the phase passes them, including across…",
   "url": "/docs/api/anim/#cinderanimanimator",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "AnimationEvent",
   "qualified": "cinder.anim.animator.AnimationEvent",
   "kind": "struct",
   "module": "cinder.anim.animator",
   "signature": "struct AnimationEvent(Copyable, Movable)",
   "summary": "An event that fired during Animator.update: the index of the state that owns it and the event's name.",
   "url": "/docs/api/anim/#struct-animationevent",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "AnimationState",
   "qualified": "cinder.anim.animator.AnimationState",
   "kind": "struct",
   "module": "cinder.anim.animator",
   "signature": "struct AnimationState(Copyable, Movable)",
   "summary": "A named animator state: a blend tree, whether its phase loops, and its events. Build it with AnimationState(name, tree^, looping) and register it with Animator.add_state, which validates the tree; add events afterwards with Animator.add_event.",
   "url": "/docs/api/anim/#struct-animationstate",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.anim.animator.AnimationState.__init__",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "AnimationState",
   "signature": "__init__( out self, name: String, var tree: BlendTree, looping: Bool = True )",
   "summary": "",
   "url": "/docs/api/anim/#animationstate-__init__",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "Animator",
   "qualified": "cinder.anim.animator.Animator",
   "kind": "struct",
   "module": "cinder.anim.animator",
   "signature": "struct Animator(Movable)",
   "summary": "Plays the states of one skeleton with crossfades, events and root motion. Owns its skeleton, clips and poses. Author states with add_clip_state / add_state, start one with play (play(state, restart=True) replays a finished non-looping state), then call update(dt) once per frame (it raises until a state has been played). Read the result from pose, palette() / palette_into or bone_matrices().…",
   "url": "/docs/api/anim/#struct-animator",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.anim.animator.Animator.__init__",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "__init__(out self, var skeleton: Skeleton, var clips: List[Clip])",
   "summary": "",
   "url": "/docs/api/anim/#animator-__init__",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "add_clip_state",
   "qualified": "cinder.anim.animator.Animator.add_clip_state",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "add_clip_state( mut self, name: String, clip: Int, looping: Bool = True, speed: Float32 = 1.0, ) raises -> Int",
   "summary": "A state that plays one clip.",
   "url": "/docs/api/anim/#animator-add_clip_state",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "add_state",
   "qualified": "cinder.anim.animator.Animator.add_state",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "add_state(mut self, var state: AnimationState) raises -> Int",
   "summary": "Validates state.tree against the animator's clips, appends the state and returns its index. Raises when the tree has no root, names a clip that does not exist, or has a blend node without children or with a parameter out of range (see BlendTree.validate).",
   "url": "/docs/api/anim/#animator-add_state",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "add_event",
   "qualified": "cinder.anim.animator.Animator.add_event",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "add_event(mut self, state: Int, phase: Float32, name: String) raises",
   "summary": "Adds an event name to state that fires each time the state's phase passes phase. phase is normalised to the state's cycle and must be in [0, 1). Raises for an unknown state or a phase outside that range.",
   "url": "/docs/api/anim/#animator-add_event",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "find_state",
   "qualified": "cinder.anim.animator.Animator.find_state",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "find_state(self, name: String) -> Int",
   "summary": "Index of the first state called name, or -1 when there is none.",
   "url": "/docs/api/anim/#animator-find_state",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "set_parameter",
   "qualified": "cinder.anim.animator.Animator.set_parameter",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "set_parameter(mut self, name: String, value: Float32) raises",
   "summary": "Sets a blend parameter on every state that declares it.",
   "url": "/docs/api/anim/#animator-set_parameter",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "play",
   "qualified": "cinder.anim.animator.Animator.play",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "play( mut self, state: Int, fade_seconds: Float32 = 0.0, start_phase: Float32 = 0.0, restart: Bool = False, ) raises",
   "summary": "Switches to state at start_phase, crossfading from the current one over fade_seconds, and clears finished. Playing the state that is already current is a no-op (so calling play every frame is safe), even when that state is non-looping and has finished. Pass restart=True to start it again from start_phase anyway, for example to replay a finished jump; with a fade the old playthrough fades out as the new one starts. Raises for an unknown state.",
   "url": "/docs/api/anim/#animator-play",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "current_state",
   "qualified": "cinder.anim.animator.Animator.current_state",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "current_state(self) -> Int",
   "summary": "Index of the playing state (the incoming one during a crossfade), or -1 before the first play.",
   "url": "/docs/api/anim/#animator-current_state",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "phase",
   "qualified": "cinder.anim.animator.Animator.phase",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "phase(self) -> Float32",
   "summary": "Normalised phase of the current state: in [0, 1) while looping; a non-looping state holds 1 once it has finished.",
   "url": "/docs/api/anim/#animator-phase",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "fade_weight",
   "qualified": "cinder.anim.animator.Animator.fade_weight",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "fade_weight(self) -> Float32",
   "summary": "Weight of the incoming state during a crossfade (1 when none is running).",
   "url": "/docs/api/anim/#animator-fade_weight",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "update",
   "qualified": "cinder.anim.animator.Animator.update",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "update(mut self, dt: Float32) raises",
   "summary": "Advances time, evaluates and blends the layers, then applies root motion.",
   "url": "/docs/api/anim/#animator-update",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "enable_root_motion",
   "qualified": "cinder.anim.animator.Animator.enable_root_motion",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "enable_root_motion(mut self, bone: Int = 0) raises",
   "summary": "Starts extracting the horizontal motion of bone (the hierarchy root by default).",
   "url": "/docs/api/anim/#animator-enable_root_motion",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "take_root_motion",
   "qualified": "cinder.anim.animator.Animator.take_root_motion",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "take_root_motion(mut self) -> Vec3",
   "summary": "Horizontal root displacement accumulated since the last call (model space).",
   "url": "/docs/api/anim/#animator-take_root_motion",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "take_events",
   "qualified": "cinder.anim.animator.Animator.take_events",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "take_events(mut self) -> List[AnimationEvent]",
   "summary": "Returns the events fired since the last call and clears the list. Only the current state fires events; a state that is fading out fires none.",
   "url": "/docs/api/anim/#animator-take_events",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "palette",
   "qualified": "cinder.anim.animator.Animator.palette",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "palette(self) -> List[Mat4]",
   "summary": "Skinning matrices for the current pose in palette (skin joint) order. Allocates a new list; palette_into is the allocation-free form.",
   "url": "/docs/api/anim/#animator-palette",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "palette_into",
   "qualified": "cinder.anim.animator.Animator.palette_into",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "palette_into(mut self, mut out: List[Mat4])",
   "summary": "Skinning matrices for the current pose into out (no allocation once sized).",
   "url": "/docs/api/anim/#animator-palette_into",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "bone_matrices",
   "qualified": "cinder.anim.animator.Animator.bone_matrices",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "bone_matrices(self) -> List[Mat4]",
   "summary": "Every bone's matrix in model space for the current pose (attachments, IK, debug).",
   "url": "/docs/api/anim/#animator-bone_matrices",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "bone_matrices_into",
   "qualified": "cinder.anim.animator.Animator.bone_matrices_into",
   "kind": "method",
   "module": "cinder.anim.animator",
   "parent": "Animator",
   "signature": "bone_matrices_into(self, mut out: List[Mat4])",
   "summary": "Every bone's model-space matrix for the current pose into out (resized; no allocation once large enough).",
   "url": "/docs/api/anim/#animator-bone_matrices_into",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "blend",
   "qualified": "cinder.anim.blend",
   "kind": "module",
   "module": "cinder.anim.blend",
   "signature": "",
   "summary": "Blend trees: clips, 1D and 2D blend nodes, evaluated phase-synchronised. A tree runs on a normalised phase in [0, 1). Every leaf clip plays at phase * duration, so blended cycles (walk and run) stay in step; the phase advances at the weighted average of the leaves' cycle rates. Leaf weights come from the blend parameters: 1D nodes interpolate between the two nearest thresholds, 2D nodes use…",
   "url": "/docs/api/anim/#cinderanimblend",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "BlendNode",
   "qualified": "cinder.anim.blend.BlendNode",
   "kind": "struct",
   "module": "cinder.anim.blend",
   "signature": "struct BlendNode(Copyable, Movable)",
   "summary": "One node of a BlendTree: a clip leaf or a 1D/2D blend over child node indices. Created by BlendTree.add_clip, add_blend_1d and add_blend_2d; indices a kind does not use stay -1 and its lists stay empty.",
   "url": "/docs/api/anim/#struct-blendnode",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.anim.blend.BlendNode.__init__",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendNode",
   "signature": "__init__(out self, kind: Int)",
   "summary": "",
   "url": "/docs/api/anim/#blendnode-__init__",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "BlendTree",
   "qualified": "cinder.anim.blend.BlendTree",
   "kind": "struct",
   "module": "cinder.anim.blend",
   "signature": "struct BlendTree(Copyable, Movable)",
   "summary": "Nodes are stored flat; root names the entry node. Build with add_clip, add_blend_1d and add_blend_2d, then set_root.",
   "url": "/docs/api/anim/#struct-blendtree",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.anim.blend.BlendTree.__init__",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/anim/#blendtree-__init__",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "add_parameter",
   "qualified": "cinder.anim.blend.BlendTree.add_parameter",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "add_parameter(mut self, name: String, initial: Float32 = 0.0) -> Int",
   "summary": "Declares a blend parameter with an initial value and returns its index, which add_blend_1d / add_blend_2d take. Duplicate names are not rejected; set_parameter updates the first match.",
   "url": "/docs/api/anim/#blendtree-add_parameter",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "set_parameter",
   "qualified": "cinder.anim.blend.BlendTree.set_parameter",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "set_parameter(mut self, name: String, value: Float32) raises",
   "summary": "Sets the first parameter called name to value. Raises when the tree has no such parameter.",
   "url": "/docs/api/anim/#blendtree-set_parameter",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "add_clip",
   "qualified": "cinder.anim.blend.BlendTree.add_clip",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "add_clip(mut self, clip: Int, speed: Float32 = 1.0) -> Int",
   "summary": "Adds a leaf that plays clip index clip at speed times its natural rate and returns the node index. The clip index is checked by validate, not here.",
   "url": "/docs/api/anim/#blendtree-add_clip",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "add_blend_1d",
   "qualified": "cinder.anim.blend.BlendTree.add_blend_1d",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "add_blend_1d(mut self, parameter: Int) -> Int",
   "summary": "Adds a 1D blend node driven by parameter index parameter and returns the node index. Attach children with add_child; the parameter index is checked by validate.",
   "url": "/docs/api/anim/#blendtree-add_blend_1d",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "add_blend_2d",
   "qualified": "cinder.anim.blend.BlendTree.add_blend_2d",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "add_blend_2d(mut self, parameter_x: Int, parameter_y: Int) -> Int",
   "summary": "Adds a 2D blend node driven by parameters parameter_x and parameter_y and returns the node index. Attach children with add_child; the parameter indices are checked by validate.",
   "url": "/docs/api/anim/#blendtree-add_blend_2d",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "add_child",
   "qualified": "cinder.anim.blend.BlendTree.add_child",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "add_child(mut self, node: Int, child: Int, at: Vec2) raises",
   "summary": "Attaches child to a blend node with full weight at parameter value at (1D nodes use at.x()). Children of a 1D node must be added in increasing order. Raises when an index is out of range, node is a clip, the node is full, a 1D threshold does not increase, or the edge would close a cycle (child is node or one of its ancestors): a tree must stay acyclic for evaluation to terminate. A node may still be shared by several parents.",
   "url": "/docs/api/anim/#blendtree-add_child",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "set_root",
   "qualified": "cinder.anim.blend.BlendTree.set_root",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "set_root(mut self, node: Int) raises",
   "summary": "Makes node the entry node of the tree. Raises when the index is out of range.",
   "url": "/docs/api/anim/#blendtree-set_root",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "validate",
   "qualified": "cinder.anim.blend.BlendTree.validate",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "validate(self, clip_count: Int) raises",
   "summary": "Checks that the tree can be evaluated with clip_count clips and raises on the first problem: no root (or one out of range), a clip leaf naming a missing clip, a blend node without children or with a child index out of range, a blend parameter index out of range (2D nodes need both), or a cycle (a node that is its own descendant; add_child already refuses these, but nodes is public). Animator.add_state calls it.",
   "url": "/docs/api/anim/#blendtree-validate",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "leaf_weights_into",
   "qualified": "cinder.anim.blend.BlendTree.leaf_weights_into",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "leaf_weights_into(self, mut weights: List[Float32])",
   "summary": "Weight per node (leaves carry the blended weight, inner nodes their subtree's), summing to one over the leaves, written into weights.",
   "url": "/docs/api/anim/#blendtree-leaf_weights_into",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "leaf_weights",
   "qualified": "cinder.anim.blend.BlendTree.leaf_weights",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "leaf_weights(self) -> List[Float32]",
   "summary": "Per-node weights for the current parameters (see leaf_weights_into) in a new list; allocates.",
   "url": "/docs/api/anim/#blendtree-leaf_weights",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "cycle_rate",
   "qualified": "cinder.anim.blend.BlendTree.cycle_rate",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "cycle_rate(self, clips: List[Clip]) -> Float32",
   "summary": "Phase advance per second: the weighted average of each leaf's speed / duration.",
   "url": "/docs/api/anim/#blendtree-cycle_rate",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "cycle_rate_with",
   "qualified": "cinder.anim.blend.BlendTree.cycle_rate_with",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "cycle_rate_with( self, clips: List[Clip], mut weights: List[Float32] ) -> Float32",
   "summary": "cycle_rate using the caller's weight scratch (no allocation once sized).",
   "url": "/docs/api/anim/#blendtree-cycle_rate_with",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "evaluate",
   "qualified": "cinder.anim.blend.BlendTree.evaluate",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "evaluate( self, clips: List[Clip], skeleton: Skeleton, phase: Float32, mut pose: Pose, mut scratch: Pose, )",
   "summary": "Blends every weighted leaf at phase into pose (allocates a weight list; the animator uses evaluate_with).",
   "url": "/docs/api/anim/#blendtree-evaluate",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "evaluate_with",
   "qualified": "cinder.anim.blend.BlendTree.evaluate_with",
   "kind": "method",
   "module": "cinder.anim.blend",
   "parent": "BlendTree",
   "signature": "evaluate_with( self, clips: List[Clip], skeleton: Skeleton, phase: Float32, mut pose: Pose, mut scratch: Pose, mut weights: List[Float32], )",
   "summary": "Blends every weighted leaf at phase into pose. scratch is a pose of the same skeleton for the per-leaf samples and weights the per-node weight scratch; callers reuse both across frames so nothing is allocated.",
   "url": "/docs/api/anim/#blendtree-evaluate_with",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "sampling",
   "qualified": "cinder.anim.sampling",
   "kind": "module",
   "module": "cinder.anim.sampling",
   "signature": "",
   "summary": "Clip sampling: step, linear and cubic-spline keyframes into a local pose. Pose is the skeleton's local transforms plus morph weights. Sampling starts from the rest pose so channels that are missing from a clip keep the skeleton's values (glTF semantics).",
   "url": "/docs/api/anim/#cinderanimsampling",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "Pose",
   "qualified": "cinder.anim.sampling.Pose",
   "kind": "struct",
   "module": "cinder.anim.sampling",
   "signature": "struct Pose(Copyable, Movable)",
   "summary": "A local pose: one parent-space transform per bone plus the morph target weights. Pose(skeleton) starts at the rest pose with zero weights. A pose is tied to the skeleton it was built for: sampling, blending and reset index by bone and never resize.",
   "url": "/docs/api/anim/#struct-pose",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.anim.sampling.Pose.__init__",
   "kind": "method",
   "module": "cinder.anim.sampling",
   "parent": "Pose",
   "signature": "__init__(out self, skeleton: Skeleton)",
   "summary": "",
   "url": "/docs/api/anim/#pose-__init__",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.anim.sampling.Pose.__init__",
   "kind": "method",
   "module": "cinder.anim.sampling",
   "parent": "Pose",
   "signature": "__init__( out self, var local: List[Transform], var morph_weights: List[Float32] )",
   "summary": "",
   "url": "/docs/api/anim/#pose-__init__-1",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "reset",
   "qualified": "cinder.anim.sampling.Pose.reset",
   "kind": "method",
   "module": "cinder.anim.sampling",
   "parent": "Pose",
   "signature": "reset(mut self, skeleton: Skeleton)",
   "summary": "Restores the rest pose of skeleton and zeroes the morph weights in place (no allocation). skeleton must be the one the pose was built for.",
   "url": "/docs/api/anim/#pose-reset",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "copy_from",
   "qualified": "cinder.anim.sampling.Pose.copy_from",
   "kind": "method",
   "module": "cinder.anim.sampling",
   "parent": "Pose",
   "signature": "copy_from(mut self, other: Pose)",
   "summary": "Element-wise copy (same skeleton), no allocation.",
   "url": "/docs/api/anim/#pose-copy_from",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "blend_with",
   "qualified": "cinder.anim.sampling.Pose.blend_with",
   "kind": "method",
   "module": "cinder.anim.sampling",
   "parent": "Pose",
   "signature": "blend_with(mut self, b: Pose, t: Float32)",
   "summary": "self = lerp(self, b, t) component-wise.",
   "url": "/docs/api/anim/#pose-blend_with",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "sample_component",
   "qualified": "cinder.anim.sampling.sample_component",
   "kind": "def",
   "module": "cinder.anim.sampling",
   "signature": "def sample_component( ch: ClipChannel, pair: _KeyPair, component: Int ) -> Float32",
   "summary": "One output component at the located time.",
   "url": "/docs/api/anim/#def-sample_component",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "sample_rotation",
   "qualified": "cinder.anim.sampling.sample_rotation",
   "kind": "def",
   "module": "cinder.anim.sampling",
   "signature": "def sample_rotation(ch: ClipChannel, pair: _KeyPair) -> Quat",
   "summary": "Rotations interpolate along the shorter arc (slerp for linear, normalised spline for cubic, as the glTF specification describes).",
   "url": "/docs/api/anim/#def-sample_rotation",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "sample_clip",
   "qualified": "cinder.anim.sampling.sample_clip",
   "kind": "def",
   "module": "cinder.anim.sampling",
   "signature": "def sample_clip(clip: Clip, skeleton: Skeleton, time: Float32, mut pose: Pose)",
   "summary": "Writes every channel of clip at time (seconds, unclamped: before the first key or after the last key the end values hold) into pose. Channels whose node is not in the skeleton are ignored; pose must have been created for skeleton.",
   "url": "/docs/api/anim/#def-sample_clip",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "wrap_time",
   "qualified": "cinder.anim.sampling.wrap_time",
   "kind": "def",
   "module": "cinder.anim.sampling",
   "signature": "def wrap_time(time: Float32, duration: Float32) -> Float32",
   "summary": "Loops time into [0, duration).",
   "url": "/docs/api/anim/#def-wrap_time",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "skeleton",
   "qualified": "cinder.anim.skeleton",
   "kind": "module",
   "module": "cinder.anim.skeleton",
   "signature": "",
   "summary": "Skeletons: a bone hierarchy with rest pose, the skin's joint list and inverse bind matrices. A skeleton is built from a glTF skin (every joint plus the ancestors needed to reach a common root, so animated parents move their children) or read from a cooked .cskel file. Clips keep glTF node indices, which node_to_bone maps to bones.",
   "url": "/docs/api/anim/#cinderanimskeleton",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "Skeleton",
   "qualified": "cinder.anim.skeleton.Skeleton",
   "kind": "struct",
   "module": "cinder.anim.skeleton",
   "signature": "struct Skeleton(Copyable, Movable)",
   "summary": "Bone hierarchy, rest pose and skin data of one glTF skin. Bones are ordered parents first. Build one with skeleton_from_gltf or read_skeleton (both validate it); palette and world_transforms turn a local pose into matrices.",
   "url": "/docs/api/anim/#struct-skeleton",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.anim.skeleton.Skeleton.__init__",
   "kind": "method",
   "module": "cinder.anim.skeleton",
   "parent": "Skeleton",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/anim/#skeleton-__init__",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "bone_count",
   "qualified": "cinder.anim.skeleton.Skeleton.bone_count",
   "kind": "method",
   "module": "cinder.anim.skeleton",
   "parent": "Skeleton",
   "signature": "bone_count(self) -> Int",
   "summary": "Number of bones (skin joints plus the ancestors needed to reach a common root).",
   "url": "/docs/api/anim/#skeleton-bone_count",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "joint_count",
   "qualified": "cinder.anim.skeleton.Skeleton.joint_count",
   "kind": "method",
   "module": "cinder.anim.skeleton",
   "parent": "Skeleton",
   "signature": "joint_count(self) -> Int",
   "summary": "Number of skin joints, which is the length of the skinning palette.",
   "url": "/docs/api/anim/#skeleton-joint_count",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "find_bone",
   "qualified": "cinder.anim.skeleton.Skeleton.find_bone",
   "kind": "method",
   "module": "cinder.anim.skeleton",
   "parent": "Skeleton",
   "signature": "find_bone(self, name: String) -> Int",
   "summary": "Index of the first bone called name, or -1 when there is none.",
   "url": "/docs/api/anim/#skeleton-find_bone",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "bone_of_node",
   "qualified": "cinder.anim.skeleton.Skeleton.bone_of_node",
   "kind": "method",
   "module": "cinder.anim.skeleton",
   "parent": "Skeleton",
   "signature": "bone_of_node(self, node: Int) -> Int",
   "summary": "Bone index of glTF node node, or -1 when the node is out of range or not part of the skeleton.",
   "url": "/docs/api/anim/#skeleton-bone_of_node",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "world_transforms_into",
   "qualified": "cinder.anim.skeleton.Skeleton.world_transforms_into",
   "kind": "method",
   "module": "cinder.anim.skeleton",
   "parent": "Skeleton",
   "signature": "world_transforms_into( self, local: List[Transform], mut out: List[Mat4] )",
   "summary": "Bone-space matrices from a local pose (parents first), in model space, written into out (resized; no allocation once large enough).",
   "url": "/docs/api/anim/#skeleton-world_transforms_into",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "world_transforms",
   "qualified": "cinder.anim.skeleton.Skeleton.world_transforms",
   "kind": "method",
   "module": "cinder.anim.skeleton",
   "parent": "Skeleton",
   "signature": "world_transforms(self, local: List[Transform]) -> List[Mat4]",
   "summary": "Model-space bone matrices for the local pose local in a new list; allocates (see world_transforms_into).",
   "url": "/docs/api/anim/#skeleton-world_transforms",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "palette_into",
   "qualified": "cinder.anim.skeleton.Skeleton.palette_into",
   "kind": "method",
   "module": "cinder.anim.skeleton",
   "parent": "Skeleton",
   "signature": "palette_into( self, local: List[Transform], mut worlds: List[Mat4], mut out: List[Mat4], )",
   "summary": "Skinning matrices in palette order into out; worlds is scratch for the bone matrices.",
   "url": "/docs/api/anim/#skeleton-palette_into",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "palette",
   "qualified": "cinder.anim.skeleton.Skeleton.palette",
   "kind": "method",
   "module": "cinder.anim.skeleton",
   "parent": "Skeleton",
   "signature": "palette(self, local: List[Transform]) -> List[Mat4]",
   "summary": "Skinning matrices in palette order: inverse(mesh node) * bone world * inverse bind.",
   "url": "/docs/api/anim/#skeleton-palette",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "validate",
   "qualified": "cinder.anim.skeleton.Skeleton.validate",
   "kind": "method",
   "module": "cinder.anim.skeleton",
   "parent": "Skeleton",
   "signature": "validate(self) raises",
   "summary": "Checks the invariants and raises on the first violation: 1 to MAX_BONES bones, one name and rest transform per bone, every parent before its child (or -1), node map and joints inside the bone range (or -1), and one inverse bind matrix per joint.",
   "url": "/docs/api/anim/#skeleton-validate",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "skeleton_from_gltf",
   "qualified": "cinder.anim.skeleton.skeleton_from_gltf",
   "kind": "def",
   "module": "cinder.anim.skeleton",
   "signature": "def skeleton_from_gltf(asset: GltfAsset, skin: Int) raises -> Skeleton",
   "summary": "Builds the skeleton of asset.skins[skin]: the joints and every ancestor up to the outermost ancestor shared by all joints (so animated parents are evaluated), in parent-before-child order. The mesh node is the first node using the skin.",
   "url": "/docs/api/anim/#def-skeleton_from_gltf",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "write_skeleton",
   "qualified": "cinder.anim.skeleton.write_skeleton",
   "kind": "def",
   "module": "cinder.anim.skeleton",
   "signature": "def write_skeleton(skeleton: Skeleton) -> List[UInt8]",
   "summary": "Serialises skeleton to the cooked .cskel format: magic, version, bones (name, parent, rest transform), node map, joints with inverse bind matrices, mesh node and its inverse, morph count. Indices are stored plus one so -1 round-trips as 0. Does not validate.",
   "url": "/docs/api/anim/#def-write_skeleton",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "read_skeleton",
   "qualified": "cinder.anim.skeleton.read_skeleton",
   "kind": "def",
   "module": "cinder.anim.skeleton",
   "signature": "def read_skeleton(var data: List[UInt8]) raises -> Skeleton",
   "summary": "Parses a cooked .cskel buffer (consumed) into a validated skeleton. Raises on a wrong magic or version, implausible bone, node or joint counts, data that ends early, trailing bytes, or a result that fails Skeleton.validate.",
   "url": "/docs/api/anim/#def-read_skeleton",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "system",
   "qualified": "cinder.anim.system",
   "kind": "module",
   "module": "cinder.anim.system",
   "signature": "",
   "summary": "The animation system: animators stored in a pool, advanced in parallel on the job system, and published to the ECS as JointPalette components for the render bridge. Animators live in the system (they own clips and poses); entities refer to them with AnimatorRef. update(dt, jobs) runs one job per animator: each job touches only its own animator, so no synchronisation is needed beyond the…",
   "url": "/docs/api/anim/#cinderanimsystem",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "AnimatorRef",
   "qualified": "cinder.anim.system.AnimatorRef",
   "kind": "struct",
   "module": "cinder.anim.system",
   "signature": "struct AnimatorRef(Component)",
   "summary": "Links an entity to AnimationSystem.animators[index].",
   "url": "/docs/api/anim/#struct-animatorref",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "component_id",
   "qualified": "cinder.anim.system.AnimatorRef.component_id",
   "kind": "method",
   "module": "cinder.anim.system",
   "parent": "AnimatorRef",
   "signature": "component_id() -> Int",
   "summary": "",
   "url": "/docs/api/anim/#animatorref-component_id",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "AnimationSystem",
   "qualified": "cinder.anim.system.AnimationSystem",
   "kind": "struct",
   "module": "cinder.anim.system",
   "signature": "struct AnimationSystem(Movable)",
   "summary": "Owns every animator, updates them in parallel and publishes their palettes to the ECS. Entities refer to animators by index through AnimatorRef; updates counts completed update calls. Jobs receive raw pointers into animators, so the system must stay in place and the list must not change while update runs.",
   "url": "/docs/api/anim/#struct-animationsystem",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.anim.system.AnimationSystem.__init__",
   "kind": "method",
   "module": "cinder.anim.system",
   "parent": "AnimationSystem",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/anim/#animationsystem-__init__",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "add",
   "qualified": "cinder.anim.system.AnimationSystem.add",
   "kind": "method",
   "module": "cinder.anim.system",
   "parent": "AnimationSystem",
   "signature": "add(mut self, var animator: Animator) -> Int",
   "summary": "Takes ownership of animator and returns its index for AnimatorRef. Call between frames, never while update is running.",
   "url": "/docs/api/anim/#animationsystem-add",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "__len__",
   "qualified": "cinder.anim.system.AnimationSystem.__len__",
   "kind": "method",
   "module": "cinder.anim.system",
   "parent": "AnimationSystem",
   "signature": "__len__(self) -> Int",
   "summary": "",
   "url": "/docs/api/anim/#animationsystem-__len__",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "clear",
   "qualified": "cinder.anim.system.AnimationSystem.clear",
   "kind": "method",
   "module": "cinder.anim.system",
   "parent": "AnimationSystem",
   "signature": "clear(mut self)",
   "summary": "Drops every animator (a level restart); AnimatorRefs become stale.",
   "url": "/docs/api/anim/#animationsystem-clear",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "update",
   "qualified": "cinder.anim.system.AnimationSystem.update",
   "kind": "method",
   "module": "cinder.anim.system",
   "parent": "AnimationSystem",
   "signature": "update( mut self, dt: Float32, jobs: Optional[Pointer[JobSystem, MutUntrackedOrigin]], ) raises",
   "summary": "Advances every animator by dt. With a job system (and more than one animator) each animator is its own job; otherwise they run inline, one after the other. Either way every animator is updated, and when any of them raised (an animator that was never played raises \"update before play\") the call raises afterwards, naming the first one that failed; the others have still advanced. updates counts only calls that did not raise.",
   "url": "/docs/api/anim/#animationsystem-update",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "publish",
   "qualified": "cinder.anim.system.AnimationSystem.publish",
   "kind": "method",
   "module": "cinder.anim.system",
   "parent": "AnimationSystem",
   "signature": "publish(mut self, mut world: World) raises -> Int",
   "summary": "Writes a JointPalette for every entity with an AnimatorRef, in place when the component exists (no steady-state allocation). Returns the count.",
   "url": "/docs/api/anim/#animationsystem-publish",
   "md": "/docs/api/anim.md"
  },
  {
   "name": "app",
   "qualified": "cinder.app",
   "kind": "module",
   "module": "cinder.app",
   "signature": "",
   "summary": "Application runtime: subsystems, the fixed-step game loop, windowed and headless modes.",
   "url": "/docs/api/app/#cinderapp-1",
   "md": "/docs/api/app.md"
  },
  {
   "name": "app",
   "qualified": "cinder.app.app",
   "kind": "module",
   "module": "cinder.app.app",
   "signature": "",
   "summary": "The application runtime: owns every subsystem, runs the fixed-step game loop and renders. App works in two modes. Windowed: an SDL window, a swapchain and the ImGui debug overlay. Headless (AppConfig.headless, the --headless flag of the sample): no window, no audio device, frames render into an offscreen texture that read_frame reads back, so tests and benchmarks drive exactly the same loop. A…",
   "url": "/docs/api/app/#cinderappapp",
   "md": "/docs/api/app.md"
  },
  {
   "name": "ui_consumes_event",
   "qualified": "cinder.app.app.ui_consumes_event",
   "kind": "def",
   "module": "cinder.app.app",
   "signature": "def ui_consumes_event(ev: Event, ui_wants_mouse: Bool, ui_wants_keyboard: Bool) -> Bool",
   "summary": "Whether the debug overlay swallows ev instead of the game's InputMap. While ImGui wants the mouse, mouse presses, motion and wheel go only to the overlay; while it wants the keyboard, key presses do. Key and mouse button releases always reach the input map: a key or button held when the overlay takes focus would otherwise stay held there.",
   "url": "/docs/api/app/#def-ui_consumes_event",
   "md": "/docs/api/app.md"
  },
  {
   "name": "AppConfig",
   "qualified": "cinder.app.app.AppConfig",
   "kind": "struct",
   "module": "cinder.app.app",
   "signature": "struct AppConfig(Copyable, Movable)",
   "summary": "Settings read once by App.__init__; parse_app_args fills them from the command line. Defaults: 1280x720 windowed, 60 Hz fixed step, audio and debug UI on, profiler off, 3 worker threads.",
   "url": "/docs/api/app/#struct-appconfig",
   "md": "/docs/api/app.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.app.app.AppConfig.__init__",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "AppConfig",
   "signature": "__init__( out self, title: String = String(\"Cinder\"), width: Int = 1280, height: Int = 720, headless: Bool = False, )",
   "summary": "",
   "url": "/docs/api/app/#appconfig-__init__",
   "md": "/docs/api/app.md"
  },
  {
   "name": "Game",
   "qualified": "cinder.app.app.Game",
   "kind": "trait",
   "module": "cinder.app.app",
   "signature": "trait Game",
   "summary": "Gameplay hooks called by App.run_frame.",
   "url": "/docs/api/app/#trait-game",
   "md": "/docs/api/app.md"
  },
  {
   "name": "start",
   "qualified": "cinder.app.app.Game.start",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "Game",
   "signature": "start(mut self, mut app: App) raises",
   "summary": "Called once, at the start of the first run_frame and before its events are polled.",
   "url": "/docs/api/app/#game-start",
   "md": "/docs/api/app.md"
  },
  {
   "name": "fixed_update",
   "qualified": "cinder.app.app.Game.fixed_update",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "Game",
   "signature": "fixed_update(mut self, mut app: App, dt: Float32) raises",
   "summary": "Called once per fixed step with the step length in seconds, after physics has stepped and body transforms were pulled into the world.",
   "url": "/docs/api/app/#game-fixed_update",
   "md": "/docs/api/app.md"
  },
  {
   "name": "update",
   "qualified": "cinder.app.app.Game.update",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "Game",
   "signature": "update(mut self, mut app: App, dt: Float32) raises",
   "summary": "Called once per frame with the frame time in seconds, after the fixed steps and before animation, transform propagation, audio and rendering.",
   "url": "/docs/api/app/#game-update",
   "md": "/docs/api/app.md"
  },
  {
   "name": "draw_ui",
   "qualified": "cinder.app.app.Game.draw_ui",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "Game",
   "signature": "draw_ui(mut self, mut app: App) raises",
   "summary": "Called while the debug overlay is built (windowed with debug_ui only, on frames that acquired a swapchain image), before the engine's own windows; make ImGui calls here.",
   "url": "/docs/api/app/#game-draw_ui",
   "md": "/docs/api/app.md"
  },
  {
   "name": "App",
   "qualified": "cinder.app.app.App",
   "kind": "struct",
   "module": "cinder.app.app",
   "signature": "struct App(Movable)",
   "summary": "The engine runtime: owns the native library, the platform and window (windowed), the GPU device, renderer, ECS world, physics, audio, animation, input map, scene registry and assets, and drives them from run_frame. Construction raises when a subsystem fails to start. Fields are destroyed in declaration order, the overlay first and lib last. Use it from the main thread, where Platform must live.",
   "url": "/docs/api/app/#struct-app",
   "md": "/docs/api/app.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.app.app.App.__init__",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "App",
   "signature": "__init__(out self, var config: AppConfig) raises",
   "summary": "",
   "url": "/docs/api/app/#app-__init__",
   "md": "/docs/api/app.md"
  },
  {
   "name": "mount_assets",
   "qualified": "cinder.app.app.App.mount_assets",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "App",
   "signature": "mount_assets(mut self, root: String) raises",
   "summary": "Attaches a cooked-asset directory (its manifest.txt).",
   "url": "/docs/api/app/#app-mount_assets",
   "md": "/docs/api/app.md"
  },
  {
   "name": "log",
   "qualified": "cinder.app.app.App.log",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "App",
   "signature": "log(mut self, level: LogLevel, category: String, message: String)",
   "summary": "Records a message in logs, the in-memory sink shown in the debug UI's Log tab.",
   "url": "/docs/api/app/#app-log",
   "md": "/docs/api/app.md"
  },
  {
   "name": "run_frame",
   "qualified": "cinder.app.app.App.run_frame",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "App",
   "signature": "run_frame[ G: Game ](mut self, mut game: G, frame_seconds: Float64 = -1.0) raises -> Bool",
   "summary": "One frame: events, fixed steps, per-frame update, render, present. frame_seconds overrides the measured frame time (tests and benchmarks run deterministically). Returns False once a quit was requested.",
   "url": "/docs/api/app/#app-run_frame",
   "md": "/docs/api/app.md"
  },
  {
   "name": "read_frame",
   "qualified": "cinder.app.app.App.read_frame",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "App",
   "signature": "read_frame(mut self) raises -> Image",
   "summary": "Headless only: the last rendered frame as an image.",
   "url": "/docs/api/app/#app-read_frame",
   "md": "/docs/api/app.md"
  },
  {
   "name": "request_quit",
   "qualified": "cinder.app.app.App.request_quit",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "App",
   "signature": "request_quit(mut self)",
   "summary": "Makes run_frame return False. Requested from fixed_update, update or draw_ui, the current frame still completes; later calls return right after polling events.",
   "url": "/docs/api/app/#app-request_quit",
   "md": "/docs/api/app.md"
  },
  {
   "name": "gpu_error_count",
   "qualified": "cinder.app.app.App.gpu_error_count",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "App",
   "signature": "gpu_error_count(self) -> Int",
   "summary": "Uncaptured wgpu validation errors seen since the device was created.",
   "url": "/docs/api/app/#app-gpu_error_count",
   "md": "/docs/api/app.md"
  },
  {
   "name": "live_objects",
   "qualified": "cinder.app.app.App.live_objects",
   "kind": "method",
   "module": "cinder.app.app",
   "parent": "App",
   "signature": "live_objects(self) -> Int",
   "summary": "Physics objects plus audio sounds and buses alive: the game-owned objects that must be zero before shutdown (the leak report). GPU objects are not counted: the engine's own render targets, pipelines and renderer meshes stay alive for the App's whole life, so a total including them is never zero. Use res[].live_counts() for GPU resources; Resources releases and counts leftovers when it is destroyed.",
   "url": "/docs/api/app/#app-live_objects",
   "md": "/docs/api/app.md"
  },
  {
   "name": "cli",
   "qualified": "cinder.app.cli",
   "kind": "module",
   "module": "cinder.app.cli",
   "signature": "",
   "summary": "Command-line options shared by every Cinder executable (--headless for tests and benchmarks).",
   "url": "/docs/api/app/#cinderappcli",
   "md": "/docs/api/app.md"
  },
  {
   "name": "parse_app_args",
   "qualified": "cinder.app.cli.parse_app_args",
   "kind": "def",
   "module": "cinder.app.cli",
   "signature": "def parse_app_args( args: List[String], mut config: AppConfig ) raises -> List[String]",
   "summary": "Applies engine options to config and returns the arguments it did not consume. Options: --headless, --profile, --no-audio, --no-debug-ui, --width N, --height N, --title TEXT. Everything else (positional arguments and the program's own options) is returned for the caller.",
   "url": "/docs/api/app/#def-parse_app_args",
   "md": "/docs/api/app.md"
  },
  {
   "name": "assets",
   "qualified": "cinder.assets",
   "kind": "module",
   "module": "cinder.assets",
   "signature": "",
   "summary": "Assets: glTF import into engine meshes, materials, textures, skins and scenes.",
   "url": "/docs/api/assets/#cinderassets-1",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "cook",
   "qualified": "cinder.assets.cook",
   "kind": "module",
   "module": "cinder.assets.cook",
   "signature": "",
   "summary": "The asset cooker: glTF sources become cooked meshes, materials and animation clips. Cooking is incremental and keyed on content: the manifest (manifest.txt in the output directory) records, per logical asset, the FNV-1a hash of the source file and the output file name. A source whose hash is unchanged and whose outputs still exist is skipped. Output files are named by the asset id of their…",
   "url": "/docs/api/assets/#cinderassetscook",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "ManifestEntry",
   "qualified": "cinder.assets.cook.ManifestEntry",
   "kind": "struct",
   "module": "cinder.assets.cook",
   "signature": "struct ManifestEntry(Copyable, Movable)",
   "summary": "One manifest line: logical asset path, FNV-1a source hash (hex64) and output file name. file is relative to the output directory and named by asset_file_name(logical, ...).",
   "url": "/docs/api/assets/#struct-manifestentry",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "CookManifest",
   "qualified": "cinder.assets.cook.CookManifest",
   "kind": "struct",
   "module": "cinder.assets.cook",
   "signature": "struct CookManifest(Movable)",
   "summary": "The cook manifest (<out_dir>/manifest.txt), shared by the cooker and AssetServer. One entry per logical asset; lookups are linear scans. Re-cooking a source drops (prune) the entries of outputs it no longer produces.",
   "url": "/docs/api/assets/#struct-cookmanifest",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.cook.CookManifest.__init__",
   "kind": "method",
   "module": "cinder.assets.cook",
   "parent": "CookManifest",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/assets/#cookmanifest-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "load",
   "qualified": "cinder.assets.cook.CookManifest.load",
   "kind": "method",
   "module": "cinder.assets.cook",
   "parent": "CookManifest",
   "signature": "load(path: String) raises -> CookManifest",
   "summary": "Reads a manifest; a missing file yields an empty one. Lines without exactly three space-separated fields (<logical> <hash> <file>) are skipped, so logical paths must not contain spaces. Raises when the file exists but cannot be read.",
   "url": "/docs/api/assets/#cookmanifest-load",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "save",
   "qualified": "cinder.assets.cook.CookManifest.save",
   "kind": "method",
   "module": "cinder.assets.cook",
   "parent": "CookManifest",
   "signature": "save(self, path: String) raises",
   "summary": "Writes a <logical> <hash> <file> line per entry, replacing path; raises on error.",
   "url": "/docs/api/assets/#cookmanifest-save",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "find",
   "qualified": "cinder.assets.cook.CookManifest.find",
   "kind": "method",
   "module": "cinder.assets.cook",
   "parent": "CookManifest",
   "signature": "find(self, logical: String) -> Int",
   "summary": "Index of the entry for logical, or -1.",
   "url": "/docs/api/assets/#cookmanifest-find",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "record",
   "qualified": "cinder.assets.cook.CookManifest.record",
   "kind": "method",
   "module": "cinder.assets.cook",
   "parent": "CookManifest",
   "signature": "record(mut self, logical: String, source_hash: String, file: String)",
   "summary": "Replaces the entry for logical, or appends one when there is none.",
   "url": "/docs/api/assets/#cookmanifest-record",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "prune",
   "qualified": "cinder.assets.cook.CookManifest.prune",
   "kind": "method",
   "module": "cinder.assets.cook",
   "parent": "CookManifest",
   "signature": "prune( mut self, root: String, produced: List[String] ) -> List[ManifestEntry]",
   "summary": "Removes the entries under root (logical paths starting with it, root itself excepted) that are not in produced, and returns them in manifest order.",
   "url": "/docs/api/assets/#cookmanifest-prune",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "up_to_date",
   "qualified": "cinder.assets.cook.CookManifest.up_to_date",
   "kind": "method",
   "module": "cinder.assets.cook",
   "parent": "CookManifest",
   "signature": "up_to_date( self, logical: String, source_hash: String, out_dir: String ) -> Bool",
   "summary": "Whether logical is recorded with source_hash and its file exists in out_dir.",
   "url": "/docs/api/assets/#cookmanifest-up_to_date",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "CookReport",
   "qualified": "cinder.assets.cook.CookReport",
   "kind": "struct",
   "module": "cinder.assets.cook",
   "signature": "struct CookReport(Movable)",
   "summary": "What one cook_gltf call did. cooked counts outputs written; skipped counts outputs found up to date when the whole source was skipped (the two never mix in one report).",
   "url": "/docs/api/assets/#struct-cookreport",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.cook.CookReport.__init__",
   "kind": "method",
   "module": "cinder.assets.cook",
   "parent": "CookReport",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/assets/#cookreport-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "cook_gltf",
   "qualified": "cinder.assets.cook.cook_gltf",
   "kind": "def",
   "module": "cinder.assets.cook",
   "signature": "def cook_gltf( lib: NativePtr, source_path: String, prefix: String, out_dir: String, mut manifest: CookManifest, ) raises -> CookReport",
   "summary": "Cooks every mesh primitive, material and animation of a glTF file. prefix is the logical name of the source (e.g. models/Fox); outputs are <prefix>#mesh<i>/prim<p>, <prefix>#material<m> and <prefix>#anim<a>.",
   "url": "/docs/api/assets/#def-cook_gltf",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "cooked",
   "qualified": "cinder.assets.cooked",
   "kind": "module",
   "module": "cinder.assets.cooked",
   "signature": "",
   "summary": "Cooked asset formats (little-endian binary, versioned, bounds-checked on read). - .cmesh: engine vertex stream (56-byte vertices), optional skin stream, u32 indices with LOD ranges, bounds, morph deltas. Written by the cooker from glTF primitives (tangents generated, LODs built with meshoptimizer), loaded by AssetServer without any further processing. - .cclip: an animation clip (channels of…",
   "url": "/docs/api/assets/#cinderassetscooked",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "asset_id",
   "qualified": "cinder.assets.cooked.asset_id",
   "kind": "def",
   "module": "cinder.assets.cooked",
   "signature": "def asset_id(logical_path: String) -> UInt64",
   "summary": "Stable 64-bit id of a logical asset path: its FNV-1a hash.",
   "url": "/docs/api/assets/#def-asset_id",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "asset_file_name",
   "qualified": "cinder.assets.cooked.asset_file_name",
   "kind": "def",
   "module": "cinder.assets.cooked",
   "signature": "def asset_file_name(logical_path: String, extension: String) -> String",
   "summary": "<16 hex digits>.<extension>: content-addressed by logical path, not by contents.",
   "url": "/docs/api/assets/#def-asset_file_name",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "CookedMesh",
   "qualified": "cinder.assets.cooked.CookedMesh",
   "kind": "struct",
   "module": "cinder.assets.cooked",
   "signature": "struct CookedMesh(Movable)",
   "summary": "What .cmesh holds. Vertex and index bytes are already in GPU layout.",
   "url": "/docs/api/assets/#struct-cookedmesh",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.cooked.CookedMesh.__init__",
   "kind": "method",
   "module": "cinder.assets.cooked",
   "parent": "CookedMesh",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/assets/#cookedmesh-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "cook_mesh",
   "qualified": "cinder.assets.cooked.cook_mesh",
   "kind": "def",
   "module": "cinder.assets.cooked",
   "signature": "def cook_mesh( data: MeshData, lod_indices: List[List[UInt32]], material: String ) -> CookedMesh",
   "summary": "Packs a validated MeshData and its LOD index lists.",
   "url": "/docs/api/assets/#def-cook_mesh",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "write_mesh",
   "qualified": "cinder.assets.cooked.write_mesh",
   "kind": "def",
   "module": "cinder.assets.cooked",
   "signature": "def write_mesh(mesh: CookedMesh) -> List[UInt8]",
   "summary": "Serialises a CookedMesh to .cmesh bytes (version MESH_VERSION, little-endian). Layout: magic, version, vertex count, byte lengths of the vertex, skin and index streams, LOD count, bounds min and max, morph target count and byte length, material path (u32 length + bytes), the LOD table (first index, index count, error), then the vertex, skin, index and morph streams.",
   "url": "/docs/api/assets/#def-write_mesh",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "Cursor",
   "qualified": "cinder.assets.cooked.Cursor",
   "kind": "struct",
   "module": "cinder.assets.cooked",
   "signature": "struct Cursor(Movable)",
   "summary": "Bounds-checked little-endian reader over an owned byte buffer (the cooked-format readers). Every read raises when it would run past the end of the data.",
   "url": "/docs/api/assets/#struct-cursor",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.cooked.Cursor.__init__",
   "kind": "method",
   "module": "cinder.assets.cooked",
   "parent": "Cursor",
   "signature": "__init__(out self, var data: List[UInt8])",
   "summary": "",
   "url": "/docs/api/assets/#cursor-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "remaining",
   "qualified": "cinder.assets.cooked.Cursor.remaining",
   "kind": "method",
   "module": "cinder.assets.cooked",
   "parent": "Cursor",
   "signature": "remaining(self) -> Int",
   "summary": "Bytes left after the read position.",
   "url": "/docs/api/assets/#cursor-remaining",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "u8",
   "qualified": "cinder.assets.cooked.Cursor.u8",
   "kind": "method",
   "module": "cinder.assets.cooked",
   "parent": "Cursor",
   "signature": "u8(mut self) raises -> UInt8",
   "summary": "Reads one byte; raises at the end of the data.",
   "url": "/docs/api/assets/#cursor-u8",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "u32",
   "qualified": "cinder.assets.cooked.Cursor.u32",
   "kind": "method",
   "module": "cinder.assets.cooked",
   "parent": "Cursor",
   "signature": "u32(mut self) raises -> UInt32",
   "summary": "Reads a little-endian u32; raises when fewer than 4 bytes remain.",
   "url": "/docs/api/assets/#cursor-u32",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "f32",
   "qualified": "cinder.assets.cooked.Cursor.f32",
   "kind": "method",
   "module": "cinder.assets.cooked",
   "parent": "Cursor",
   "signature": "f32(mut self) raises -> Float32",
   "summary": "Reads a float32 from the bit pattern of a little-endian u32.",
   "url": "/docs/api/assets/#cursor-f32",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "bytes",
   "qualified": "cinder.assets.cooked.Cursor.bytes",
   "kind": "method",
   "module": "cinder.assets.cooked",
   "parent": "Cursor",
   "signature": "bytes(mut self, count: Int) raises -> List[UInt8]",
   "summary": "Copies the next count bytes; raises if count is negative or above remaining().",
   "url": "/docs/api/assets/#cursor-bytes",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "string",
   "qualified": "cinder.assets.cooked.Cursor.string",
   "kind": "method",
   "module": "cinder.assets.cooked",
   "parent": "Cursor",
   "signature": "string(mut self) raises -> String",
   "summary": "Reads a u32 byte length and that many bytes of UTF-8 text; raises when the length exceeds the data or the bytes are not valid UTF-8.",
   "url": "/docs/api/assets/#cursor-string",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "magic",
   "qualified": "cinder.assets.cooked.Cursor.magic",
   "kind": "method",
   "module": "cinder.assets.cooked",
   "parent": "Cursor",
   "signature": "magic(mut self, expected: String) raises",
   "summary": "Reads the bytes of expected; raises bad magic at the first mismatch.",
   "url": "/docs/api/assets/#cursor-magic",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "read_mesh",
   "qualified": "cinder.assets.cooked.read_mesh",
   "kind": "def",
   "module": "cinder.assets.cooked",
   "signature": "def read_mesh(var data: List[UInt8]) raises -> CookedMesh",
   "summary": "Parses .cmesh bytes into a CookedMesh, taking ownership of data. Raises on a wrong magic or version; stream lengths that disagree with the vertex count (56 bytes per vertex, 24 per skin vertex, 32 per vertex and morph target); index bytes not a multiple of 4; a LOD count outside 1..16; a LOD range outside the index buffer or not a multiple of 3; any index >= vertex count; truncated data or…",
   "url": "/docs/api/assets/#def-read_mesh",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "ClipChannel",
   "qualified": "cinder.assets.cooked.ClipChannel",
   "kind": "struct",
   "module": "cinder.assets.cooked",
   "signature": "struct ClipChannel(Copyable, Movable)",
   "summary": "Keyframes for one node property. path: 0 translation, 1 rotation, 2 scale, 3 weights. interpolation: 0 linear, 1 step, 2 cubic spline. values holds components floats per key (3 per cubic-spline key: in-tangent, value, out-tangent).",
   "url": "/docs/api/assets/#struct-clipchannel",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "Clip",
   "qualified": "cinder.assets.cooked.Clip",
   "kind": "struct",
   "module": "cinder.assets.cooked",
   "signature": "struct Clip(Copyable, Movable)",
   "summary": "A cooked animation clip: name, duration (the latest keyframe time) and its channels.",
   "url": "/docs/api/assets/#struct-clip",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.cooked.Clip.__init__",
   "kind": "method",
   "module": "cinder.assets.cooked",
   "parent": "Clip",
   "signature": "__init__(out self, name: String)",
   "summary": "",
   "url": "/docs/api/assets/#clip-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "write_clip",
   "qualified": "cinder.assets.cooked.write_clip",
   "kind": "def",
   "module": "cinder.assets.cooked",
   "signature": "def write_clip(clip: Clip) -> List[UInt8]",
   "summary": "Serialises a clip to .cclip bytes (version CLIP_VERSION, little-endian). Layout: magic, version, name, duration, channel count, then per channel its node, path, interpolation, components, key count and value count followed by the times and values.",
   "url": "/docs/api/assets/#def-write_clip",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "read_clip",
   "qualified": "cinder.assets.cooked.read_clip",
   "kind": "def",
   "module": "cinder.assets.cooked",
   "signature": "def read_clip(var data: List[UInt8]) raises -> Clip",
   "summary": "Parses .cclip bytes into a Clip, taking ownership of data. Raises on a wrong magic or version, more than 100000 channels, a path above 3, an interpolation above 2, components outside 1..64, a value count other than keys * components (* 3 for cubic spline), decreasing keyframe times, truncated data or trailing bytes. Node indices are not checked.",
   "url": "/docs/api/assets/#def-read_clip",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "CookedMaterial",
   "qualified": "cinder.assets.cooked.CookedMaterial",
   "kind": "struct",
   "module": "cinder.assets.cooked",
   "signature": "struct CookedMaterial(Copyable, Movable)",
   "summary": "Material parameters plus the logical image path per map slot (empty when absent).",
   "url": "/docs/api/assets/#struct-cookedmaterial",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.cooked.CookedMaterial.__init__",
   "kind": "method",
   "module": "cinder.assets.cooked",
   "parent": "CookedMaterial",
   "signature": "__init__(out self, var material: Material)",
   "summary": "",
   "url": "/docs/api/assets/#cookedmaterial-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "write_material",
   "qualified": "cinder.assets.cooked.write_material",
   "kind": "def",
   "module": "cinder.assets.cooked",
   "signature": "def write_material(cm: CookedMaterial) -> List[UInt8]",
   "summary": "Serialises a CookedMaterial to .cmat bytes (version MATERIAL_VERSION, little-endian). Layout: magic, version, name, factors, alpha mode and cutoff, double-sided flag, UV transform, then per map slot (5) the texcoord set and image path, then the sampler's linear-filter flag and address mode.",
   "url": "/docs/api/assets/#def-write_material",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "read_material",
   "qualified": "cinder.assets.cooked.read_material",
   "kind": "def",
   "module": "cinder.assets.cooked",
   "signature": "def read_material(var data: List[UInt8]) raises -> CookedMaterial",
   "summary": "Parses .cmat bytes into a CookedMaterial, taking ownership of data. Raises on a wrong magic or version, an alpha mode above 2, truncated data or trailing bytes. Only the parameters and image paths are read; AssetServer resolves the textures and creates the sampler.",
   "url": "/docs/api/assets/#def-read_material",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "gltf",
   "qualified": "cinder.assets.gltf",
   "kind": "module",
   "module": "cinder.assets.gltf",
   "signature": "",
   "summary": "glTF 2.0 import through cgltf: meshes (with tangents, second UV set, skinning, morph targets), metallic-roughness materials (KHR_texture_transform, KHR_materials_emissive_strength), images (file, data URI or GLB buffer view), nodes, skins and scenes. load_gltf produces a CPU-side GltfAsset; instantiate uploads it through a Renderer and fills a RenderScene with one instance per (node,…",
   "url": "/docs/api/assets/#cinderassetsgltf",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "GltfImage",
   "qualified": "cinder.assets.gltf.GltfImage",
   "kind": "struct",
   "module": "cinder.assets.gltf",
   "signature": "struct GltfImage(Copyable, Movable)",
   "summary": "An image decoded on the CPU by load_gltf, with its glTF name (empty when unnamed).",
   "url": "/docs/api/assets/#struct-gltfimage",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "GltfTexture",
   "qualified": "cinder.assets.gltf.GltfTexture",
   "kind": "struct",
   "module": "cinder.assets.gltf",
   "signature": "struct GltfTexture(ImplicitlyCopyable, Movable)",
   "summary": "A glTF texture: image index (-1 without one) plus sampler settings. linear_filter is True for a linear or unspecified magnification filter; address_mode is the WGPU address mode from the sampler's wrap_s (repeat when there is no sampler).",
   "url": "/docs/api/assets/#struct-gltftexture",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "GltfMaterial",
   "qualified": "cinder.assets.gltf.GltfMaterial",
   "kind": "struct",
   "module": "cinder.assets.gltf",
   "signature": "struct GltfMaterial(Copyable, Movable)",
   "summary": "Engine material parameters plus the asset texture index per map (-1 when absent).",
   "url": "/docs/api/assets/#struct-gltfmaterial",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.gltf.GltfMaterial.__init__",
   "kind": "method",
   "module": "cinder.assets.gltf",
   "parent": "GltfMaterial",
   "signature": "__init__(out self, var material: Material)",
   "summary": "",
   "url": "/docs/api/assets/#gltfmaterial-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "GltfPrimitive",
   "qualified": "cinder.assets.gltf.GltfPrimitive",
   "kind": "struct",
   "module": "cinder.assets.gltf",
   "signature": "struct GltfPrimitive(Copyable, Movable)",
   "summary": "A triangle primitive as validated MeshData and its material index (-1 when none). Point, line and strip primitives are dropped on import.",
   "url": "/docs/api/assets/#struct-gltfprimitive",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "GltfMesh",
   "qualified": "cinder.assets.gltf.GltfMesh",
   "kind": "struct",
   "module": "cinder.assets.gltf",
   "signature": "struct GltfMesh(Copyable, Movable)",
   "summary": "A glTF mesh: name, its triangle primitives and the mesh's default morph weights.",
   "url": "/docs/api/assets/#struct-gltfmesh",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "GltfNode",
   "qualified": "cinder.assets.gltf.GltfNode",
   "kind": "struct",
   "module": "cinder.assets.gltf",
   "signature": "struct GltfNode(Copyable, Movable)",
   "summary": "A scene node; every reference is an index into GltfAsset, -1 when absent. local and world are computed by cgltf at import (the world matrix walks the parents); weights are the node's morph weight overrides (empty when it has none).",
   "url": "/docs/api/assets/#struct-gltfnode",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "GltfSkin",
   "qualified": "cinder.assets.gltf.GltfSkin",
   "kind": "struct",
   "module": "cinder.assets.gltf",
   "signature": "struct GltfSkin(Copyable, Movable)",
   "summary": "Joint node indices and an inverse bind matrix each (identity where the file has none).",
   "url": "/docs/api/assets/#struct-gltfskin",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "GltfChannel",
   "qualified": "cinder.assets.gltf.GltfChannel",
   "kind": "struct",
   "module": "cinder.assets.gltf",
   "signature": "struct GltfChannel(Copyable, Movable)",
   "summary": "One animated node property. path: 0 translation, 1 rotation, 2 scale, 3 weights; interpolation: 0 linear, 1 step, 2 cubic spline (values hold in-tangent, value, out-tangent).",
   "url": "/docs/api/assets/#struct-gltfchannel",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "GltfAnimation",
   "qualified": "cinder.assets.gltf.GltfAnimation",
   "kind": "struct",
   "module": "cinder.assets.gltf",
   "signature": "struct GltfAnimation(Copyable, Movable)",
   "summary": "An animation: name, duration (latest keyframe time over its channels) and channels. Channels without a sampler, target node or supported target path are skipped on import.",
   "url": "/docs/api/assets/#struct-gltfanimation",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.gltf.GltfAnimation.__init__",
   "kind": "method",
   "module": "cinder.assets.gltf",
   "parent": "GltfAnimation",
   "signature": "__init__(out self, name: String)",
   "summary": "",
   "url": "/docs/api/assets/#gltfanimation-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "SceneBounds",
   "qualified": "cinder.assets.gltf.SceneBounds",
   "kind": "struct",
   "module": "cinder.assets.gltf",
   "signature": "struct SceneBounds(ImplicitlyCopyable, Movable)",
   "summary": "Axis-aligned box from GltfAsset.world_bounds; all zero when the asset has no meshes.",
   "url": "/docs/api/assets/#struct-scenebounds",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "centre",
   "qualified": "cinder.assets.gltf.SceneBounds.centre",
   "kind": "method",
   "module": "cinder.assets.gltf",
   "parent": "SceneBounds",
   "signature": "centre(self) -> Vec3",
   "summary": "Midpoint of the box.",
   "url": "/docs/api/assets/#scenebounds-centre",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "radius",
   "qualified": "cinder.assets.gltf.SceneBounds.radius",
   "kind": "method",
   "module": "cinder.assets.gltf",
   "parent": "SceneBounds",
   "signature": "radius(self) -> Float32",
   "summary": "Half the diagonal: the radius of the sphere around centre that encloses the box.",
   "url": "/docs/api/assets/#scenebounds-radius",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "GltfAsset",
   "qualified": "cinder.assets.gltf.GltfAsset",
   "kind": "struct",
   "module": "cinder.assets.gltf",
   "signature": "struct GltfAsset(Movable)",
   "summary": "Everything load_gltf imported from one file, CPU side; cross references are list indices. roots holds the default scene's root nodes, or every parentless node when the file has no default scene.",
   "url": "/docs/api/assets/#struct-gltfasset",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.gltf.GltfAsset.__init__",
   "kind": "method",
   "module": "cinder.assets.gltf",
   "parent": "GltfAsset",
   "signature": "__init__(out self, path: String)",
   "summary": "",
   "url": "/docs/api/assets/#gltfasset-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "world_bounds",
   "qualified": "cinder.assets.gltf.GltfAsset.world_bounds",
   "kind": "method",
   "module": "cinder.assets.gltf",
   "parent": "GltfAsset",
   "signature": "world_bounds(self) -> SceneBounds",
   "summary": "Axis-aligned bounds of every mesh instance in world space. Skinned meshes are posed on the CPU with their bind-pose joint matrices (what the GPU draws at rest).",
   "url": "/docs/api/assets/#gltfasset-world_bounds",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "load_gltf",
   "qualified": "cinder.assets.gltf.load_gltf",
   "kind": "def",
   "module": "cinder.assets.gltf",
   "signature": "def load_gltf(lib: NativePtr, path: String) raises -> GltfAsset",
   "summary": "Parses a .gltf or .glb file (and its buffers and images) into a GltfAsset.",
   "url": "/docs/api/assets/#def-load_gltf",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "UploadedGltf",
   "qualified": "cinder.assets.gltf.UploadedGltf",
   "kind": "struct",
   "module": "cinder.assets.gltf",
   "signature": "struct UploadedGltf(Movable)",
   "summary": "Renderer ids for an uploaded asset: mesh_ids[mesh][primitive], material_ids[material] and a default material for primitives without one.",
   "url": "/docs/api/assets/#struct-uploadedgltf",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.gltf.UploadedGltf.__init__",
   "kind": "method",
   "module": "cinder.assets.gltf",
   "parent": "UploadedGltf",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/assets/#uploadedgltf-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "upload_gltf",
   "qualified": "cinder.assets.gltf.upload_gltf",
   "kind": "def",
   "module": "cinder.assets.gltf",
   "signature": "def upload_gltf( mut renderer: Renderer, mut res: Resources, asset: GltfAsset, lods: Bool = True, ) raises -> UploadedGltf",
   "summary": "Uploads every image, material and primitive of asset to the renderer. Base colour and emissive images are sRGB; the rest are linear. Materials without textures share the renderer's default textures.",
   "url": "/docs/api/assets/#def-upload_gltf",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "instantiate",
   "qualified": "cinder.assets.gltf.instantiate",
   "kind": "def",
   "module": "cinder.assets.gltf",
   "signature": "def instantiate( mut renderer: Renderer, mut res: Resources, asset: GltfAsset, mut scene: RenderScene, lods: Bool = True, ) raises -> Int",
   "summary": "Uploads the asset and appends its instances, joints and morph weights to scene. Returns the number of instances added. Base colour and emissive images are sRGB; the rest are linear. Materials without textures share the renderer's default textures.",
   "url": "/docs/api/assets/#def-instantiate",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "runtime",
   "qualified": "cinder.assets.runtime",
   "kind": "module",
   "module": "cinder.assets.runtime",
   "signature": "",
   "summary": "Runtime asset server: asynchronous loading of cooked assets on the job system, reference counting, and hot reload. Loading a cooked mesh has two halves: a job reads and parses the file (CPU only, any thread) into a heap slot; update() on the main thread uploads finished slots to the GPU through the renderer and flips the handle to ready. Nothing GPU-related happens off the main thread. Each…",
   "url": "/docs/api/assets/#cinderassetsruntime",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "AssetState",
   "qualified": "cinder.assets.runtime.AssetState",
   "kind": "struct",
   "module": "cinder.assets.runtime",
   "signature": "struct AssetState(Equatable, ImplicitlyCopyable, RegisterPassable)",
   "summary": "Load state of an AssetServer record: loading, ready or failed.",
   "url": "/docs/api/assets/#struct-assetstate",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "loading",
   "qualified": "cinder.assets.runtime.AssetState.loading",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetState",
   "signature": "loading() -> AssetState",
   "summary": "Load started and not finished; a material also stays here while its textures load.",
   "url": "/docs/api/assets/#assetstate-loading",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "ready",
   "qualified": "cinder.assets.runtime.AssetState.ready",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetState",
   "signature": "ready() -> AssetState",
   "summary": "Loaded; the accessors return data.",
   "url": "/docs/api/assets/#assetstate-ready",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "failed",
   "qualified": "cinder.assets.runtime.AssetState.failed",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetState",
   "signature": "failed() -> AssetState",
   "summary": "The load failed (see AssetServer.error) or the record was released.",
   "url": "/docs/api/assets/#assetstate-failed",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "AssetRecord",
   "qualified": "cinder.assets.runtime.AssetRecord",
   "kind": "struct",
   "module": "cinder.assets.runtime",
   "signature": "struct AssetRecord(Movable)",
   "summary": "One logical asset known to an AssetServer and its loaded result. kind is 0 mesh, 1 clip, 2 texture, 3 material. Records are never removed: releasing the last reference leaves the record with state failed and error released (and an empty logical, so loading the path again makes a new record).",
   "url": "/docs/api/assets/#struct-assetrecord",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.runtime.AssetRecord.__init__",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetRecord",
   "signature": "__init__(out self, logical: String, file: String, kind: Int)",
   "summary": "",
   "url": "/docs/api/assets/#assetrecord-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "AssetServer",
   "qualified": "cinder.assets.runtime.AssetServer",
   "kind": "struct",
   "module": "cinder.assets.runtime",
   "signature": "struct AssetServer(Movable)",
   "summary": "Loads cooked assets listed in <root>/manifest.txt, shared by logical path and refcounted. Jobs only read, parse and transcode files; update does every GPU upload. All methods are main-thread calls (there are no locks). Indices from load_* stay valid for the server's lifetime. Dropping the server waits for all jobs but does not free the GPU resources of assets that were never released.",
   "url": "/docs/api/assets/#struct-assetserver",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.runtime.AssetServer.__init__",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "__init__( out self, lib: NativePtr, jobs: Pointer[JobSystem, MutUntrackedOrigin], renderer: Pointer[Renderer, MutUntrackedOrigin], root: String, ) raises",
   "summary": "",
   "url": "/docs/api/assets/#assetserver-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "load_mesh",
   "qualified": "cinder.assets.runtime.AssetServer.load_mesh",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "load_mesh(mut self, logical: String) raises -> Int",
   "summary": "Returns the asset index (also a reference). Loading starts immediately on a job. Raises when logical is not in the manifest or is known as another kind of asset. A known path returns its existing record (refcount + 1); one whose load failed is loaded again.",
   "url": "/docs/api/assets/#assetserver-load_mesh",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "load_clip",
   "qualified": "cinder.assets.runtime.AssetServer.load_clip",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "load_clip(mut self, logical: String) raises -> Int",
   "summary": "Returns the asset index of a cooked clip (also a reference); a job parses the file. Same sharing, kind check and retry of failed loads as load_mesh.",
   "url": "/docs/api/assets/#assetserver-load_clip",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "load_texture",
   "qualified": "cinder.assets.runtime.AssetServer.load_texture",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "load_texture(mut self, logical: String) raises -> Int",
   "summary": "Returns the asset index of a cooked KTX2 texture (also a reference). The job reads and transcodes it (BC7 when the device supports block compression, else RGBA8); update uploads it. Same sharing, kind check and retry of failed loads as load_mesh.",
   "url": "/docs/api/assets/#assetserver-load_texture",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "load_material",
   "qualified": "cinder.assets.runtime.AssetServer.load_material",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "load_material(mut self, logical: String) raises -> Int",
   "summary": "Loads a cooked material and every texture it references; ready when all of them are. Same sharing, kind check and retry of failed loads as load_mesh.",
   "url": "/docs/api/assets/#assetserver-load_material",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "material_index",
   "qualified": "cinder.assets.runtime.AssetServer.material_index",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "material_index(self, index: Int) raises -> Int",
   "summary": "Renderer material index of a ready material; raises otherwise.",
   "url": "/docs/api/assets/#assetserver-material_index",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "texture_view",
   "qualified": "cinder.assets.runtime.AssetServer.texture_view",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "texture_view(self, index: Int) raises -> TextureViewHandle",
   "summary": "View of a ready texture; raises otherwise. A hot reload destroys it for a new one.",
   "url": "/docs/api/assets/#assetserver-texture_view",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "update",
   "qualified": "cinder.assets.runtime.AssetServer.update",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "update(mut self) raises -> Int",
   "summary": "Main thread: finishes loads whose job completed (GPU upload for meshes). Returns how many assets became ready or failed this call.",
   "url": "/docs/api/assets/#assetserver-update",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "wait_all",
   "qualified": "cinder.assets.runtime.AssetServer.wait_all",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "wait_all(mut self) raises",
   "summary": "Blocks until every pending load is applied (tests, loading screens).",
   "url": "/docs/api/assets/#assetserver-wait_all",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "state",
   "qualified": "cinder.assets.runtime.AssetServer.state",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "state(self, index: Int) -> AssetState",
   "summary": "State of the record at index (failed once released).",
   "url": "/docs/api/assets/#assetserver-state",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "mesh_index",
   "qualified": "cinder.assets.runtime.AssetServer.mesh_index",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "mesh_index(self, index: Int) raises -> Int",
   "summary": "Renderer mesh index of a ready asset, stable across hot reloads; raises when not ready. The kind is not checked: a ready asset that is not a mesh returns -1.",
   "url": "/docs/api/assets/#assetserver-mesh_index",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "clip",
   "qualified": "cinder.assets.runtime.AssetServer.clip",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "clip(self, index: Int) raises -> Clip",
   "summary": "A copy of a ready clip with all its keyframes; raises when not a ready clip.",
   "url": "/docs/api/assets/#assetserver-clip",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "error",
   "qualified": "cinder.assets.runtime.AssetServer.error",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "error(self, index: Int) -> String",
   "summary": "Message of a failed load (released after the last release), empty otherwise.",
   "url": "/docs/api/assets/#assetserver-error",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "refcount",
   "qualified": "cinder.assets.runtime.AssetServer.refcount",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "refcount(self, index: Int) -> Int",
   "summary": "Outstanding references to the record at index; 0 once released.",
   "url": "/docs/api/assets/#assetserver-refcount",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "release",
   "qualified": "cinder.assets.runtime.AssetServer.release",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "release(mut self, index: Int) raises",
   "summary": "Drops one reference; the last one frees what the asset holds on the GPU (mesh, texture, renderer material and its sampler), releases a material's textures and forgets the asset.",
   "url": "/docs/api/assets/#assetserver-release",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "check_for_changes",
   "qualified": "cinder.assets.runtime.AssetServer.check_for_changes",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "check_for_changes(mut self) -> Int",
   "summary": "Starts a reload for every ready asset whose cooked file changed. Returns how many.",
   "url": "/docs/api/assets/#assetserver-check_for_changes",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "live_count",
   "qualified": "cinder.assets.runtime.AssetServer.live_count",
   "kind": "method",
   "module": "cinder.assets.runtime",
   "parent": "AssetServer",
   "signature": "live_count(self) -> Int",
   "summary": "Number of records with a positive refcount.",
   "url": "/docs/api/assets/#assetserver-live_count",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "textures",
   "qualified": "cinder.assets.textures",
   "kind": "module",
   "module": "cinder.assets.textures",
   "signature": "",
   "summary": "KTX2 textures: cooking (BasisU ETC1S or UASTC with full mip chains) and runtime loading (transcode to BC7 when the device has block compression, otherwise to RGBA8), through libktx.",
   "url": "/docs/api/assets/#cinderassetstextures",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "cook_texture_ktx2",
   "qualified": "cinder.assets.textures.cook_texture_ktx2",
   "kind": "def",
   "module": "cinder.assets.textures",
   "signature": "def cook_texture_ktx2( lib: NativePtr, img: Image, path: String, srgb: Bool, normal_map: Bool, uastc: Bool, quality: Int = 128, ) raises",
   "summary": "Writes img with a full mip chain as a BasisU-compressed KTX2 file. uastc picks the high-quality UASTC codec (normal maps, detail textures); otherwise ETC1S at quality (1..255). sRGB images carry the sRGB transfer function in the data format descriptor so loaders choose an sRGB GPU format.",
   "url": "/docs/api/assets/#def-cook_texture_ktx2",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "LoadedTexture",
   "qualified": "cinder.assets.textures.LoadedTexture",
   "kind": "struct",
   "module": "cinder.assets.textures",
   "signature": "struct LoadedTexture(Movable)",
   "summary": "A KTX2 file transcoded on the CPU: one byte list per mip level, ready for upload_loaded.",
   "url": "/docs/api/assets/#struct-loadedtexture",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.assets.textures.LoadedTexture.__init__",
   "kind": "method",
   "module": "cinder.assets.textures",
   "parent": "LoadedTexture",
   "signature": "__init__(out self, width: Int, height: Int, bc7: Bool, srgb: Bool)",
   "summary": "",
   "url": "/docs/api/assets/#loadedtexture-__init__",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "load_ktx2",
   "qualified": "cinder.assets.textures.load_ktx2",
   "kind": "def",
   "module": "cinder.assets.textures",
   "signature": "def load_ktx2( lib: NativePtr, path: String, prefer_bc7: Bool ) raises -> LoadedTexture",
   "summary": "Reads and transcodes a KTX2 file (CPU only; safe on a job thread).",
   "url": "/docs/api/assets/#def-load_ktx2",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "upload_loaded",
   "qualified": "cinder.assets.textures.upload_loaded",
   "kind": "def",
   "module": "cinder.assets.textures",
   "signature": "def upload_loaded( mut res: Resources, label: String, loaded: LoadedTexture ) raises -> Tuple[TextureHandle, TextureViewHandle]",
   "summary": "Creates the GPU texture (BC7 or RGBA8, sRGB variants when flagged) and uploads every level.",
   "url": "/docs/api/assets/#def-upload_loaded",
   "md": "/docs/api/assets.md"
  },
  {
   "name": "audio",
   "qualified": "cinder.audio",
   "kind": "module",
   "module": "cinder.audio",
   "signature": "",
   "summary": "Audio over miniaudio: buses, decoded and streamed sounds, one-shots, 3D spatialisation, a listener, and the ECS bridge that follows entities and the camera.",
   "url": "/docs/api/audio/#cinderaudio-1",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "engine",
   "qualified": "cinder.audio.engine",
   "kind": "module",
   "module": "cinder.audio.engine",
   "signature": "",
   "summary": "Audio over miniaudio: buses, decoded and streamed sounds, one-shots, 3D spatialisation and a listener. The engine can run headless (no device) for tests and servers; frames are then pulled with read_frames. Sounds live in the shim (miniaudio structs are opaque to Mojo) and are tracked here with generational handles. Release sounds with release and destroy the buses you created with…",
   "url": "/docs/api/audio/#cinderaudioengine",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "SoundHandle",
   "qualified": "cinder.audio.engine.SoundHandle",
   "kind": "struct",
   "module": "cinder.audio.engine",
   "signature": "struct SoundHandle(Equatable, ImplicitlyCopyable, Movable)",
   "summary": "Generational handle to a sound owned by AudioEngine: a slot index and that slot's generation. It goes stale once the sound is released (one-shots are released by AudioEngine.update without any call of yours); AudioEngine.is_valid tells, and every method that takes a stale handle raises.",
   "url": "/docs/api/audio/#struct-soundhandle",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "null",
   "qualified": "cinder.audio.engine.SoundHandle.null",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "SoundHandle",
   "signature": "null() -> SoundHandle",
   "summary": "The invalid handle (index -1); it converts to False.",
   "url": "/docs/api/audio/#soundhandle-null",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "Attenuation",
   "qualified": "cinder.audio.engine.Attenuation",
   "kind": "struct",
   "module": "cinder.audio.engine",
   "signature": "struct Attenuation(Equatable, ImplicitlyCopyable, Movable)",
   "summary": "Distance attenuation model of a spatial sound, mapped to miniaudio's models by AudioEngine.set_attenuation.",
   "url": "/docs/api/audio/#struct-attenuation",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "none",
   "qualified": "cinder.audio.engine.Attenuation.none",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "Attenuation",
   "signature": "none() -> Attenuation",
   "summary": "No distance attenuation.",
   "url": "/docs/api/audio/#attenuation-none",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "inverse",
   "qualified": "cinder.audio.engine.Attenuation.inverse",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "Attenuation",
   "signature": "inverse() -> Attenuation",
   "summary": "miniaudio's inverse-distance model; the SoundDesc default.",
   "url": "/docs/api/audio/#attenuation-inverse",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "linear",
   "qualified": "cinder.audio.engine.Attenuation.linear",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "Attenuation",
   "signature": "linear() -> Attenuation",
   "summary": "miniaudio's linear model.",
   "url": "/docs/api/audio/#attenuation-linear",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "exponential",
   "qualified": "cinder.audio.engine.Attenuation.exponential",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "Attenuation",
   "signature": "exponential() -> Attenuation",
   "summary": "miniaudio's exponential model.",
   "url": "/docs/api/audio/#attenuation-exponential",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "SoundDesc",
   "qualified": "cinder.audio.engine.SoundDesc",
   "kind": "struct",
   "module": "cinder.audio.engine",
   "signature": "struct SoundDesc(Copyable, Movable)",
   "summary": "How AudioEngine.load creates a sound. The constructor takes the file path, bus index, streamed, looping and spatial; the other fields keep their defaults until set on the value: volume 1, pitch 1, inverse attenuation with min_distance 1 m, max_distance 100 m and rolloff 1, not a one-shot. The attenuation settings apply only when spatial is set.",
   "url": "/docs/api/audio/#struct-sounddesc",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.audio.engine.SoundDesc.__init__",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "SoundDesc",
   "signature": "__init__( out self, path: String, bus: Int = 0, streamed: Bool = False, looping: Bool = False, spatial: Bool = True, )",
   "summary": "",
   "url": "/docs/api/audio/#sounddesc-__init__",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "AudioEngine",
   "qualified": "cinder.audio.engine.AudioEngine",
   "kind": "struct",
   "module": "cinder.audio.engine",
   "signature": "struct AudioEngine(Movable)",
   "summary": "Owns the miniaudio engine, its mixing buses and every loaded sound. Bus 0 is the master bus and lives as long as the engine; buses made with create_bus are destroyed with destroy_bus. Sounds are addressed by SoundHandle and freed with release (one-shots by update); the destructor frees whatever is left, but live_sounds() and live_buses() should be zero first. The NativePtr library must outlive…",
   "url": "/docs/api/audio/#struct-audioengine",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.audio.engine.AudioEngine.__init__",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "__init__( out self, lib: NativePtr, headless: Bool = False, sample_rate: Int = 48000, channels: Int = 2, ) raises",
   "summary": "",
   "url": "/docs/api/audio/#audioengine-__init__",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "create_bus",
   "qualified": "cinder.audio.engine.AudioEngine.create_bus",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "create_bus(mut self, name: String, parent: Int = 0) raises -> Int",
   "summary": "A mixing bus under parent (0 = master, -1 = the engine endpoint). Returns its index; destroy it with destroy_bus. Raises when parent does not exist (or was destroyed) or miniaudio fails to create the group.",
   "url": "/docs/api/audio/#audioengine-create_bus",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "destroy_bus",
   "qualified": "cinder.audio.engine.AudioEngine.destroy_bus",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "destroy_bus(mut self, bus: Int) raises",
   "summary": "Destroys a bus made with create_bus; its index stays invalid (indices are not reused) and live_buses() drops by one. Raises for the master bus (0, owned by the engine), a bus that does not exist or was already destroyed, and a bus that still has sounds or live child buses routed into it: release or destroy those first.",
   "url": "/docs/api/audio/#audioengine-destroy_bus",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "find_bus",
   "qualified": "cinder.audio.engine.AudioEngine.find_bus",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "find_bus(self, name: String) -> Int",
   "summary": "Index of the first live bus called name (the master bus is 0), or -1 when there is none.",
   "url": "/docs/api/audio/#audioengine-find_bus",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "set_bus_volume",
   "qualified": "cinder.audio.engine.AudioEngine.set_bus_volume",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "set_bus_volume(self, bus: Int, volume: Float32) raises",
   "summary": "Sets the linear volume of bus bus (1 is unity), which scales every sound and bus routed through it. Raises when the bus does not exist.",
   "url": "/docs/api/audio/#audioengine-set_bus_volume",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "bus_volume",
   "qualified": "cinder.audio.engine.AudioEngine.bus_volume",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "bus_volume(self, bus: Int) raises -> Float32",
   "summary": "Linear volume of bus bus. Raises when the bus does not exist.",
   "url": "/docs/api/audio/#audioengine-bus_volume",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "set_master_volume",
   "qualified": "cinder.audio.engine.AudioEngine.set_master_volume",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "set_master_volume(self, volume: Float32)",
   "summary": "Sets the engine's own output volume (linear), separate from the master bus volume; miniaudio's result code is ignored.",
   "url": "/docs/api/audio/#audioengine-set_master_volume",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "live_buses",
   "qualified": "cinder.audio.engine.AudioEngine.live_buses",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "live_buses(self) -> Int",
   "summary": "Buses created with create_bus and not yet destroyed with destroy_bus (the master bus is the engine's own); should be zero before the engine is destroyed.",
   "url": "/docs/api/audio/#audioengine-live_buses",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "load",
   "qualified": "cinder.audio.engine.AudioEngine.load",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "load(mut self, desc: SoundDesc) raises -> SoundHandle",
   "summary": "Creates a sound from a file (WAV, FLAC, MP3, Vorbis). It starts stopped.",
   "url": "/docs/api/audio/#audioengine-load",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "play_one_shot",
   "qualified": "cinder.audio.engine.AudioEngine.play_one_shot",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "play_one_shot( mut self, var desc: SoundDesc, position: Vec3 ) raises -> SoundHandle",
   "summary": "Loads, positions and starts a sound that is released when it ends.",
   "url": "/docs/api/audio/#audioengine-play_one_shot",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "release",
   "qualified": "cinder.audio.engine.AudioEngine.release",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "release(mut self, handle: SoundHandle) raises",
   "summary": "Destroys the sound and invalidates handle and its copies; the slot is reused with a new generation. Raises on a stale handle, so do not release a one-shot that update already released.",
   "url": "/docs/api/audio/#audioengine-release",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "is_valid",
   "qualified": "cinder.audio.engine.AudioEngine.is_valid",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "is_valid(self, handle: SoundHandle) -> Bool",
   "summary": "Whether handle refers to a live sound (in range, same generation, not released). Never raises.",
   "url": "/docs/api/audio/#audioengine-is_valid",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "live_sounds",
   "qualified": "cinder.audio.engine.AudioEngine.live_sounds",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "live_sounds(self) -> Int",
   "summary": "Number of sounds not yet released, one-shots included; should be zero before the engine is destroyed.",
   "url": "/docs/api/audio/#audioengine-live_sounds",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "play",
   "qualified": "cinder.audio.engine.AudioEngine.play",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "play(self, handle: SoundHandle) raises",
   "summary": "Starts the sound. Raises on a stale handle or when miniaudio fails to start it.",
   "url": "/docs/api/audio/#audioengine-play",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "stop",
   "qualified": "cinder.audio.engine.AudioEngine.stop",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "stop(self, handle: SoundHandle) raises",
   "summary": "Stops the sound without releasing it. Raises on a stale handle; miniaudio's result code is ignored.",
   "url": "/docs/api/audio/#audioengine-stop",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "is_playing",
   "qualified": "cinder.audio.engine.AudioEngine.is_playing",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "is_playing(self, handle: SoundHandle) raises -> Bool",
   "summary": "Whether the sound is playing. Raises on a stale handle.",
   "url": "/docs/api/audio/#audioengine-is_playing",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "at_end",
   "qualified": "cinder.audio.engine.AudioEngine.at_end",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "at_end(self, handle: SoundHandle) raises -> Bool",
   "summary": "Whether the sound has reached the end of its data. Raises on a stale handle.",
   "url": "/docs/api/audio/#audioengine-at_end",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "seek",
   "qualified": "cinder.audio.engine.AudioEngine.seek",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "seek(self, handle: SoundHandle, frame: Int) raises",
   "summary": "Moves the playback cursor to PCM frame frame. Raises on a stale handle; miniaudio's result code is ignored.",
   "url": "/docs/api/audio/#audioengine-seek",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "set_volume",
   "qualified": "cinder.audio.engine.AudioEngine.set_volume",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "set_volume(self, handle: SoundHandle, volume: Float32) raises",
   "summary": "Sets the sound's linear volume (1 is unity). Raises on a stale handle.",
   "url": "/docs/api/audio/#audioengine-set_volume",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "set_pitch",
   "qualified": "cinder.audio.engine.AudioEngine.set_pitch",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "set_pitch(self, handle: SoundHandle, pitch: Float32) raises",
   "summary": "Sets the sound's pitch multiplier (1 is the original pitch). Raises on a stale handle.",
   "url": "/docs/api/audio/#audioengine-set_pitch",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "set_pan",
   "qualified": "cinder.audio.engine.AudioEngine.set_pan",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "set_pan(self, handle: SoundHandle, pan: Float32) raises",
   "summary": "Sets the sound's stereo pan (-1 left, 0 centre, 1 right); the only positioning control of a non-spatial sound. Raises on a stale handle.",
   "url": "/docs/api/audio/#audioengine-set_pan",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "set_looping",
   "qualified": "cinder.audio.engine.AudioEngine.set_looping",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "set_looping(self, handle: SoundHandle, looping: Bool) raises",
   "summary": "Turns looping on or off. Raises on a stale handle.",
   "url": "/docs/api/audio/#audioengine-set_looping",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "fade",
   "qualified": "cinder.audio.engine.AudioEngine.fade",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "fade( self, handle: SoundHandle, from_volume: Float32, to_volume: Float32, milliseconds: Int, ) raises",
   "summary": "Fades the sound's volume from from_volume to to_volume over milliseconds. Raises on a stale handle.",
   "url": "/docs/api/audio/#audioengine-fade",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "set_position",
   "qualified": "cinder.audio.engine.AudioEngine.set_position",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "set_position(self, handle: SoundHandle, p: Vec3) raises",
   "summary": "Sets the sound's world position in metres (used while spatialisation is on). Raises on a stale handle.",
   "url": "/docs/api/audio/#audioengine-set_position",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "set_velocity",
   "qualified": "cinder.audio.engine.AudioEngine.set_velocity",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "set_velocity(self, handle: SoundHandle, v: Vec3) raises",
   "summary": "Sets the sound's velocity in metres per second, used for the Doppler effect. Raises on a stale handle.",
   "url": "/docs/api/audio/#audioengine-set_velocity",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "set_spatial",
   "qualified": "cinder.audio.engine.AudioEngine.set_spatial",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "set_spatial(self, handle: SoundHandle, enabled: Bool) raises",
   "summary": "Turns 3D spatialisation of the sound on or off. Raises on a stale handle.",
   "url": "/docs/api/audio/#audioengine-set_spatial",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "set_attenuation",
   "qualified": "cinder.audio.engine.AudioEngine.set_attenuation",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "set_attenuation( self, handle: SoundHandle, model: Attenuation, min_distance: Float32, max_distance: Float32, rolloff: Float32, ) raises",
   "summary": "Sets the distance attenuation: the model, min_distance and max_distance in metres and the rolloff factor. An unrecognised model value falls back to inverse. Raises on a stale handle.",
   "url": "/docs/api/audio/#audioengine-set_attenuation",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "set_listener",
   "qualified": "cinder.audio.engine.AudioEngine.set_listener",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "set_listener( self, position: Vec3, forward: Vec3, up: Vec3 = Vec3.unit_y(), velocity: Vec3 = Vec3.zero(), )",
   "summary": "Places miniaudio's listener 0: position in metres, the forward direction it faces, the world up and its velocity in metres per second (Doppler). The engine convention is -Z forward and +Y up; sync_audio calls this from the AudioListener entity.",
   "url": "/docs/api/audio/#audioengine-set_listener",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "update",
   "qualified": "cinder.audio.engine.AudioEngine.update",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "update(mut self) raises -> Int",
   "summary": "Drains the shim queue: log messages become diagnostics, finished sounds are recorded (and one-shots released). Returns the number of sounds that ended.",
   "url": "/docs/api/audio/#audioengine-update",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "take_ended",
   "qualified": "cinder.audio.engine.AudioEngine.take_ended",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "take_ended(mut self) -> List[SoundHandle]",
   "summary": "Returns the handles of sounds that ended since the last call and clears the list. Handles of one-shots are already stale when they are returned.",
   "url": "/docs/api/audio/#audioengine-take_ended",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "error_count",
   "qualified": "cinder.audio.engine.AudioEngine.error_count",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "error_count(self) -> Int",
   "summary": "Number of error-level records in diagnostics (miniaudio log messages collected by update).",
   "url": "/docs/api/audio/#audioengine-error_count",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "read_frames",
   "qualified": "cinder.audio.engine.AudioEngine.read_frames",
   "kind": "method",
   "module": "cinder.audio.engine",
   "parent": "AudioEngine",
   "signature": "read_frames(self, frames: Int) raises -> List[Float32]",
   "summary": "Headless engines: mixes frames interleaved float frames (tests, offline rendering).",
   "url": "/docs/api/audio/#audioengine-read_frames",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "sync",
   "qualified": "cinder.audio.sync",
   "kind": "module",
   "module": "cinder.audio.sync",
   "signature": "",
   "summary": "ECS <-> audio: AudioSource entities position their sounds, AudioListener places the listener (attach it to the camera entity so the listener follows the camera).",
   "url": "/docs/api/audio/#cinderaudiosync",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "AudioSource",
   "qualified": "cinder.audio.sync.AudioSource",
   "kind": "struct",
   "module": "cinder.audio.sync",
   "signature": "struct AudioSource(Component)",
   "summary": "A spatial sound that follows its entity. velocity feeds the Doppler effect.",
   "url": "/docs/api/audio/#struct-audiosource",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "component_id",
   "qualified": "cinder.audio.sync.AudioSource.component_id",
   "kind": "method",
   "module": "cinder.audio.sync",
   "parent": "AudioSource",
   "signature": "component_id() -> Int",
   "summary": "",
   "url": "/docs/api/audio/#audiosource-component_id",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "AudioListener",
   "qualified": "cinder.audio.sync.AudioListener",
   "kind": "struct",
   "module": "cinder.audio.sync",
   "signature": "struct AudioListener(Component)",
   "summary": "Marks the entity whose world transform drives the listener (position, -Z forward, +Y up). With several, the first one found wins.",
   "url": "/docs/api/audio/#struct-audiolistener",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "component_id",
   "qualified": "cinder.audio.sync.AudioListener.component_id",
   "kind": "method",
   "module": "cinder.audio.sync",
   "parent": "AudioListener",
   "signature": "component_id() -> Int",
   "summary": "",
   "url": "/docs/api/audio/#audiolistener-component_id",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "sync_audio",
   "qualified": "cinder.audio.sync.sync_audio",
   "kind": "def",
   "module": "cinder.audio.sync",
   "signature": "def sync_audio(world: World, audio: AudioEngine) raises -> Int",
   "summary": "Pushes entity transforms to the sounds and the listener. Returns the number of sources positioned; stale handles are skipped.",
   "url": "/docs/api/audio/#def-sync_audio",
   "md": "/docs/api/audio.md"
  },
  {
   "name": "core",
   "qualified": "cinder.core",
   "kind": "module",
   "module": "cinder.core",
   "signature": "",
   "summary": "Core: math, logging, assertions, allocators, containers, handles, time, file system. No I/O to GPU, audio or window systems lives here.",
   "url": "/docs/api/core/#cindercore-1",
   "md": "/docs/api/core.md"
  },
  {
   "name": "arena",
   "qualified": "cinder.core.arena",
   "kind": "module",
   "module": "cinder.core.arena",
   "signature": "",
   "summary": "LinearArena: a bump allocator for per-frame scratch memory. One block is allocated up front; alloc_bytes hands out aligned sub-ranges in O(1) and reset returns everything at once. There is no per-allocation free. After warm-up the engine's frame loop allocates only from arenas and pools, which is what makes the zero-allocation steady-state test possible.",
   "url": "/docs/api/core/#cindercorearena",
   "md": "/docs/api/core.md"
  },
  {
   "name": "LinearArena",
   "qualified": "cinder.core.arena.LinearArena",
   "kind": "struct",
   "module": "cinder.core.arena",
   "signature": "struct LinearArena(Movable)",
   "summary": "Bump allocator over one fixed block. Every address returned is aligned as requested.",
   "url": "/docs/api/core/#struct-lineararena",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.arena.LinearArena.__init__",
   "kind": "method",
   "module": "cinder.core.arena",
   "parent": "LinearArena",
   "signature": "__init__(out self, capacity: Int) raises",
   "summary": "Allocates capacity bytes once. Raises on a non-positive capacity.",
   "url": "/docs/api/core/#lineararena-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "capacity",
   "qualified": "cinder.core.arena.LinearArena.capacity",
   "kind": "method",
   "module": "cinder.core.arena",
   "parent": "LinearArena",
   "signature": "capacity(self) -> Int",
   "summary": "Usable bytes requested at construction; the 64-byte alignment slack is not counted.",
   "url": "/docs/api/core/#lineararena-capacity",
   "md": "/docs/api/core.md"
  },
  {
   "name": "used",
   "qualified": "cinder.core.arena.LinearArena.used",
   "kind": "method",
   "module": "cinder.core.arena",
   "parent": "LinearArena",
   "signature": "used(self) -> Int",
   "summary": "Bytes handed out since the last reset, including alignment padding.",
   "url": "/docs/api/core/#lineararena-used",
   "md": "/docs/api/core.md"
  },
  {
   "name": "high_water",
   "qualified": "cinder.core.arena.LinearArena.high_water",
   "kind": "method",
   "module": "cinder.core.arena",
   "parent": "LinearArena",
   "signature": "high_water(self) -> Int",
   "summary": "Largest used() ever observed; the number to size the arena by.",
   "url": "/docs/api/core/#lineararena-high_water",
   "md": "/docs/api/core.md"
  },
  {
   "name": "alloc_bytes",
   "qualified": "cinder.core.arena.LinearArena.alloc_bytes",
   "kind": "method",
   "module": "cinder.core.arena",
   "parent": "LinearArena",
   "signature": "alloc_bytes( mut self, size: Int, alignment: Int = 16 ) raises -> Pointer[UInt8, MutUntrackedOrigin]",
   "summary": "Returns size bytes aligned to alignment (a power of two <= 64). Raises when exhausted.",
   "url": "/docs/api/core/#lineararena-alloc_bytes",
   "md": "/docs/api/core.md"
  },
  {
   "name": "alloc",
   "qualified": "cinder.core.arena.LinearArena.alloc",
   "kind": "method",
   "module": "cinder.core.arena",
   "parent": "LinearArena",
   "signature": "alloc[ T: AnyType ](mut self, count: Int = 1) raises -> Pointer[T, MutUntrackedOrigin]",
   "summary": "Uninitialised storage for count values of T, aligned for T. The caller initialises it.",
   "url": "/docs/api/core/#lineararena-alloc",
   "md": "/docs/api/core.md"
  },
  {
   "name": "reset",
   "qualified": "cinder.core.arena.LinearArena.reset",
   "kind": "method",
   "module": "cinder.core.arena",
   "parent": "LinearArena",
   "signature": "reset(mut self)",
   "summary": "Makes the whole block available again. Previously returned pointers become dangling.",
   "url": "/docs/api/core/#lineararena-reset",
   "md": "/docs/api/core.md"
  },
  {
   "name": "assertions",
   "qualified": "cinder.core.assertions",
   "kind": "module",
   "module": "cinder.core.assertions",
   "signature": "",
   "summary": "Engine assertions: broken invariants abort with an explicit message. cinder_assert is compiled in unless the build defines CINDER_ASSERTS=0 (mojo build -D CINDER_ASSERTS=0), which release builds of the shipped game set and nothing else does. cinder_check is never compiled out and is used where the cost is negligible and the invariant guards memory safety (handle validation, FFI preconditions).…",
   "url": "/docs/api/core/#cindercoreassertions",
   "md": "/docs/api/core.md"
  },
  {
   "name": "cinder_assert",
   "qualified": "cinder.core.assertions.cinder_assert",
   "kind": "def",
   "module": "cinder.core.assertions",
   "signature": "def cinder_assert(condition: Bool, message: StaticString)",
   "summary": "Aborts with message when condition is false, unless asserts are compiled out.",
   "url": "/docs/api/core/#def-cinder_assert",
   "md": "/docs/api/core.md"
  },
  {
   "name": "cinder_check",
   "qualified": "cinder.core.assertions.cinder_check",
   "kind": "def",
   "module": "cinder.core.assertions",
   "signature": "def cinder_check(condition: Bool, message: StaticString)",
   "summary": "Aborts with message when condition is false, in every build.",
   "url": "/docs/api/core/#def-cinder_check",
   "md": "/docs/api/core.md"
  },
  {
   "name": "base64",
   "qualified": "cinder.core.base64",
   "kind": "module",
   "module": "cinder.core.base64",
   "signature": "",
   "summary": "Base64 decoding (RFC 4648, with or without padding) for data URIs in glTF files.",
   "url": "/docs/api/core/#cindercorebase64",
   "md": "/docs/api/core.md"
  },
  {
   "name": "decode_base64",
   "qualified": "cinder.core.base64.decode_base64",
   "kind": "def",
   "module": "cinder.core.base64",
   "signature": "def decode_base64(text: StringSpan) raises -> List[UInt8]",
   "summary": "Decodes base64 text; whitespace is skipped and '=' padding is optional.",
   "url": "/docs/api/core/#def-decode_base64",
   "md": "/docs/api/core.md"
  },
  {
   "name": "boxed",
   "qualified": "cinder.core.boxed",
   "kind": "module",
   "module": "cinder.core.boxed",
   "signature": "",
   "summary": "Boxed: a value at a stable heap address. Subsystems that hand out Pointers to themselves (Gfx, Resources, Renderer, JobSystem, ...) must never move once those pointers exist. Boxed[T] owns one T on the heap so the owner can move freely while the pointee stays put.",
   "url": "/docs/api/core/#cindercoreboxed",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Boxed",
   "qualified": "cinder.core.boxed.Boxed",
   "kind": "struct",
   "module": "cinder.core.boxed",
   "signature": "struct Boxed[T: Deinitable & Movable](Movable)",
   "summary": "Owns one T on the heap so pointers to it stay valid while the box itself moves. The value is moved in at construction and destroyed, then freed, when the box is destroyed. ptr() and [] give untracked mutable access; neither may outlive the box.",
   "url": "/docs/api/core/#struct-boxed",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.boxed.Boxed.__init__",
   "kind": "method",
   "module": "cinder.core.boxed",
   "parent": "Boxed",
   "signature": "__init__(out self, var value: Self.T)",
   "summary": "",
   "url": "/docs/api/core/#boxed-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "ptr",
   "qualified": "cinder.core.boxed.Boxed.ptr",
   "kind": "method",
   "module": "cinder.core.boxed",
   "parent": "Boxed",
   "signature": "ptr(self) -> Pointer[Self.T, MutUntrackedOrigin]",
   "summary": "A raw pointer valid for the box's lifetime.",
   "url": "/docs/api/core/#boxed-ptr",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__getitem__",
   "qualified": "cinder.core.boxed.Boxed.__getitem__",
   "kind": "method",
   "module": "cinder.core.boxed",
   "parent": "Boxed",
   "signature": "__getitem__(ref self) -> ref[MutUntrackedOrigin] Self.T",
   "summary": "",
   "url": "/docs/api/core/#boxed-__getitem__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "bytes",
   "qualified": "cinder.core.bytes",
   "kind": "module",
   "module": "cinder.core.bytes",
   "signature": "",
   "summary": "Little-endian byte packing for GPU uploads (std140/std430-style layouts are the caller's job).",
   "url": "/docs/api/core/#cindercorebytes",
   "md": "/docs/api/core.md"
  },
  {
   "name": "ByteWriter",
   "qualified": "cinder.core.bytes.ByteWriter",
   "kind": "struct",
   "module": "cinder.core.bytes",
   "signature": "struct ByteWriter(Movable, Sized)",
   "summary": "Appends plain values to a byte buffer. pad_to aligns the length for struct rules.",
   "url": "/docs/api/core/#struct-bytewriter",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.bytes.ByteWriter.__init__",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "__init__(out self, capacity: Int = 256)",
   "summary": "",
   "url": "/docs/api/core/#bytewriter-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__len__",
   "qualified": "cinder.core.bytes.ByteWriter.__len__",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "__len__(self) -> Int",
   "summary": "",
   "url": "/docs/api/core/#bytewriter-__len__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "clear",
   "qualified": "cinder.core.bytes.ByteWriter.clear",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "clear(mut self)",
   "summary": "Empties the buffer, keeping its capacity (same as reset).",
   "url": "/docs/api/core/#bytewriter-clear",
   "md": "/docs/api/core.md"
  },
  {
   "name": "u8",
   "qualified": "cinder.core.bytes.ByteWriter.u8",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "u8(mut self, v: UInt8)",
   "summary": "Appends one byte.",
   "url": "/docs/api/core/#bytewriter-u8",
   "md": "/docs/api/core.md"
  },
  {
   "name": "u32",
   "qualified": "cinder.core.bytes.ByteWriter.u32",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "u32(mut self, v: UInt32)",
   "summary": "Appends v as four bytes, little-endian.",
   "url": "/docs/api/core/#bytewriter-u32",
   "md": "/docs/api/core.md"
  },
  {
   "name": "i32",
   "qualified": "cinder.core.bytes.ByteWriter.i32",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "i32(mut self, v: Int32)",
   "summary": "Appends v as four bytes, little-endian two's complement.",
   "url": "/docs/api/core/#bytewriter-i32",
   "md": "/docs/api/core.md"
  },
  {
   "name": "f32",
   "qualified": "cinder.core.bytes.ByteWriter.f32",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "f32(mut self, v: Float32)",
   "summary": "Appends the IEEE-754 bits of v as four bytes, little-endian.",
   "url": "/docs/api/core/#bytewriter-f32",
   "md": "/docs/api/core.md"
  },
  {
   "name": "vec2",
   "qualified": "cinder.core.bytes.ByteWriter.vec2",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "vec2(mut self, v: Vec2)",
   "summary": "Appends x then y as two f32 (8 bytes, no padding).",
   "url": "/docs/api/core/#bytewriter-vec2",
   "md": "/docs/api/core.md"
  },
  {
   "name": "vec3",
   "qualified": "cinder.core.bytes.ByteWriter.vec3",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "vec3(mut self, v: Vec3)",
   "summary": "Three floats, no padding (callers add f32 or pad_to(16) for vec4 alignment).",
   "url": "/docs/api/core/#bytewriter-vec3",
   "md": "/docs/api/core.md"
  },
  {
   "name": "vec3_padded",
   "qualified": "cinder.core.bytes.ByteWriter.vec3_padded",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "vec3_padded(mut self, v: Vec3, w: Float32 = 0.0)",
   "summary": "Appends x, y, z, then w (default 0) as four f32: a vec3 in a 16-byte vec4 slot.",
   "url": "/docs/api/core/#bytewriter-vec3_padded",
   "md": "/docs/api/core.md"
  },
  {
   "name": "vec4",
   "qualified": "cinder.core.bytes.ByteWriter.vec4",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "vec4(mut self, v: Vec4)",
   "summary": "Appends x, y, z, w as four f32 (16 bytes).",
   "url": "/docs/api/core/#bytewriter-vec4",
   "md": "/docs/api/core.md"
  },
  {
   "name": "mat4",
   "qualified": "cinder.core.bytes.ByteWriter.mat4",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "mat4(mut self, m: Mat4)",
   "summary": "Column-major, matching WGSL mat4x4<f32>.",
   "url": "/docs/api/core/#bytewriter-mat4",
   "md": "/docs/api/core.md"
  },
  {
   "name": "pad_to",
   "qualified": "cinder.core.bytes.ByteWriter.pad_to",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "pad_to(mut self, alignment: Int)",
   "summary": "Zero-fills to the next multiple of alignment; no-op when already aligned. alignment must be positive: 0 or a negative value is a bug and cinder_assert aborts. With assertions compiled out it leaves the bytes unchanged.",
   "url": "/docs/api/core/#bytewriter-pad_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "span",
   "qualified": "cinder.core.bytes.ByteWriter.span",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "span(self) -> Span[UInt8, origin_of(self.bytes)]",
   "summary": "A view of the bytes written so far, borrowed from the writer; invalid after it changes.",
   "url": "/docs/api/core/#bytewriter-span",
   "md": "/docs/api/core.md"
  },
  {
   "name": "reset",
   "qualified": "cinder.core.bytes.ByteWriter.reset",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "reset(mut self)",
   "summary": "Empties the writer, keeping its capacity (frame scratch buffers).",
   "url": "/docs/api/core/#bytewriter-reset",
   "md": "/docs/api/core.md"
  },
  {
   "name": "take",
   "qualified": "cinder.core.bytes.ByteWriter.take",
   "kind": "method",
   "module": "cinder.core.bytes",
   "parent": "ByteWriter",
   "signature": "take(deinit self) -> List[UInt8]",
   "summary": "Consumes the writer and returns its bytes.",
   "url": "/docs/api/core/#bytewriter-take",
   "md": "/docs/api/core.md"
  },
  {
   "name": "cstring",
   "qualified": "cinder.core.cstring",
   "kind": "module",
   "module": "cinder.core.cstring",
   "signature": "",
   "summary": "C strings to Mojo Strings, decoding the bytes as UTF-8. C APIs (SDL, the shim, stb) hand back NUL-terminated UTF-8. Converting byte by byte with chr treats every byte as a code point and double-encodes anything outside ASCII, so every conversion goes through string_from_c instead.",
   "url": "/docs/api/core/#cindercorecstring",
   "md": "/docs/api/core.md"
  },
  {
   "name": "string_from_c",
   "qualified": "cinder.core.cstring.string_from_c",
   "kind": "def",
   "module": "cinder.core.cstring",
   "signature": "def string_from_c( p: Optional[Pointer[c_char, MutUntrackedOrigin]], max_len: Int = -1 ) -> String",
   "summary": "The UTF-8 text at p up to its NUL terminator, or up to max_len bytes when max_len is not negative (fixed-size C buffers). A null pointer gives the empty string. Invalid UTF-8 sequences become U+FFFD instead of failing: C text is diagnostic data here and must never make the caller raise. The caller guarantees p points at a terminated string or at least max_len readable bytes.",
   "url": "/docs/api/core/#def-string_from_c",
   "md": "/docs/api/core.md"
  },
  {
   "name": "fs",
   "qualified": "cinder.core.fs",
   "kind": "module",
   "module": "cinder.core.fs",
   "signature": "",
   "summary": "Filesystem helpers with typed errors. Thin on purpose: the asset database layers on top.",
   "url": "/docs/api/core/#cindercorefs",
   "md": "/docs/api/core.md"
  },
  {
   "name": "FileError",
   "qualified": "cinder.core.fs.FileError",
   "kind": "struct",
   "module": "cinder.core.fs",
   "signature": "struct FileError(Copyable, Movable, Writable)",
   "summary": "A failed file operation, with the path and the underlying message.",
   "url": "/docs/api/core/#struct-fileerror",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.core.fs.FileError.write_to",
   "kind": "method",
   "module": "cinder.core.fs",
   "parent": "FileError",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/core/#fileerror-write_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "file_exists",
   "qualified": "cinder.core.fs.file_exists",
   "kind": "def",
   "module": "cinder.core.fs",
   "signature": "def file_exists(path: String) -> Bool",
   "summary": "True when something exists at path (a file or a directory). Never raises.",
   "url": "/docs/api/core/#def-file_exists",
   "md": "/docs/api/core.md"
  },
  {
   "name": "read_bytes",
   "qualified": "cinder.core.fs.read_bytes",
   "kind": "def",
   "module": "cinder.core.fs",
   "signature": "def read_bytes(path: String) raises FileError -> List[UInt8]",
   "summary": "Reads a whole file into memory.",
   "url": "/docs/api/core/#def-read_bytes",
   "md": "/docs/api/core.md"
  },
  {
   "name": "read_text",
   "qualified": "cinder.core.fs.read_text",
   "kind": "def",
   "module": "cinder.core.fs",
   "signature": "def read_text(path: String) raises FileError -> String",
   "summary": "Reads a whole UTF-8 text file.",
   "url": "/docs/api/core/#def-read_text",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_bytes",
   "qualified": "cinder.core.fs.write_bytes",
   "kind": "def",
   "module": "cinder.core.fs",
   "signature": "def write_bytes(path: String, data: Span[UInt8, _]) raises FileError",
   "summary": "Writes (truncating) data to path.",
   "url": "/docs/api/core/#def-write_bytes",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_text",
   "qualified": "cinder.core.fs.write_text",
   "kind": "def",
   "module": "cinder.core.fs",
   "signature": "def write_text(path: String, text: String) raises FileError",
   "summary": "Writes (truncating) text to path. Raises FileError carrying the path on failure.",
   "url": "/docs/api/core/#def-write_text",
   "md": "/docs/api/core.md"
  },
  {
   "name": "handles",
   "qualified": "cinder.core.handles",
   "kind": "module",
   "module": "cinder.core.handles",
   "signature": "",
   "summary": "Generational handles and the slot pool that issues them. A Handle[Tag] names a slot in a Pool[T, Tag]. The generation counter makes a stale handle (one whose slot was freed and reused) fail validation instead of aliasing a new object. Tag is a phantom type so that, for example, a texture handle cannot be passed where a buffer handle is expected.",
   "url": "/docs/api/core/#cindercorehandles",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Handle",
   "qualified": "cinder.core.handles.Handle",
   "kind": "struct",
   "module": "cinder.core.handles",
   "signature": "struct Handle[Tag: AnyType]( Boolable, Equatable, Hashable, ImplicitlyCopyable, RegisterPassable, Writable, )",
   "summary": "A 64-bit generational handle: 32-bit slot index, 32-bit generation. Zero is the null handle.",
   "url": "/docs/api/core/#struct-handle",
   "md": "/docs/api/core.md"
  },
  {
   "name": "null",
   "qualified": "cinder.core.handles.Handle.null",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Handle",
   "signature": "null() -> Handle[Self.Tag]",
   "summary": "The null handle (index 0, generation 0); never valid in any Pool.",
   "url": "/docs/api/core/#handle-null",
   "md": "/docs/api/core.md"
  },
  {
   "name": "is_null",
   "qualified": "cinder.core.handles.Handle.is_null",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Handle",
   "signature": "is_null(self) -> Bool",
   "summary": "True when the generation is 0, whatever the index; pools never issue generation 0.",
   "url": "/docs/api/core/#handle-is_null",
   "md": "/docs/api/core.md"
  },
  {
   "name": "packed",
   "qualified": "cinder.core.handles.Handle.packed",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Handle",
   "signature": "packed(self) -> UInt64",
   "summary": "The handle as one integer, for serialization and GPU-side ids.",
   "url": "/docs/api/core/#handle-packed",
   "md": "/docs/api/core.md"
  },
  {
   "name": "from_packed",
   "qualified": "cinder.core.handles.Handle.from_packed",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Handle",
   "signature": "from_packed(v: UInt64) -> Handle[Self.Tag]",
   "summary": "Inverse of packed(): low 32 bits are the index, high 32 bits the generation.",
   "url": "/docs/api/core/#handle-from_packed",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.core.handles.Handle.write_to",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Handle",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/core/#handle-write_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Pool",
   "qualified": "cinder.core.handles.Pool",
   "kind": "struct",
   "module": "cinder.core.handles",
   "signature": "struct Pool[T: Copyable & Deinitable, Tag: AnyType](Movable)",
   "summary": "A slot map: O(1) insert, remove and lookup by Handle[Self.Tag], with generation checking. Slots are never reallocated once created, so a Pool holds at most capacity live values; insert raises when full, which keeps steady-state frames free of allocation (section 4 of the brief). Freed slots are recycled through an intrusive free list. Generations start at 1 and skip 0 so the zero handle is…",
   "url": "/docs/api/core/#struct-pool",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.handles.Pool.__init__",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Pool",
   "signature": "__init__(out self, capacity: Int) raises",
   "summary": "Creates a pool with room for capacity values (1 <= capacity < 2^32).",
   "url": "/docs/api/core/#pool-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "capacity",
   "qualified": "cinder.core.handles.Pool.capacity",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Pool",
   "signature": "capacity(self) -> Int",
   "summary": "Number of slots, fixed at construction; the pool never grows past it.",
   "url": "/docs/api/core/#pool-capacity",
   "md": "/docs/api/core.md"
  },
  {
   "name": "live",
   "qualified": "cinder.core.handles.Pool.live",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Pool",
   "signature": "live(self) -> Int",
   "summary": "Number of values currently stored.",
   "url": "/docs/api/core/#pool-live",
   "md": "/docs/api/core.md"
  },
  {
   "name": "insert",
   "qualified": "cinder.core.handles.Pool.insert",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Pool",
   "signature": "insert(mut self, var value: Self.T) raises -> Handle[Self.Tag]",
   "summary": "Stores value and returns its handle. Raises when the pool is full.",
   "url": "/docs/api/core/#pool-insert",
   "md": "/docs/api/core.md"
  },
  {
   "name": "is_valid",
   "qualified": "cinder.core.handles.Pool.is_valid",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Pool",
   "signature": "is_valid(self, h: Handle[Self.Tag]) -> Bool",
   "summary": "True when h names a live value (right slot, current generation).",
   "url": "/docs/api/core/#pool-is_valid",
   "md": "/docs/api/core.md"
  },
  {
   "name": "get",
   "qualified": "cinder.core.handles.Pool.get",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Pool",
   "signature": "get(self, h: Handle[Self.Tag]) raises -> Self.T",
   "summary": "A copy of the value behind h; raises on a null, stale or foreign handle. Pooled values are small records (handles, descriptors), so copying is the intended access pattern; update writes a value back.",
   "url": "/docs/api/core/#pool-get",
   "md": "/docs/api/core.md"
  },
  {
   "name": "update",
   "qualified": "cinder.core.handles.Pool.update",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Pool",
   "signature": "update(mut self, h: Handle[Self.Tag], var value: Self.T) raises",
   "summary": "Replaces the value behind h; raises on an invalid handle.",
   "url": "/docs/api/core/#pool-update",
   "md": "/docs/api/core.md"
  },
  {
   "name": "remove",
   "qualified": "cinder.core.handles.Pool.remove",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Pool",
   "signature": "remove(mut self, h: Handle[Self.Tag]) raises -> Self.T",
   "summary": "Removes and returns the value behind h, retiring the handle's generation.",
   "url": "/docs/api/core/#pool-remove",
   "md": "/docs/api/core.md"
  },
  {
   "name": "handles",
   "qualified": "cinder.core.handles.Pool.handles",
   "kind": "method",
   "module": "cinder.core.handles",
   "parent": "Pool",
   "signature": "handles(self) -> List[Handle[Self.Tag]]",
   "summary": "Handles of every live value, in slot order (allocates; for tools and tests).",
   "url": "/docs/api/core/#pool-handles",
   "md": "/docs/api/core.md"
  },
  {
   "name": "hash",
   "qualified": "cinder.core.hash",
   "kind": "module",
   "module": "cinder.core.hash",
   "signature": "",
   "summary": "Content hashing: 64-bit FNV-1a over bytes and strings (stable across runs and platforms).",
   "url": "/docs/api/core/#cindercorehash",
   "md": "/docs/api/core.md"
  },
  {
   "name": "fnv1a64",
   "qualified": "cinder.core.hash.fnv1a64",
   "kind": "def",
   "module": "cinder.core.hash",
   "signature": "def fnv1a64(data: Span[UInt8, _]) -> UInt64",
   "summary": "64-bit FNV-1a of data. Stable across runs and platforms, which is why the asset cooker uses it as a content hash. Not cryptographic: do not use it where collisions could be engineered.",
   "url": "/docs/api/core/#def-fnv1a64",
   "md": "/docs/api/core.md"
  },
  {
   "name": "fnv1a64_string",
   "qualified": "cinder.core.hash.fnv1a64_string",
   "kind": "def",
   "module": "cinder.core.hash",
   "signature": "def fnv1a64_string(text: String) -> UInt64",
   "summary": "fnv1a64 of the string's UTF-8 bytes, without a terminator.",
   "url": "/docs/api/core/#def-fnv1a64_string",
   "md": "/docs/api/core.md"
  },
  {
   "name": "hex64",
   "qualified": "cinder.core.hash.hex64",
   "kind": "def",
   "module": "cinder.core.hash",
   "signature": "def hex64(v: UInt64) -> String",
   "summary": "Sixteen lowercase hex digits.",
   "url": "/docs/api/core/#def-hex64",
   "md": "/docs/api/core.md"
  },
  {
   "name": "image",
   "qualified": "cinder.core.image",
   "kind": "module",
   "module": "cinder.core.image",
   "signature": "",
   "summary": "CPU images: RGBA8 load/decode/save through the shim (stb) and perceptual comparison (SSIM). Image owns its pixels in a List[UInt8] (tightly packed RGBA8). ssim is the structural similarity index on luma with an 8x8 box window; golden-image tests compare against it.",
   "url": "/docs/api/core/#cindercoreimage",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Image",
   "qualified": "cinder.core.image.Image",
   "kind": "struct",
   "module": "cinder.core.image",
   "signature": "struct Image(Copyable, Movable)",
   "summary": "A tightly packed RGBA8 image.",
   "url": "/docs/api/core/#struct-image",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.image.Image.__init__",
   "kind": "method",
   "module": "cinder.core.image",
   "parent": "Image",
   "signature": "__init__(out self, width: Int, height: Int)",
   "summary": "",
   "url": "/docs/api/core/#image-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.image.Image.__init__",
   "kind": "method",
   "module": "cinder.core.image",
   "parent": "Image",
   "signature": "__init__( out self, width: Int, height: Int, var pixels: List[UInt8] ) raises",
   "summary": "",
   "url": "/docs/api/core/#image-__init__-1",
   "md": "/docs/api/core.md"
  },
  {
   "name": "from_rows",
   "qualified": "cinder.core.image.Image.from_rows",
   "kind": "method",
   "module": "cinder.core.image",
   "parent": "Image",
   "signature": "from_rows( width: Int, height: Int, rows: List[UInt8], stride: Int ) raises -> Image",
   "summary": "Repacks rows of stride bytes (GPU readback with 256-byte alignment) into a tight image.",
   "url": "/docs/api/core/#image-from_rows",
   "md": "/docs/api/core.md"
  },
  {
   "name": "pixel",
   "qualified": "cinder.core.image.Image.pixel",
   "kind": "method",
   "module": "cinder.core.image",
   "parent": "Image",
   "signature": "pixel(self, x: Int, y: Int) -> SIMD[DType.uint8, 4]",
   "summary": "The RGBA8 value at column x, row y; (0, 0) is the first pixel in memory. x must be in [0, width) and y in [0, height). Anything else is a bug and aborts through cinder_check in every build (an unchecked index would read outside the pixel list, or silently wrap into the next row).",
   "url": "/docs/api/core/#image-pixel",
   "md": "/docs/api/core.md"
  },
  {
   "name": "set_pixel",
   "qualified": "cinder.core.image.Image.set_pixel",
   "kind": "method",
   "module": "cinder.core.image",
   "parent": "Image",
   "signature": "set_pixel(mut self, x: Int, y: Int, value: SIMD[DType.uint8, 4])",
   "summary": "Writes RGBA8 value at column x, row y; addressed and range-checked like pixel.",
   "url": "/docs/api/core/#image-set_pixel",
   "md": "/docs/api/core.md"
  },
  {
   "name": "swap_rb",
   "qualified": "cinder.core.image.Image.swap_rb",
   "kind": "method",
   "module": "cinder.core.image",
   "parent": "Image",
   "signature": "swap_rb(mut self)",
   "summary": "BGRA <-> RGBA in place (swapchain readbacks are BGRA).",
   "url": "/docs/api/core/#image-swap_rb",
   "md": "/docs/api/core.md"
  },
  {
   "name": "luma",
   "qualified": "cinder.core.image.Image.luma",
   "kind": "method",
   "module": "cinder.core.image",
   "parent": "Image",
   "signature": "luma(self, x: Int, y: Int) -> Float64",
   "summary": "Rec. 709 luma of the pixel at (x, y) in [0, 255], from the stored (gamma-encoded) values; alpha is ignored. compare computes SSIM on this value.",
   "url": "/docs/api/core/#image-luma",
   "md": "/docs/api/core.md"
  },
  {
   "name": "load_image",
   "qualified": "cinder.core.image.load_image",
   "kind": "def",
   "module": "cinder.core.image",
   "signature": "def load_image(lib: NativePtr, path: String) raises -> Image",
   "summary": "Loads the image file at path through the shim's stb_image and returns it as RGBA8. Any channel count in the file is expanded to four. lib must point at the loaded native shim. Raises with stb's failure reason when the file cannot be read or decoded. The stb buffer is copied into the Image and freed before returning.",
   "url": "/docs/api/core/#def-load_image",
   "md": "/docs/api/core.md"
  },
  {
   "name": "decode_image",
   "qualified": "cinder.core.image.decode_image",
   "kind": "def",
   "module": "cinder.core.image",
   "signature": "def decode_image(lib: NativePtr, bytes: Span[UInt8, _]) raises -> Image",
   "summary": "Decodes an encoded image held in memory (stb_image) to RGBA8. Raises with stb's failure reason on undecodable data; the shim also rejects inputs larger than 2^31 - 1 bytes. The stb buffer is copied into the Image and freed before returning.",
   "url": "/docs/api/core/#def-decode_image",
   "md": "/docs/api/core.md"
  },
  {
   "name": "save_png",
   "qualified": "cinder.core.image.save_png",
   "kind": "def",
   "module": "cinder.core.image",
   "signature": "def save_png(lib: NativePtr, path: String, img: Image) raises",
   "summary": "Writes img to path as an RGBA8 PNG through the shim's stb_image_write. Raises when the file cannot be written; the shim also refuses an image with zero width or height.",
   "url": "/docs/api/core/#def-save_png",
   "md": "/docs/api/core.md"
  },
  {
   "name": "ImageDiff",
   "qualified": "cinder.core.image.ImageDiff",
   "kind": "struct",
   "module": "cinder.core.image",
   "signature": "struct ImageDiff(ImplicitlyCopyable, Movable, Writable)",
   "summary": "Result of compare: SSIM on luma, plus the raw pixel statistics tests may also bound.",
   "url": "/docs/api/core/#struct-imagediff",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.core.image.ImageDiff.write_to",
   "kind": "method",
   "module": "cinder.core.image",
   "parent": "ImageDiff",
   "signature": "write_to(self, mut w: Some[Writer])",
   "summary": "",
   "url": "/docs/api/core/#imagediff-write_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "compare",
   "qualified": "cinder.core.image.compare",
   "kind": "def",
   "module": "cinder.core.image",
   "signature": "def compare( a: Image, b: Image, tolerance: Int = 2, window: Int = 8 ) raises -> ImageDiff",
   "summary": "SSIM (luma, non-overlapping window boxes, K1 = 0.01, K2 = 0.03, L = 255) and pixel deltas.",
   "url": "/docs/api/core/#def-compare",
   "md": "/docs/api/core.md"
  },
  {
   "name": "jobs",
   "qualified": "cinder.core.jobs",
   "kind": "module",
   "module": "cinder.core.jobs",
   "signature": "",
   "summary": "The job system: a work-stealing thread pool with dependency counters. Design (ADR-0008, docs/THREADING.md): - One worker per logical core minus one (the main thread is the remaining core), each with a fixed-capacity Chase-Lev deque of job indices. A worker pushes and pops at the bottom of its own deque; idle workers steal from the top of others'. - Jobs are JobFn thin function pointers plus an…",
   "url": "/docs/api/core/#cindercorejobs",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Counter",
   "qualified": "cinder.core.jobs.Counter",
   "kind": "struct",
   "module": "cinder.core.jobs",
   "signature": "struct Counter(Movable)",
   "summary": "Completion counter: incremented per submitted job, decremented when each finishes.",
   "url": "/docs/api/core/#struct-counter",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.jobs.Counter.__init__",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "Counter",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/core/#counter-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "load",
   "qualified": "cinder.core.jobs.Counter.load",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "Counter",
   "signature": "load(self) -> Int32",
   "summary": "Jobs still outstanding on this counter (acquire load); 0 when all have finished.",
   "url": "/docs/api/core/#counter-load",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Job",
   "qualified": "cinder.core.jobs.Job",
   "kind": "struct",
   "module": "cinder.core.jobs",
   "signature": "struct Job(ImplicitlyCopyable, Movable)",
   "summary": "One unit of work in the job table.",
   "url": "/docs/api/core/#struct-job",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.jobs.Job.__init__",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "Job",
   "signature": "__init__( out self, run: JobFn, data: Pointer[NoneType, MutUntrackedOrigin], counter: Optional[Pointer[Counter, MutUntrackedOrigin]], )",
   "summary": "",
   "url": "/docs/api/core/#job-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Deque",
   "qualified": "cinder.core.jobs.Deque",
   "kind": "struct",
   "module": "cinder.core.jobs",
   "signature": "struct Deque(Movable)",
   "summary": "Chase-Lev work-stealing deque of job indices with a fixed power-of-two capacity. The owner thread calls push and pop; any thread calls steal. Indices wrap through the mask; push fails when the deque is full instead of growing.",
   "url": "/docs/api/core/#struct-deque",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.jobs.Deque.__init__",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "Deque",
   "signature": "__init__(out self, capacity: Int)",
   "summary": "",
   "url": "/docs/api/core/#deque-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "push",
   "qualified": "cinder.core.jobs.Deque.push",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "Deque",
   "signature": "push(mut self, job: Int32) -> Bool",
   "summary": "Owner only. Returns False when full.",
   "url": "/docs/api/core/#deque-push",
   "md": "/docs/api/core.md"
  },
  {
   "name": "pop",
   "qualified": "cinder.core.jobs.Deque.pop",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "Deque",
   "signature": "pop(mut self) -> Int32",
   "summary": "Owner only. Returns INVALID_JOB when empty.",
   "url": "/docs/api/core/#deque-pop",
   "md": "/docs/api/core.md"
  },
  {
   "name": "steal",
   "qualified": "cinder.core.jobs.Deque.steal",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "Deque",
   "signature": "steal(mut self) -> Int32",
   "summary": "Any thread. Returns INVALID_JOB when empty or when it lost a race (caller retries elsewhere).",
   "url": "/docs/api/core/#deque-steal",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Shared",
   "qualified": "cinder.core.jobs.Shared",
   "kind": "struct",
   "module": "cinder.core.jobs",
   "signature": "struct Shared(Movable)",
   "summary": "State shared by all workers; lives at a stable heap address for the system's lifetime.",
   "url": "/docs/api/core/#struct-shared",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.jobs.Shared.__init__",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "Shared",
   "signature": "__init__( out self, worker_count: Int, job_capacity: Int, semaphore: Optional[Pointer[CnSemaphore, MutUntrackedOrigin]], lib: Pointer[CinderNative, MutUntrackedOrigin], )",
   "summary": "",
   "url": "/docs/api/core/#shared-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "WorkerContext",
   "qualified": "cinder.core.jobs.WorkerContext",
   "kind": "struct",
   "module": "cinder.core.jobs",
   "signature": "struct WorkerContext(Movable)",
   "summary": "Passed to each worker thread entry: which deque is mine and where the shared state lives.",
   "url": "/docs/api/core/#struct-workercontext",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.jobs.WorkerContext.__init__",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "WorkerContext",
   "signature": "__init__( out self, shared: Pointer[Shared, MutUntrackedOrigin], index: Int )",
   "summary": "",
   "url": "/docs/api/core/#workercontext-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "JobSystem",
   "qualified": "cinder.core.jobs.JobSystem",
   "kind": "struct",
   "module": "cinder.core.jobs",
   "signature": "struct JobSystem(Movable)",
   "summary": "Owns the worker threads, the shared state and the job table. Deque 0 belongs to the main thread. Hold one instance for the life of the program (section 4: the job system runs everything that is not SDL or presentation). __deinit__ stops and joins every worker.",
   "url": "/docs/api/core/#struct-jobsystem",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.jobs.JobSystem.__init__",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "JobSystem",
   "signature": "__init__( out self, lib: Pointer[CinderNative, MutUntrackedOrigin], worker_count: Int, job_capacity: Int = 1 << 14, ) raises",
   "summary": "Starts worker_count workers (0 runs everything on the calling thread). job_capacity must be a power of two; it bounds the number of jobs in flight between reset calls.",
   "url": "/docs/api/core/#jobsystem-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "worker_count",
   "qualified": "cinder.core.jobs.JobSystem.worker_count",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "JobSystem",
   "signature": "worker_count(self) -> Int",
   "summary": "Number of worker threads started, not counting the main thread (which owns deque 0).",
   "url": "/docs/api/core/#jobsystem-worker_count",
   "md": "/docs/api/core.md"
  },
  {
   "name": "executed",
   "qualified": "cinder.core.jobs.JobSystem.executed",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "JobSystem",
   "signature": "executed(self) -> Int",
   "summary": "Jobs completed since construction (diagnostics).",
   "url": "/docs/api/core/#jobsystem-executed",
   "md": "/docs/api/core.md"
  },
  {
   "name": "submit",
   "qualified": "cinder.core.jobs.JobSystem.submit",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "JobSystem",
   "signature": "submit( mut self, run: JobFn, data: Pointer[NoneType, MutUntrackedOrigin], counter: Optional[Pointer[Counter, MutUntrackedOrigin]], ) -> Bool",
   "summary": "Queues a job from the main thread. Increments counter before the job can run. Returns False when the job table or the main deque is full; the caller must then run it inline.",
   "url": "/docs/api/core/#jobsystem-submit",
   "md": "/docs/api/core.md"
  },
  {
   "name": "wait",
   "qualified": "cinder.core.jobs.JobSystem.wait",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "JobSystem",
   "signature": "wait(mut self, counter: Pointer[Counter, MutUntrackedOrigin])",
   "summary": "Runs jobs on the calling thread until counter reaches zero.",
   "url": "/docs/api/core/#jobsystem-wait",
   "md": "/docs/api/core.md"
  },
  {
   "name": "reset",
   "qualified": "cinder.core.jobs.JobSystem.reset",
   "kind": "method",
   "module": "cinder.core.jobs",
   "parent": "JobSystem",
   "signature": "reset(mut self)",
   "summary": "Recycles the job table. Only valid when no job is queued or running (e.g. at frame start).",
   "url": "/docs/api/core/#jobsystem-reset",
   "md": "/docs/api/core.md"
  },
  {
   "name": "log",
   "qualified": "cinder.core.log",
   "kind": "module",
   "module": "cinder.core.log",
   "signature": "",
   "summary": "Structured, levelled logging. A Logger owns a minimum level and a sink. Records carry a level, a category and a message plus optional key=value fields, and are formatted as one line: [LEVEL] category: message key=value .... Sinks are a trait so tests capture records in memory and the engine routes them to stderr, a file or the debug console. Logging never raises; a failing sink drops the record.",
   "url": "/docs/api/core/#cindercorelog",
   "md": "/docs/api/core.md"
  },
  {
   "name": "LogLevel",
   "qualified": "cinder.core.log.LogLevel",
   "kind": "struct",
   "module": "cinder.core.log",
   "signature": "struct LogLevel( Comparable, Equatable, ImplicitlyCopyable, RegisterPassable, Writable )",
   "summary": "Severity, ordered. Compare with the usual operators.",
   "url": "/docs/api/core/#struct-loglevel",
   "md": "/docs/api/core.md"
  },
  {
   "name": "trace",
   "qualified": "cinder.core.log.LogLevel.trace",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "LogLevel",
   "signature": "trace() -> LogLevel",
   "summary": "Severity 0, the lowest: a logger at this level passes everything.",
   "url": "/docs/api/core/#loglevel-trace",
   "md": "/docs/api/core.md"
  },
  {
   "name": "debug",
   "qualified": "cinder.core.log.LogLevel.debug",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "LogLevel",
   "signature": "debug() -> LogLevel",
   "summary": "Severity 1, between trace and info.",
   "url": "/docs/api/core/#loglevel-debug",
   "md": "/docs/api/core.md"
  },
  {
   "name": "info",
   "qualified": "cinder.core.log.LogLevel.info",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "LogLevel",
   "signature": "info() -> LogLevel",
   "summary": "Severity 2; the default Logger minimum level.",
   "url": "/docs/api/core/#loglevel-info",
   "md": "/docs/api/core.md"
  },
  {
   "name": "warn",
   "qualified": "cinder.core.log.LogLevel.warn",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "LogLevel",
   "signature": "warn() -> LogLevel",
   "summary": "Severity 3, between info and error.",
   "url": "/docs/api/core/#loglevel-warn",
   "md": "/docs/api/core.md"
  },
  {
   "name": "error",
   "qualified": "cinder.core.log.LogLevel.error",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "LogLevel",
   "signature": "error() -> LogLevel",
   "summary": "Severity 4, the highest named level.",
   "url": "/docs/api/core/#loglevel-error",
   "md": "/docs/api/core.md"
  },
  {
   "name": "name",
   "qualified": "cinder.core.log.LogLevel.name",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "LogLevel",
   "signature": "name(self) -> StaticString",
   "summary": "Label printed in records: TRACE, DEBUG, INFO, WARN, or ERROR for 4 and above.",
   "url": "/docs/api/core/#loglevel-name",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.core.log.LogLevel.write_to",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "LogLevel",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/core/#loglevel-write_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "LogField",
   "qualified": "cinder.core.log.LogField",
   "kind": "struct",
   "module": "cinder.core.log",
   "signature": "struct LogField(Copyable, Movable, Writable)",
   "summary": "One key=value pair attached to a record.",
   "url": "/docs/api/core/#struct-logfield",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.core.log.LogField.write_to",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "LogField",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/core/#logfield-write_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "LogRecord",
   "qualified": "cinder.core.log.LogRecord",
   "kind": "struct",
   "module": "cinder.core.log",
   "signature": "struct LogRecord(Copyable, Movable, Writable)",
   "summary": "A formatted log entry.",
   "url": "/docs/api/core/#struct-logrecord",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.log.LogRecord.__init__",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "LogRecord",
   "signature": "__init__( out self, level: LogLevel, category: String, message: String, var fields: List[LogField], )",
   "summary": "",
   "url": "/docs/api/core/#logrecord-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.core.log.LogRecord.write_to",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "LogRecord",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/core/#logrecord-write_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "LogSink",
   "qualified": "cinder.core.log.LogSink",
   "kind": "trait",
   "module": "cinder.core.log",
   "signature": "trait LogSink",
   "summary": "Receives formatted records. Implementations must not raise.",
   "url": "/docs/api/core/#trait-logsink",
   "md": "/docs/api/core.md"
  },
  {
   "name": "emit",
   "qualified": "cinder.core.log.LogSink.emit",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "LogSink",
   "signature": "emit(mut self, record: LogRecord)",
   "summary": "Handles one record that passed the filter. Must not raise: drop the record instead.",
   "url": "/docs/api/core/#logsink-emit",
   "md": "/docs/api/core.md"
  },
  {
   "name": "PrintSink",
   "qualified": "cinder.core.log.PrintSink",
   "kind": "struct",
   "module": "cinder.core.log",
   "signature": "struct PrintSink(LogSink, Movable)",
   "summary": "Writes each record as one line to standard output.",
   "url": "/docs/api/core/#struct-printsink",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.log.PrintSink.__init__",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "PrintSink",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/core/#printsink-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "emit",
   "qualified": "cinder.core.log.PrintSink.emit",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "PrintSink",
   "signature": "emit(mut self, record: LogRecord)",
   "summary": "Prints the record as one line to standard output and increments emitted.",
   "url": "/docs/api/core/#printsink-emit",
   "md": "/docs/api/core.md"
  },
  {
   "name": "MemorySink",
   "qualified": "cinder.core.log.MemorySink",
   "kind": "struct",
   "module": "cinder.core.log",
   "signature": "struct MemorySink(LogSink, Movable)",
   "summary": "Keeps every record; used by tests and the in-engine console.",
   "url": "/docs/api/core/#struct-memorysink",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.log.MemorySink.__init__",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "MemorySink",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/core/#memorysink-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "emit",
   "qualified": "cinder.core.log.MemorySink.emit",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "MemorySink",
   "signature": "emit(mut self, record: LogRecord)",
   "summary": "Appends a copy of the record to records, which grows without bound.",
   "url": "/docs/api/core/#memorysink-emit",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Logger",
   "qualified": "cinder.core.log.Logger",
   "kind": "struct",
   "module": "cinder.core.log",
   "signature": "struct Logger[S: LogSink & Movable & Deinitable](Movable)",
   "summary": "Filters by minimum level and forwards to its sink.",
   "url": "/docs/api/core/#struct-logger",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.log.Logger.__init__",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "Logger",
   "signature": "__init__( out self, var sink: Self.S, min_level: LogLevel = LogLevel.info() )",
   "summary": "",
   "url": "/docs/api/core/#logger-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "enabled",
   "qualified": "cinder.core.log.Logger.enabled",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "Logger",
   "signature": "enabled(self, level: LogLevel) -> Bool",
   "summary": "True when level >= min_level; check it before building costly messages.",
   "url": "/docs/api/core/#logger-enabled",
   "md": "/docs/api/core.md"
  },
  {
   "name": "log",
   "qualified": "cinder.core.log.Logger.log",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "Logger",
   "signature": "log( mut self, level: LogLevel, category: String, message: String, var fields: List[LogField], )",
   "summary": "Emits a record when level passes the filter. Field lists are consumed.",
   "url": "/docs/api/core/#logger-log",
   "md": "/docs/api/core.md"
  },
  {
   "name": "log",
   "qualified": "cinder.core.log.Logger.log",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "Logger",
   "signature": "log(mut self, level: LogLevel, category: String, message: String)",
   "summary": "Emits a record without fields when level passes the filter.",
   "url": "/docs/api/core/#logger-log-1",
   "md": "/docs/api/core.md"
  },
  {
   "name": "trace",
   "qualified": "cinder.core.log.Logger.trace",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "Logger",
   "signature": "trace(mut self, category: String, message: String)",
   "summary": "Logs message under category at TRACE, subject to min_level.",
   "url": "/docs/api/core/#logger-trace",
   "md": "/docs/api/core.md"
  },
  {
   "name": "debug",
   "qualified": "cinder.core.log.Logger.debug",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "Logger",
   "signature": "debug(mut self, category: String, message: String)",
   "summary": "Logs message under category at DEBUG, subject to min_level.",
   "url": "/docs/api/core/#logger-debug",
   "md": "/docs/api/core.md"
  },
  {
   "name": "info",
   "qualified": "cinder.core.log.Logger.info",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "Logger",
   "signature": "info(mut self, category: String, message: String)",
   "summary": "Logs message under category at INFO, subject to min_level.",
   "url": "/docs/api/core/#logger-info",
   "md": "/docs/api/core.md"
  },
  {
   "name": "warn",
   "qualified": "cinder.core.log.Logger.warn",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "Logger",
   "signature": "warn(mut self, category: String, message: String)",
   "summary": "Logs message under category at WARN, subject to min_level.",
   "url": "/docs/api/core/#logger-warn",
   "md": "/docs/api/core.md"
  },
  {
   "name": "error",
   "qualified": "cinder.core.log.Logger.error",
   "kind": "method",
   "module": "cinder.core.log",
   "parent": "Logger",
   "signature": "error(mut self, category: String, message: String)",
   "summary": "Logs message under category at ERROR, subject to min_level.",
   "url": "/docs/api/core/#logger-error",
   "md": "/docs/api/core.md"
  },
  {
   "name": "math",
   "qualified": "cinder.core.math",
   "kind": "module",
   "module": "cinder.core.math",
   "signature": "",
   "summary": "SIMD math for the engine. Conventions (docs/ARCHITECTURE.md, fixed): right-handed, Y up, -Z forward, metres, column-major matrices, reverse-Z depth with an infinite far plane. All types are plain 32-bit float values backed by SIMD[DType.float32, 4]; a Vec3 keeps its fourth lane at zero.",
   "url": "/docs/api/core/#cindercoremath",
   "md": "/docs/api/core.md"
  },
  {
   "name": "mat4",
   "qualified": "cinder.core.math.mat4",
   "kind": "module",
   "module": "cinder.core.math.mat4",
   "signature": "",
   "summary": "Mat4: a column-major 4x4 float matrix, as WGSL and glTF store it.",
   "url": "/docs/api/core/#cindercoremathmat4",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Mat4",
   "qualified": "cinder.core.math.mat4.Mat4",
   "kind": "struct",
   "module": "cinder.core.math.mat4",
   "signature": "struct Mat4(Equatable, ImplicitlyCopyable, RegisterPassable, Writable)",
   "summary": "Column-major 4x4 matrix. c0..c3 are the columns; element (row r, column c) is cC[r].",
   "url": "/docs/api/core/#struct-mat4",
   "md": "/docs/api/core.md"
  },
  {
   "name": "identity",
   "qualified": "cinder.core.math.mat4.Mat4.identity",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "identity() -> Mat4",
   "summary": "The identity matrix.",
   "url": "/docs/api/core/#mat4-identity",
   "md": "/docs/api/core.md"
  },
  {
   "name": "zero",
   "qualified": "cinder.core.math.mat4.Mat4.zero",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "zero() -> Mat4",
   "summary": "All sixteen elements zero; also what inverse returns for a singular matrix.",
   "url": "/docs/api/core/#mat4-zero",
   "md": "/docs/api/core.md"
  },
  {
   "name": "from_rows",
   "qualified": "cinder.core.math.mat4.Mat4.from_rows",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "from_rows(r0: Vec4, r1: Vec4, r2: Vec4, r3: Vec4) -> Mat4",
   "summary": "Builds a matrix from its rows (handy for literals written the way maths books print them).",
   "url": "/docs/api/core/#mat4-from_rows",
   "md": "/docs/api/core.md"
  },
  {
   "name": "translation",
   "qualified": "cinder.core.math.mat4.Mat4.translation",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "translation(t: Vec3) -> Mat4",
   "summary": "Translation by t (metres): the identity with t in the last column.",
   "url": "/docs/api/core/#mat4-translation",
   "md": "/docs/api/core.md"
  },
  {
   "name": "scaling",
   "qualified": "cinder.core.math.mat4.Mat4.scaling",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "scaling(s: Vec3) -> Mat4",
   "summary": "Scale by s.x(), s.y(), s.z() along the x, y and z axes.",
   "url": "/docs/api/core/#mat4-scaling",
   "md": "/docs/api/core.md"
  },
  {
   "name": "rotation",
   "qualified": "cinder.core.math.mat4.Mat4.rotation",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "rotation(q: Quat) -> Mat4",
   "summary": "Rotation matrix of a unit quaternion.",
   "url": "/docs/api/core/#mat4-rotation",
   "md": "/docs/api/core.md"
  },
  {
   "name": "trs",
   "qualified": "cinder.core.math.mat4.Mat4.trs",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "trs(t: Vec3, r: Quat, s: Vec3) -> Mat4",
   "summary": "Translation * Rotation * Scale, the glTF node transform order.",
   "url": "/docs/api/core/#mat4-trs",
   "md": "/docs/api/core.md"
  },
  {
   "name": "look_at",
   "qualified": "cinder.core.math.mat4.Mat4.look_at",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "look_at(eye: Vec3, target: Vec3, up: Vec3) -> Mat4",
   "summary": "Right-handed view matrix: the camera looks down -Z, with +Y up and +X right.",
   "url": "/docs/api/core/#mat4-look_at",
   "md": "/docs/api/core.md"
  },
  {
   "name": "perspective_reverse_z_infinite",
   "qualified": "cinder.core.math.mat4.Mat4.perspective_reverse_z_infinite",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "perspective_reverse_z_infinite( fov_y: Float32, aspect: Float32, near: Float32 ) -> Mat4",
   "summary": "Right-handed perspective projection, reverse-Z (near maps to 1) with an infinite far plane, clip depth in [0, 1] as wgpu expects.",
   "url": "/docs/api/core/#mat4-perspective_reverse_z_infinite",
   "md": "/docs/api/core.md"
  },
  {
   "name": "orthographic_reverse_z",
   "qualified": "cinder.core.math.mat4.Mat4.orthographic_reverse_z",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "orthographic_reverse_z( left: Float32, right: Float32, bottom: Float32, top: Float32, near: Float32, far: Float32, ) -> Mat4",
   "summary": "Right-handed orthographic projection with reverse-Z (near maps to 1, far to 0).",
   "url": "/docs/api/core/#mat4-orthographic_reverse_z",
   "md": "/docs/api/core.md"
  },
  {
   "name": "column",
   "qualified": "cinder.core.math.mat4.Mat4.column",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "column(self, c: Int) -> Vec4",
   "summary": "Column c (0 to 3) as a Vec4. Any other index is a bug: cinder_assert aborts. With assertions compiled out (-D CINDER_ASSERTS=0) the index wraps to c & 3.",
   "url": "/docs/api/core/#mat4-column",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__getitem__",
   "qualified": "cinder.core.math.mat4.Mat4.__getitem__",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "__getitem__(self, row: Int, col: Int) -> Float32",
   "summary": "Element (row, col); both indices are checked like row and column.",
   "url": "/docs/api/core/#mat4-__getitem__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "row",
   "qualified": "cinder.core.math.mat4.Mat4.row",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "row(self, r: Int) -> Vec4",
   "summary": "Row r (0 to 3), gathered from the four columns. Any other index is a bug: cinder_assert aborts. With assertions compiled out the index wraps to r & 3.",
   "url": "/docs/api/core/#mat4-row",
   "md": "/docs/api/core.md"
  },
  {
   "name": "to_quat",
   "qualified": "cinder.core.math.mat4.Mat4.to_quat",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "to_quat(self) -> Quat",
   "summary": "Rotation of an orthonormal (possibly scaled) matrix's upper 3x3 (Shepperd's method, choosing the largest diagonal term for stability). Scale is removed first.",
   "url": "/docs/api/core/#mat4-to_quat",
   "md": "/docs/api/core.md"
  },
  {
   "name": "transform_point",
   "qualified": "cinder.core.math.mat4.Mat4.transform_point",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "transform_point(self, p: Vec3) -> Vec3",
   "summary": "Applies the affine part to a point (w = 1), ignoring any projective row.",
   "url": "/docs/api/core/#mat4-transform_point",
   "md": "/docs/api/core.md"
  },
  {
   "name": "transform_vector",
   "qualified": "cinder.core.math.mat4.Mat4.transform_vector",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "transform_vector(self, v: Vec3) -> Vec3",
   "summary": "Applies the linear part to a direction (w = 0).",
   "url": "/docs/api/core/#mat4-transform_vector",
   "md": "/docs/api/core.md"
  },
  {
   "name": "project_point",
   "qualified": "cinder.core.math.mat4.Mat4.project_point",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "project_point(self, p: Vec3) -> Vec3",
   "summary": "Full projective transform with perspective divide.",
   "url": "/docs/api/core/#mat4-project_point",
   "md": "/docs/api/core.md"
  },
  {
   "name": "transpose",
   "qualified": "cinder.core.math.mat4.Mat4.transpose",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "transpose(self) -> Mat4",
   "summary": "Rows and columns swapped; for a pure rotation this is also its inverse.",
   "url": "/docs/api/core/#mat4-transpose",
   "md": "/docs/api/core.md"
  },
  {
   "name": "determinant",
   "qualified": "cinder.core.math.mat4.Mat4.determinant",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "determinant(self) -> Float32",
   "summary": "Determinant of the full 4x4 matrix, by expansion in 2x2 minors. Exactly 0 is what makes inverse return the zero matrix; a negative value means the matrix mirrors space (Transform.from_mat4 relies on this).",
   "url": "/docs/api/core/#mat4-determinant",
   "md": "/docs/api/core.md"
  },
  {
   "name": "inverse",
   "qualified": "cinder.core.math.mat4.Mat4.inverse",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "inverse(self) -> Mat4",
   "summary": "General inverse by cofactors. A singular matrix returns the zero matrix; callers that need to detect that check determinant() first.",
   "url": "/docs/api/core/#mat4-inverse",
   "md": "/docs/api/core.md"
  },
  {
   "name": "approx_equal",
   "qualified": "cinder.core.math.mat4.Mat4.approx_equal",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "approx_equal(self, o: Mat4, eps: Float32 = EPSILON) -> Bool",
   "summary": "True when every element matches within eps under approx_eq.",
   "url": "/docs/api/core/#mat4-approx_equal",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.core.math.mat4.Mat4.write_to",
   "kind": "method",
   "module": "cinder.core.math.mat4",
   "parent": "Mat4",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/core/#mat4-write_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "quat",
   "qualified": "cinder.core.math.quat",
   "kind": "module",
   "module": "cinder.core.math.quat",
   "signature": "",
   "summary": "Quat: a unit quaternion (x, y, z, w) representing a rotation.",
   "url": "/docs/api/core/#cindercoremathquat",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Quat",
   "qualified": "cinder.core.math.quat.Quat",
   "kind": "struct",
   "module": "cinder.core.math.quat",
   "signature": "struct Quat(Equatable, ImplicitlyCopyable, RegisterPassable, Writable)",
   "summary": "Rotation quaternion. Lanes are (x, y, z, w); w is the scalar part.",
   "url": "/docs/api/core/#struct-quat",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.math.quat.Quat.__init__",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "__init__(out self, x: Float32, y: Float32, z: Float32, w: Float32)",
   "summary": "",
   "url": "/docs/api/core/#quat-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "identity",
   "qualified": "cinder.core.math.quat.Quat.identity",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "identity() -> Quat",
   "summary": "The no-rotation quaternion (0, 0, 0, 1).",
   "url": "/docs/api/core/#quat-identity",
   "md": "/docs/api/core.md"
  },
  {
   "name": "from_axis_angle",
   "qualified": "cinder.core.math.quat.Quat.from_axis_angle",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "from_axis_angle(axis: Vec3, angle: Float32) -> Quat",
   "summary": "Rotation of angle radians about the unit vector axis (right-handed).",
   "url": "/docs/api/core/#quat-from_axis_angle",
   "md": "/docs/api/core.md"
  },
  {
   "name": "from_euler",
   "qualified": "cinder.core.math.quat.Quat.from_euler",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "from_euler(yaw: Float32, pitch: Float32, roll: Float32) -> Quat",
   "summary": "Yaw about +Y, then pitch about +X, then roll about +Z (applied in that order to a body).",
   "url": "/docs/api/core/#quat-from_euler",
   "md": "/docs/api/core.md"
  },
  {
   "name": "x",
   "qualified": "cinder.core.math.quat.Quat.x",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "x(self) -> Float32",
   "summary": "Lane 0, the x term of the vector part.",
   "url": "/docs/api/core/#quat-x",
   "md": "/docs/api/core.md"
  },
  {
   "name": "y",
   "qualified": "cinder.core.math.quat.Quat.y",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "y(self) -> Float32",
   "summary": "Lane 1, the y term of the vector part.",
   "url": "/docs/api/core/#quat-y",
   "md": "/docs/api/core.md"
  },
  {
   "name": "z",
   "qualified": "cinder.core.math.quat.Quat.z",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "z(self) -> Float32",
   "summary": "Lane 2, the z term of the vector part.",
   "url": "/docs/api/core/#quat-z",
   "md": "/docs/api/core.md"
  },
  {
   "name": "w",
   "qualified": "cinder.core.math.quat.Quat.w",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "w(self) -> Float32",
   "summary": "Lane 3, the scalar part: cos(angle / 2) for a unit quaternion.",
   "url": "/docs/api/core/#quat-w",
   "md": "/docs/api/core.md"
  },
  {
   "name": "vector_part",
   "qualified": "cinder.core.math.quat.Quat.vector_part",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "vector_part(self) -> Vec3",
   "summary": "(x, y, z) as a Vec3: the rotation axis times sin(angle / 2) for a unit quaternion.",
   "url": "/docs/api/core/#quat-vector_part",
   "md": "/docs/api/core.md"
  },
  {
   "name": "dot",
   "qualified": "cinder.core.math.quat.Quat.dot",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "dot(self, o: Quat) -> Float32",
   "summary": "4D dot product; negative when the two are on opposite hemispheres (see slerp).",
   "url": "/docs/api/core/#quat-dot",
   "md": "/docs/api/core.md"
  },
  {
   "name": "length",
   "qualified": "cinder.core.math.quat.Quat.length",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "length(self) -> Float32",
   "summary": "Euclidean norm over all four lanes; 1 for a unit quaternion.",
   "url": "/docs/api/core/#quat-length",
   "md": "/docs/api/core.md"
  },
  {
   "name": "normalized",
   "qualified": "cinder.core.math.quat.Quat.normalized",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "normalized(self) -> Quat",
   "summary": "Unit quaternion; the zero quaternion becomes the identity.",
   "url": "/docs/api/core/#quat-normalized",
   "md": "/docs/api/core.md"
  },
  {
   "name": "conjugate",
   "qualified": "cinder.core.math.quat.Quat.conjugate",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "conjugate(self) -> Quat",
   "summary": "The vector part negated; for a unit quaternion this is the inverse rotation.",
   "url": "/docs/api/core/#quat-conjugate",
   "md": "/docs/api/core.md"
  },
  {
   "name": "inverse",
   "qualified": "cinder.core.math.quat.Quat.inverse",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "inverse(self) -> Quat",
   "summary": "Inverse for any non-zero quaternion (equals the conjugate for unit quaternions). The zero quaternion has no inverse and returns the zero quaternion, as Mat4.inverse returns the zero matrix for a singular matrix.",
   "url": "/docs/api/core/#quat-inverse",
   "md": "/docs/api/core.md"
  },
  {
   "name": "rotate",
   "qualified": "cinder.core.math.quat.Quat.rotate",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "rotate(self, v: Vec3) -> Vec3",
   "summary": "Rotates v by this unit quaternion: v' = v + 2w(u x v) + 2u x (u x v).",
   "url": "/docs/api/core/#quat-rotate",
   "md": "/docs/api/core.md"
  },
  {
   "name": "nlerp",
   "qualified": "cinder.core.math.quat.Quat.nlerp",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "nlerp(self, o: Quat, t: Float32) -> Quat",
   "summary": "Normalised linear interpolation along the shorter arc.",
   "url": "/docs/api/core/#quat-nlerp",
   "md": "/docs/api/core.md"
  },
  {
   "name": "slerp",
   "qualified": "cinder.core.math.quat.Quat.slerp",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "slerp(self, o: Quat, t: Float32) -> Quat",
   "summary": "Spherical interpolation along the shorter arc; falls back to nlerp when nearly parallel.",
   "url": "/docs/api/core/#quat-slerp",
   "md": "/docs/api/core.md"
  },
  {
   "name": "approx_equal",
   "qualified": "cinder.core.math.quat.Quat.approx_equal",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "approx_equal(self, o: Quat, eps: Float32 = EPSILON) -> Bool",
   "summary": "True when both represent the same rotation (q and -q are equal rotations).",
   "url": "/docs/api/core/#quat-approx_equal",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.core.math.quat.Quat.write_to",
   "kind": "method",
   "module": "cinder.core.math.quat",
   "parent": "Quat",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/core/#quat-write_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "scalar",
   "qualified": "cinder.core.math.scalar",
   "kind": "module",
   "module": "cinder.core.math.scalar",
   "signature": "",
   "summary": "Scalar helpers shared by the vector, quaternion and matrix types.",
   "url": "/docs/api/core/#cindercoremathscalar",
   "md": "/docs/api/core.md"
  },
  {
   "name": "radians",
   "qualified": "cinder.core.math.scalar.radians",
   "kind": "def",
   "module": "cinder.core.math.scalar",
   "signature": "def radians(deg: Float32) -> Float32",
   "summary": "Converts degrees to radians.",
   "url": "/docs/api/core/#def-radians",
   "md": "/docs/api/core.md"
  },
  {
   "name": "degrees",
   "qualified": "cinder.core.math.scalar.degrees",
   "kind": "def",
   "module": "cinder.core.math.scalar",
   "signature": "def degrees(rad: Float32) -> Float32",
   "summary": "Converts radians to degrees.",
   "url": "/docs/api/core/#def-degrees",
   "md": "/docs/api/core.md"
  },
  {
   "name": "clamp",
   "qualified": "cinder.core.math.scalar.clamp",
   "kind": "def",
   "module": "cinder.core.math.scalar",
   "signature": "def clamp(x: Float32, lo: Float32, hi: Float32) -> Float32",
   "summary": "Clamps x to [lo, hi].",
   "url": "/docs/api/core/#def-clamp",
   "md": "/docs/api/core.md"
  },
  {
   "name": "saturate",
   "qualified": "cinder.core.math.scalar.saturate",
   "kind": "def",
   "module": "cinder.core.math.scalar",
   "signature": "def saturate(x: Float32) -> Float32",
   "summary": "Clamps x to [0, 1].",
   "url": "/docs/api/core/#def-saturate",
   "md": "/docs/api/core.md"
  },
  {
   "name": "lerp",
   "qualified": "cinder.core.math.scalar.lerp",
   "kind": "def",
   "module": "cinder.core.math.scalar",
   "signature": "def lerp(a: Float32, b: Float32, t: Float32) -> Float32",
   "summary": "Linear interpolation; exact at t = 0 and t = 1.",
   "url": "/docs/api/core/#def-lerp",
   "md": "/docs/api/core.md"
  },
  {
   "name": "approx_eq",
   "qualified": "cinder.core.math.scalar.approx_eq",
   "kind": "def",
   "module": "cinder.core.math.scalar",
   "signature": "def approx_eq(a: Float32, b: Float32, eps: Float32 = EPSILON) -> Bool",
   "summary": "True when |a - b| <= eps * max(1, |a|, |b|): absolute near zero, relative elsewhere.",
   "url": "/docs/api/core/#def-approx_eq",
   "md": "/docs/api/core.md"
  },
  {
   "name": "transform",
   "qualified": "cinder.core.math.transform",
   "kind": "module",
   "module": "cinder.core.math.transform",
   "signature": "",
   "summary": "Transform: translation, rotation and scale as separate terms (poses, animation keys).",
   "url": "/docs/api/core/#cindercoremathtransform",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Transform",
   "qualified": "cinder.core.math.transform.Transform",
   "kind": "struct",
   "module": "cinder.core.math.transform",
   "signature": "struct Transform(Equatable, ImplicitlyCopyable, Movable, Writable)",
   "summary": "A TRS transform. Composition order is scale, then rotation, then translation.",
   "url": "/docs/api/core/#struct-transform",
   "md": "/docs/api/core.md"
  },
  {
   "name": "identity",
   "qualified": "cinder.core.math.transform.Transform.identity",
   "kind": "method",
   "module": "cinder.core.math.transform",
   "parent": "Transform",
   "signature": "identity() -> Transform",
   "summary": "Zero translation, identity rotation and unit scale.",
   "url": "/docs/api/core/#transform-identity",
   "md": "/docs/api/core.md"
  },
  {
   "name": "from_mat4",
   "qualified": "cinder.core.math.transform.Transform.from_mat4",
   "kind": "method",
   "module": "cinder.core.math.transform",
   "parent": "Transform",
   "signature": "from_mat4(m: Mat4) -> Transform",
   "summary": "Decomposes a matrix without shear: translation from the last column, scale from the column lengths, rotation from the normalised columns. A mirrored matrix (negative determinant) has no proper rotation; the reflection is folded into a negative x scale and the rotation is taken from the matrix with its first column negated, so to_mat4() rebuilds the input.",
   "url": "/docs/api/core/#transform-from_mat4",
   "md": "/docs/api/core.md"
  },
  {
   "name": "to_mat4",
   "qualified": "cinder.core.math.transform.Transform.to_mat4",
   "kind": "method",
   "module": "cinder.core.math.transform",
   "parent": "Transform",
   "signature": "to_mat4(self) -> Mat4",
   "summary": "The equivalent matrix, Mat4.trs: scale, then rotation, then translation.",
   "url": "/docs/api/core/#transform-to_mat4",
   "md": "/docs/api/core.md"
  },
  {
   "name": "lerp",
   "qualified": "cinder.core.math.transform.Transform.lerp",
   "kind": "method",
   "module": "cinder.core.math.transform",
   "parent": "Transform",
   "signature": "lerp(self, o: Transform, t: Float32) -> Transform",
   "summary": "Linear translation and scale, normalised-lerp rotation along the shorter arc.",
   "url": "/docs/api/core/#transform-lerp",
   "md": "/docs/api/core.md"
  },
  {
   "name": "approx_equal",
   "qualified": "cinder.core.math.transform.Transform.approx_equal",
   "kind": "method",
   "module": "cinder.core.math.transform",
   "parent": "Transform",
   "signature": "approx_equal(self, o: Transform, eps: Float32 = EPSILON) -> Bool",
   "summary": "True when translation, rotation and scale match within eps (q and -q are equal).",
   "url": "/docs/api/core/#transform-approx_equal",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.core.math.transform.Transform.write_to",
   "kind": "method",
   "module": "cinder.core.math.transform",
   "parent": "Transform",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/core/#transform-write_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "vec",
   "qualified": "cinder.core.math.vec",
   "kind": "module",
   "module": "cinder.core.math.vec",
   "signature": "",
   "summary": "Vec2, Vec3 and Vec4: 32-bit float vectors backed by SIMD registers.",
   "url": "/docs/api/core/#cindercoremathvec",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Vec2",
   "qualified": "cinder.core.math.vec.Vec2",
   "kind": "struct",
   "module": "cinder.core.math.vec",
   "signature": "struct Vec2(Equatable, ImplicitlyCopyable, RegisterPassable, Writable)",
   "summary": "A 2D vector.",
   "url": "/docs/api/core/#struct-vec2",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.math.vec.Vec2.__init__",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec2",
   "signature": "__init__(out self, x: Float32, y: Float32)",
   "summary": "",
   "url": "/docs/api/core/#vec2-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "zero",
   "qualified": "cinder.core.math.vec.Vec2.zero",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec2",
   "signature": "zero() -> Vec2",
   "summary": "(0, 0).",
   "url": "/docs/api/core/#vec2-zero",
   "md": "/docs/api/core.md"
  },
  {
   "name": "x",
   "qualified": "cinder.core.math.vec.Vec2.x",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec2",
   "signature": "x(self) -> Float32",
   "summary": "Lane 0.",
   "url": "/docs/api/core/#vec2-x",
   "md": "/docs/api/core.md"
  },
  {
   "name": "y",
   "qualified": "cinder.core.math.vec.Vec2.y",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec2",
   "signature": "y(self) -> Float32",
   "summary": "Lane 1.",
   "url": "/docs/api/core/#vec2-y",
   "md": "/docs/api/core.md"
  },
  {
   "name": "dot",
   "qualified": "cinder.core.math.vec.Vec2.dot",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec2",
   "signature": "dot(self, o: Vec2) -> Float32",
   "summary": "Sum of the component-wise products.",
   "url": "/docs/api/core/#vec2-dot",
   "md": "/docs/api/core.md"
  },
  {
   "name": "length_squared",
   "qualified": "cinder.core.math.vec.Vec2.length_squared",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec2",
   "signature": "length_squared(self) -> Float32",
   "summary": "Squared Euclidean length; avoids the square root when only comparing lengths.",
   "url": "/docs/api/core/#vec2-length_squared",
   "md": "/docs/api/core.md"
  },
  {
   "name": "length",
   "qualified": "cinder.core.math.vec.Vec2.length",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec2",
   "signature": "length(self) -> Float32",
   "summary": "Euclidean length.",
   "url": "/docs/api/core/#vec2-length",
   "md": "/docs/api/core.md"
  },
  {
   "name": "approx_equal",
   "qualified": "cinder.core.math.vec.Vec2.approx_equal",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec2",
   "signature": "approx_equal(self, o: Vec2, eps: Float32 = EPSILON) -> Bool",
   "summary": "True when x and y each match within eps under approx_eq.",
   "url": "/docs/api/core/#vec2-approx_equal",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.core.math.vec.Vec2.write_to",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec2",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/core/#vec2-write_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Vec3",
   "qualified": "cinder.core.math.vec.Vec3",
   "kind": "struct",
   "module": "cinder.core.math.vec",
   "signature": "struct Vec3(Equatable, ImplicitlyCopyable, RegisterPassable, Writable)",
   "summary": "A 3D vector. The fourth SIMD lane is always zero so 4-wide operations stay exact.",
   "url": "/docs/api/core/#struct-vec3",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.math.vec.Vec3.__init__",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "__init__(out self, x: Float32, y: Float32, z: Float32)",
   "summary": "",
   "url": "/docs/api/core/#vec3-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "zero",
   "qualified": "cinder.core.math.vec.Vec3.zero",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "zero() -> Vec3",
   "summary": "(0, 0, 0).",
   "url": "/docs/api/core/#vec3-zero",
   "md": "/docs/api/core.md"
  },
  {
   "name": "one",
   "qualified": "cinder.core.math.vec.Vec3.one",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "one() -> Vec3",
   "summary": "(1, 1, 1), the unit scale.",
   "url": "/docs/api/core/#vec3-one",
   "md": "/docs/api/core.md"
  },
  {
   "name": "unit_x",
   "qualified": "cinder.core.math.vec.Vec3.unit_x",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "unit_x() -> Vec3",
   "summary": "+X, the engine's right axis.",
   "url": "/docs/api/core/#vec3-unit_x",
   "md": "/docs/api/core.md"
  },
  {
   "name": "unit_y",
   "qualified": "cinder.core.math.vec.Vec3.unit_y",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "unit_y() -> Vec3",
   "summary": "+Y, the engine's up axis (right-handed, Y-up).",
   "url": "/docs/api/core/#vec3-unit_y",
   "md": "/docs/api/core.md"
  },
  {
   "name": "unit_z",
   "qualified": "cinder.core.math.vec.Vec3.unit_z",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "unit_z() -> Vec3",
   "summary": "+Z, pointing backwards: the engine's forward is -Z.",
   "url": "/docs/api/core/#vec3-unit_z",
   "md": "/docs/api/core.md"
  },
  {
   "name": "forward",
   "qualified": "cinder.core.math.vec.Vec3.forward",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "forward() -> Vec3",
   "summary": "The engine's forward direction, -Z.",
   "url": "/docs/api/core/#vec3-forward",
   "md": "/docs/api/core.md"
  },
  {
   "name": "splat",
   "qualified": "cinder.core.math.vec.Vec3.splat",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "splat(v: Float32) -> Vec3",
   "summary": "All three components set to v (the fourth lane stays zero).",
   "url": "/docs/api/core/#vec3-splat",
   "md": "/docs/api/core.md"
  },
  {
   "name": "x",
   "qualified": "cinder.core.math.vec.Vec3.x",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "x(self) -> Float32",
   "summary": "Lane 0.",
   "url": "/docs/api/core/#vec3-x",
   "md": "/docs/api/core.md"
  },
  {
   "name": "y",
   "qualified": "cinder.core.math.vec.Vec3.y",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "y(self) -> Float32",
   "summary": "Lane 1.",
   "url": "/docs/api/core/#vec3-y",
   "md": "/docs/api/core.md"
  },
  {
   "name": "z",
   "qualified": "cinder.core.math.vec.Vec3.z",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "z(self) -> Float32",
   "summary": "Lane 2.",
   "url": "/docs/api/core/#vec3-z",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__getitem__",
   "qualified": "cinder.core.math.vec.Vec3.__getitem__",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "__getitem__(self, i: Int) -> Float32",
   "summary": "",
   "url": "/docs/api/core/#vec3-__getitem__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "with_x",
   "qualified": "cinder.core.math.vec.Vec3.with_x",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "with_x(self, v: Float32) -> Vec3",
   "summary": "A copy with x replaced by v.",
   "url": "/docs/api/core/#vec3-with_x",
   "md": "/docs/api/core.md"
  },
  {
   "name": "with_y",
   "qualified": "cinder.core.math.vec.Vec3.with_y",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "with_y(self, v: Float32) -> Vec3",
   "summary": "A copy with y replaced by v.",
   "url": "/docs/api/core/#vec3-with_y",
   "md": "/docs/api/core.md"
  },
  {
   "name": "with_z",
   "qualified": "cinder.core.math.vec.Vec3.with_z",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "with_z(self, v: Float32) -> Vec3",
   "summary": "A copy with z replaced by v.",
   "url": "/docs/api/core/#vec3-with_z",
   "md": "/docs/api/core.md"
  },
  {
   "name": "dot",
   "qualified": "cinder.core.math.vec.Vec3.dot",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "dot(self, o: Vec3) -> Float32",
   "summary": "Sum of the component-wise products of x, y and z.",
   "url": "/docs/api/core/#vec3-dot",
   "md": "/docs/api/core.md"
  },
  {
   "name": "cross",
   "qualified": "cinder.core.math.vec.Vec3.cross",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "cross(self, o: Vec3) -> Vec3",
   "summary": "Right-handed cross product self x o (unit_x cross unit_y is unit_z).",
   "url": "/docs/api/core/#vec3-cross",
   "md": "/docs/api/core.md"
  },
  {
   "name": "length_squared",
   "qualified": "cinder.core.math.vec.Vec3.length_squared",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "length_squared(self) -> Float32",
   "summary": "Squared Euclidean length; avoids the square root when only comparing lengths.",
   "url": "/docs/api/core/#vec3-length_squared",
   "md": "/docs/api/core.md"
  },
  {
   "name": "length",
   "qualified": "cinder.core.math.vec.Vec3.length",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "length(self) -> Float32",
   "summary": "Euclidean length.",
   "url": "/docs/api/core/#vec3-length",
   "md": "/docs/api/core.md"
  },
  {
   "name": "distance",
   "qualified": "cinder.core.math.vec.Vec3.distance",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "distance(self, o: Vec3) -> Float32",
   "summary": "Euclidean distance to o.",
   "url": "/docs/api/core/#vec3-distance",
   "md": "/docs/api/core.md"
  },
  {
   "name": "normalized",
   "qualified": "cinder.core.math.vec.Vec3.normalized",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "normalized(self) -> Vec3",
   "summary": "Unit vector in the same direction; zero stays zero.",
   "url": "/docs/api/core/#vec3-normalized",
   "md": "/docs/api/core.md"
  },
  {
   "name": "lerp",
   "qualified": "cinder.core.math.vec.Vec3.lerp",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "lerp(self, o: Vec3, t: Float32) -> Vec3",
   "summary": "self + (o - self) * t per component; t is unclamped, so it extrapolates.",
   "url": "/docs/api/core/#vec3-lerp",
   "md": "/docs/api/core.md"
  },
  {
   "name": "min",
   "qualified": "cinder.core.math.vec.Vec3.min",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "min(self, o: Vec3) -> Vec3",
   "summary": "Component-wise minimum.",
   "url": "/docs/api/core/#vec3-min",
   "md": "/docs/api/core.md"
  },
  {
   "name": "max",
   "qualified": "cinder.core.math.vec.Vec3.max",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "max(self, o: Vec3) -> Vec3",
   "summary": "Component-wise maximum.",
   "url": "/docs/api/core/#vec3-max",
   "md": "/docs/api/core.md"
  },
  {
   "name": "abs",
   "qualified": "cinder.core.math.vec.Vec3.abs",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "abs(self) -> Vec3",
   "summary": "Component-wise absolute value.",
   "url": "/docs/api/core/#vec3-abs",
   "md": "/docs/api/core.md"
  },
  {
   "name": "max_component",
   "qualified": "cinder.core.math.vec.Vec3.max_component",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "max_component(self) -> Float32",
   "summary": "Largest of x, y and z by signed value (not by magnitude; use abs() first for that).",
   "url": "/docs/api/core/#vec3-max_component",
   "md": "/docs/api/core.md"
  },
  {
   "name": "approx_equal",
   "qualified": "cinder.core.math.vec.Vec3.approx_equal",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "approx_equal(self, o: Vec3, eps: Float32 = EPSILON) -> Bool",
   "summary": "True when x, y and z each match within eps under approx_eq.",
   "url": "/docs/api/core/#vec3-approx_equal",
   "md": "/docs/api/core.md"
  },
  {
   "name": "to_vec4",
   "qualified": "cinder.core.math.vec.Vec3.to_vec4",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "to_vec4(self, w: Float32) -> Vec4",
   "summary": "(x, y, z, w): pass 1 for a point and 0 for a direction.",
   "url": "/docs/api/core/#vec3-to_vec4",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.core.math.vec.Vec3.write_to",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec3",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/core/#vec3-write_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Vec4",
   "qualified": "cinder.core.math.vec.Vec4",
   "kind": "struct",
   "module": "cinder.core.math.vec",
   "signature": "struct Vec4(Equatable, ImplicitlyCopyable, RegisterPassable, Writable)",
   "summary": "A 4D vector, also used for homogeneous points and colours.",
   "url": "/docs/api/core/#struct-vec4",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.math.vec.Vec4.__init__",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec4",
   "signature": "__init__(out self, x: Float32, y: Float32, z: Float32, w: Float32)",
   "summary": "",
   "url": "/docs/api/core/#vec4-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "zero",
   "qualified": "cinder.core.math.vec.Vec4.zero",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec4",
   "signature": "zero() -> Vec4",
   "summary": "(0, 0, 0, 0).",
   "url": "/docs/api/core/#vec4-zero",
   "md": "/docs/api/core.md"
  },
  {
   "name": "x",
   "qualified": "cinder.core.math.vec.Vec4.x",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec4",
   "signature": "x(self) -> Float32",
   "summary": "Lane 0.",
   "url": "/docs/api/core/#vec4-x",
   "md": "/docs/api/core.md"
  },
  {
   "name": "y",
   "qualified": "cinder.core.math.vec.Vec4.y",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec4",
   "signature": "y(self) -> Float32",
   "summary": "Lane 1.",
   "url": "/docs/api/core/#vec4-y",
   "md": "/docs/api/core.md"
  },
  {
   "name": "z",
   "qualified": "cinder.core.math.vec.Vec4.z",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec4",
   "signature": "z(self) -> Float32",
   "summary": "Lane 2.",
   "url": "/docs/api/core/#vec4-z",
   "md": "/docs/api/core.md"
  },
  {
   "name": "w",
   "qualified": "cinder.core.math.vec.Vec4.w",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec4",
   "signature": "w(self) -> Float32",
   "summary": "Lane 3: 1 for a point, 0 for a direction, alpha for a colour.",
   "url": "/docs/api/core/#vec4-w",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__getitem__",
   "qualified": "cinder.core.math.vec.Vec4.__getitem__",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec4",
   "signature": "__getitem__(self, i: Int) -> Float32",
   "summary": "",
   "url": "/docs/api/core/#vec4-__getitem__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "xyz",
   "qualified": "cinder.core.math.vec.Vec4.xyz",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec4",
   "signature": "xyz(self) -> Vec3",
   "summary": "(x, y, z) as a Vec3, dropping w without a perspective divide.",
   "url": "/docs/api/core/#vec4-xyz",
   "md": "/docs/api/core.md"
  },
  {
   "name": "dot",
   "qualified": "cinder.core.math.vec.Vec4.dot",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec4",
   "signature": "dot(self, o: Vec4) -> Float32",
   "summary": "Sum of the component-wise products over all four lanes.",
   "url": "/docs/api/core/#vec4-dot",
   "md": "/docs/api/core.md"
  },
  {
   "name": "length",
   "qualified": "cinder.core.math.vec.Vec4.length",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec4",
   "signature": "length(self) -> Float32",
   "summary": "Euclidean length over all four lanes.",
   "url": "/docs/api/core/#vec4-length",
   "md": "/docs/api/core.md"
  },
  {
   "name": "approx_equal",
   "qualified": "cinder.core.math.vec.Vec4.approx_equal",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec4",
   "signature": "approx_equal(self, o: Vec4, eps: Float32 = EPSILON) -> Bool",
   "summary": "True when all four components match within eps under approx_eq.",
   "url": "/docs/api/core/#vec4-approx_equal",
   "md": "/docs/api/core.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.core.math.vec.Vec4.write_to",
   "kind": "method",
   "module": "cinder.core.math.vec",
   "parent": "Vec4",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/core/#vec4-write_to",
   "md": "/docs/api/core.md"
  },
  {
   "name": "profile",
   "qualified": "cinder.core.profile",
   "kind": "module",
   "module": "cinder.core.profile",
   "signature": "",
   "summary": "Tracy profiling for the engine: zones, frame marks, plots and messages. Profiling is off until Profiler.start() (nothing listens on the network before that) and every call is a cheap no-op while it is off. Zone opens on construction and closes when it is destroyed. Mojo destroys a value right after its last use, so end the zone explicitly where it should close: var z = profiler.zone(\"render\")…",
   "url": "/docs/api/core/#cindercoreprofile",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Profiler",
   "qualified": "cinder.core.profile.Profiler",
   "kind": "struct",
   "module": "cinder.core.profile",
   "signature": "struct Profiler(ImplicitlyCopyable, Movable)",
   "summary": "A handle to the shim's Tracy client; copies share the process-wide profiler and its plot name table.",
   "url": "/docs/api/core/#struct-profiler",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.profile.Profiler.__init__",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Profiler",
   "signature": "__init__(out self, lib: NativePtr)",
   "summary": "",
   "url": "/docs/api/core/#profiler-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "available",
   "qualified": "cinder.core.profile.Profiler.available",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Profiler",
   "signature": "available(self) -> Bool",
   "summary": "Whether the shim was built with Tracy.",
   "url": "/docs/api/core/#profiler-available",
   "md": "/docs/api/core.md"
  },
  {
   "name": "start",
   "qualified": "cinder.core.profile.Profiler.start",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Profiler",
   "signature": "start(self) -> Bool",
   "summary": "Starts the Tracy client (idempotent). Returns False when Tracy is not built in.",
   "url": "/docs/api/core/#profiler-start",
   "md": "/docs/api/core.md"
  },
  {
   "name": "stop",
   "qualified": "cinder.core.profile.Profiler.stop",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Profiler",
   "signature": "stop(self)",
   "summary": "Shuts the Tracy client down if it is running; a no-op otherwise or without Tracy.",
   "url": "/docs/api/core/#profiler-stop",
   "md": "/docs/api/core.md"
  },
  {
   "name": "is_started",
   "qualified": "cinder.core.profile.Profiler.is_started",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Profiler",
   "signature": "is_started(self) -> Bool",
   "summary": "Whether the Tracy client is running (start without stop).",
   "url": "/docs/api/core/#profiler-is_started",
   "md": "/docs/api/core.md"
  },
  {
   "name": "is_connected",
   "qualified": "cinder.core.profile.Profiler.is_connected",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Profiler",
   "signature": "is_connected(self) -> Bool",
   "summary": "Whether a Tracy viewer is connected; always False while stopped or without Tracy.",
   "url": "/docs/api/core/#profiler-is_connected",
   "md": "/docs/api/core.md"
  },
  {
   "name": "zone",
   "qualified": "cinder.core.profile.Profiler.zone",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Profiler",
   "signature": "zone(self, name: String, color: UInt32 = 0) -> Zone",
   "summary": "Opens a zone named name that ends when the returned Zone is destroyed. color is 0xRRGGBB (0 keeps Tracy's default; see the COLOR_* constants). Mojo destroys a value after its last use, so end the zone explicitly with _ = z^ where it should close. While profiling is off the zone is inert and its id is 0.",
   "url": "/docs/api/core/#profiler-zone",
   "md": "/docs/api/core.md"
  },
  {
   "name": "frame_mark",
   "qualified": "cinder.core.profile.Profiler.frame_mark",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Profiler",
   "signature": "frame_mark(self)",
   "summary": "Marks the end of a frame.",
   "url": "/docs/api/core/#profiler-frame_mark",
   "md": "/docs/api/core.md"
  },
  {
   "name": "plot",
   "qualified": "cinder.core.profile.Profiler.plot",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Profiler",
   "signature": "plot(self, name: String, value: Float64)",
   "summary": "Adds value to the Tracy plot called name. Does nothing while profiling is off. Tracy keeps the name pointer for the program's life, so the name is interned (copied once into a never-freed table); later calls with the same name reuse that copy and do not allocate.",
   "url": "/docs/api/core/#profiler-plot",
   "md": "/docs/api/core.md"
  },
  {
   "name": "plot_name_count",
   "qualified": "cinder.core.profile.Profiler.plot_name_count",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Profiler",
   "signature": "plot_name_count(self) -> Int",
   "summary": "How many distinct plot names have been interned (shared by every copy).",
   "url": "/docs/api/core/#profiler-plot_name_count",
   "md": "/docs/api/core.md"
  },
  {
   "name": "message",
   "qualified": "cinder.core.profile.Profiler.message",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Profiler",
   "signature": "message(self, text: String)",
   "summary": "Sends text to Tracy's message log (info severity); a no-op while profiling is off.",
   "url": "/docs/api/core/#profiler-message",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Zone",
   "qualified": "cinder.core.profile.Zone",
   "kind": "struct",
   "module": "cinder.core.profile",
   "signature": "struct Zone(Movable)",
   "summary": "An open profiling zone; ends when destroyed. id is 0 while profiling is off.",
   "url": "/docs/api/core/#struct-zone",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.profile.Zone.__init__",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Zone",
   "signature": "__init__(out self, lib: NativePtr, name: String, color: UInt32)",
   "summary": "",
   "url": "/docs/api/core/#zone-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "text",
   "qualified": "cinder.core.profile.Zone.text",
   "kind": "method",
   "module": "cinder.core.profile",
   "parent": "Zone",
   "signature": "text(self, note: String)",
   "summary": "Attaches text to the open zone.",
   "url": "/docs/api/core/#zone-text",
   "md": "/docs/api/core.md"
  },
  {
   "name": "ring",
   "qualified": "cinder.core.ring",
   "kind": "module",
   "module": "cinder.core.ring",
   "signature": "",
   "summary": "RingBuffer: a fixed-capacity FIFO queue with no allocation after construction.",
   "url": "/docs/api/core/#cindercorering",
   "md": "/docs/api/core.md"
  },
  {
   "name": "RingBuffer",
   "qualified": "cinder.core.ring.RingBuffer",
   "kind": "struct",
   "module": "cinder.core.ring",
   "signature": "struct RingBuffer[T: Copyable & Deinitable](Movable, Sized)",
   "summary": "Single-threaded bounded FIFO. push returns False when full; pop returns None when empty. Capacity must be a power of two so index wrapping is a mask. Cross-thread queues live in the native shim (CnEventQueue); this type is for in-engine command and event buffering.",
   "url": "/docs/api/core/#struct-ringbuffer",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.ring.RingBuffer.__init__",
   "kind": "method",
   "module": "cinder.core.ring",
   "parent": "RingBuffer",
   "signature": "__init__(out self, capacity: Int) raises",
   "summary": "",
   "url": "/docs/api/core/#ringbuffer-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "capacity",
   "qualified": "cinder.core.ring.RingBuffer.capacity",
   "kind": "method",
   "module": "cinder.core.ring",
   "parent": "RingBuffer",
   "signature": "capacity(self) -> Int",
   "summary": "Number of slots, a power of two fixed at construction.",
   "url": "/docs/api/core/#ringbuffer-capacity",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__len__",
   "qualified": "cinder.core.ring.RingBuffer.__len__",
   "kind": "method",
   "module": "cinder.core.ring",
   "parent": "RingBuffer",
   "signature": "__len__(self) -> Int",
   "summary": "",
   "url": "/docs/api/core/#ringbuffer-__len__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "is_empty",
   "qualified": "cinder.core.ring.RingBuffer.is_empty",
   "kind": "method",
   "module": "cinder.core.ring",
   "parent": "RingBuffer",
   "signature": "is_empty(self) -> Bool",
   "summary": "True when nothing is queued (pop would return None).",
   "url": "/docs/api/core/#ringbuffer-is_empty",
   "md": "/docs/api/core.md"
  },
  {
   "name": "is_full",
   "qualified": "cinder.core.ring.RingBuffer.is_full",
   "kind": "method",
   "module": "cinder.core.ring",
   "parent": "RingBuffer",
   "signature": "is_full(self) -> Bool",
   "summary": "True when every slot is taken (push would return False).",
   "url": "/docs/api/core/#ringbuffer-is_full",
   "md": "/docs/api/core.md"
  },
  {
   "name": "push",
   "qualified": "cinder.core.ring.RingBuffer.push",
   "kind": "method",
   "module": "cinder.core.ring",
   "parent": "RingBuffer",
   "signature": "push(mut self, var value: Self.T) -> Bool",
   "summary": "Appends value; returns False (and drops nothing already queued) when full.",
   "url": "/docs/api/core/#ringbuffer-push",
   "md": "/docs/api/core.md"
  },
  {
   "name": "pop",
   "qualified": "cinder.core.ring.RingBuffer.pop",
   "kind": "method",
   "module": "cinder.core.ring",
   "parent": "RingBuffer",
   "signature": "pop(mut self) -> Optional[Self.T]",
   "summary": "Removes and returns the oldest value, or None when empty.",
   "url": "/docs/api/core/#ringbuffer-pop",
   "md": "/docs/api/core.md"
  },
  {
   "name": "peek",
   "qualified": "cinder.core.ring.RingBuffer.peek",
   "kind": "method",
   "module": "cinder.core.ring",
   "parent": "RingBuffer",
   "signature": "peek(self) raises -> Self.T",
   "summary": "A copy of the oldest value; raises when empty.",
   "url": "/docs/api/core/#ringbuffer-peek",
   "md": "/docs/api/core.md"
  },
  {
   "name": "clear",
   "qualified": "cinder.core.ring.RingBuffer.clear",
   "kind": "method",
   "module": "cinder.core.ring",
   "parent": "RingBuffer",
   "signature": "clear(mut self)",
   "summary": "Pops and destroys every queued value, oldest first.",
   "url": "/docs/api/core/#ringbuffer-clear",
   "md": "/docs/api/core.md"
  },
  {
   "name": "time",
   "qualified": "cinder.core.time",
   "kind": "module",
   "module": "cinder.core.time",
   "signature": "",
   "summary": "Time: a monotonic clock and the fixed-timestep accumulator that drives the simulation. The frame loop (section 4 of the brief) simulates at a fixed 60 Hz and renders at whatever rate the display allows, interpolating between the last two simulation states with alpha.",
   "url": "/docs/api/core/#cindercoretime",
   "md": "/docs/api/core.md"
  },
  {
   "name": "Clock",
   "qualified": "cinder.core.time.Clock",
   "kind": "struct",
   "module": "cinder.core.time",
   "signature": "struct Clock(Movable)",
   "summary": "Monotonic wall clock in nanoseconds, with per-frame deltas.",
   "url": "/docs/api/core/#struct-clock",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.time.Clock.__init__",
   "kind": "method",
   "module": "cinder.core.time",
   "parent": "Clock",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/core/#clock-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "now_ns",
   "qualified": "cinder.core.time.Clock.now_ns",
   "kind": "method",
   "module": "cinder.core.time",
   "parent": "Clock",
   "signature": "now_ns(self) -> Int",
   "summary": "Current perf_counter_ns() reading. Monotonic, but its origin is arbitrary (not the clock's creation), so only differences between readings are meaningful.",
   "url": "/docs/api/core/#clock-now_ns",
   "md": "/docs/api/core.md"
  },
  {
   "name": "elapsed_seconds",
   "qualified": "cinder.core.time.Clock.elapsed_seconds",
   "kind": "method",
   "module": "cinder.core.time",
   "parent": "Clock",
   "signature": "elapsed_seconds(self) -> Float64",
   "summary": "Seconds since the clock was created.",
   "url": "/docs/api/core/#clock-elapsed_seconds",
   "md": "/docs/api/core.md"
  },
  {
   "name": "tick",
   "qualified": "cinder.core.time.Clock.tick",
   "kind": "method",
   "module": "cinder.core.time",
   "parent": "Clock",
   "signature": "tick(mut self) -> Float64",
   "summary": "Seconds since the previous tick (or creation). Never negative.",
   "url": "/docs/api/core/#clock-tick",
   "md": "/docs/api/core.md"
  },
  {
   "name": "FixedStep",
   "qualified": "cinder.core.time.FixedStep",
   "kind": "struct",
   "module": "cinder.core.time",
   "signature": "struct FixedStep(ImplicitlyCopyable, Movable)",
   "summary": "Fixed-timestep accumulator. Feed real frame times with advance; it returns how many simulation steps of step_seconds to run (capped at max_steps_per_frame to avoid the spiral of death) and leaves alpha() as the interpolation factor for rendering between the previous and current simulation state.",
   "url": "/docs/api/core/#struct-fixedstep",
   "md": "/docs/api/core.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.core.time.FixedStep.__init__",
   "kind": "method",
   "module": "cinder.core.time",
   "parent": "FixedStep",
   "signature": "__init__(out self, hz: Float64 = 60.0, max_steps_per_frame: Int = 8)",
   "summary": "",
   "url": "/docs/api/core/#fixedstep-__init__",
   "md": "/docs/api/core.md"
  },
  {
   "name": "advance",
   "qualified": "cinder.core.time.FixedStep.advance",
   "kind": "method",
   "module": "cinder.core.time",
   "parent": "FixedStep",
   "signature": "advance(mut self, frame_seconds: Float64) -> Int",
   "summary": "Accounts for frame_seconds of real time and returns the number of steps to simulate.",
   "url": "/docs/api/core/#fixedstep-advance",
   "md": "/docs/api/core.md"
  },
  {
   "name": "alpha",
   "qualified": "cinder.core.time.FixedStep.alpha",
   "kind": "method",
   "module": "cinder.core.time",
   "parent": "FixedStep",
   "signature": "alpha(self) -> Float64",
   "summary": "Fraction of a step accumulated but not yet simulated, in [0, 1).",
   "url": "/docs/api/core/#fixedstep-alpha",
   "md": "/docs/api/core.md"
  },
  {
   "name": "total_steps",
   "qualified": "cinder.core.time.FixedStep.total_steps",
   "kind": "method",
   "module": "cinder.core.time",
   "parent": "FixedStep",
   "signature": "total_steps(self) -> Int",
   "summary": "Sum of every step count advance has returned.",
   "url": "/docs/api/core/#fixedstep-total_steps",
   "md": "/docs/api/core.md"
  },
  {
   "name": "ecs",
   "qualified": "cinder.ecs",
   "kind": "module",
   "module": "cinder.ecs",
   "signature": "",
   "summary": "Entity component system: archetype world, typed queries, change detection, command buffers, parent-child transforms and a scheduler that runs non-conflicting systems in parallel.",
   "url": "/docs/api/ecs/#cinderecs-1",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "commands",
   "qualified": "cinder.ecs.commands",
   "kind": "module",
   "module": "cinder.ecs.commands",
   "signature": "",
   "summary": "Deferred structural changes: record while iterating, apply when it is safe. A CommandBuffer stores spawns (returning placeholder entities resolved on apply), despawns, and typed adds/removes as type-erased byte payloads with the component's move/destroy functions, so it can be filled from jobs that must not mutate the world's archetypes.",
   "url": "/docs/api/ecs/#cinderecscommands",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "CommandBuffer",
   "qualified": "cinder.ecs.commands.CommandBuffer",
   "kind": "struct",
   "module": "cinder.ecs.commands",
   "signature": "struct CommandBuffer(Movable, Sized)",
   "summary": "Records spawns, despawns, adds and removes for a later apply on the main thread. Recording never touches the world, so a job can fill a buffer while systems iterate; one buffer is not safe to share between threads (no locks). Added values are moved into a payload the buffer owns; every add command still in the buffer owns its value, so dropping the buffer (or clear) destroys the values of…",
   "url": "/docs/api/ecs/#struct-commandbuffer",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.ecs.commands.CommandBuffer.__init__",
   "kind": "method",
   "module": "cinder.ecs.commands",
   "parent": "CommandBuffer",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/ecs/#commandbuffer-__init__",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "clear",
   "qualified": "cinder.ecs.commands.CommandBuffer.clear",
   "kind": "method",
   "module": "cinder.ecs.commands",
   "parent": "CommandBuffer",
   "signature": "clear(mut self)",
   "summary": "Drops every recorded command, destroying the values of unapplied adds. Use it to discard what is left after an apply that raised.",
   "url": "/docs/api/ecs/#commandbuffer-clear",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "spawn",
   "qualified": "cinder.ecs.commands.CommandBuffer.spawn",
   "kind": "method",
   "module": "cinder.ecs.commands",
   "parent": "CommandBuffer",
   "signature": "spawn(mut self) -> Int",
   "summary": "Returns a placeholder index usable with add_to_spawned; see resolved after apply.",
   "url": "/docs/api/ecs/#commandbuffer-spawn",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "despawn",
   "qualified": "cinder.ecs.commands.CommandBuffer.despawn",
   "kind": "method",
   "module": "cinder.ecs.commands",
   "parent": "CommandBuffer",
   "signature": "despawn(mut self, e: Entity)",
   "summary": "Records a despawn of e; apply skips it when e is no longer alive by then.",
   "url": "/docs/api/ecs/#commandbuffer-despawn",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "add",
   "qualified": "cinder.ecs.commands.CommandBuffer.add",
   "kind": "method",
   "module": "cinder.ecs.commands",
   "parent": "CommandBuffer",
   "signature": "add[T: Component](mut self, e: Entity, var value: T)",
   "summary": "Records adding (or replacing) T on e, moving value into the buffer. apply raises when T was never registered with the world or when e is not alive.",
   "url": "/docs/api/ecs/#commandbuffer-add",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "add_to_spawned",
   "qualified": "cinder.ecs.commands.CommandBuffer.add_to_spawned",
   "kind": "method",
   "module": "cinder.ecs.commands",
   "parent": "CommandBuffer",
   "signature": "add_to_spawned[T: Component](mut self, placeholder: Int, var value: T)",
   "summary": "Like add, for the entity created by the spawn() call that returned placeholder.",
   "url": "/docs/api/ecs/#commandbuffer-add_to_spawned",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "remove",
   "qualified": "cinder.ecs.commands.CommandBuffer.remove",
   "kind": "method",
   "module": "cinder.ecs.commands",
   "parent": "CommandBuffer",
   "signature": "remove[T: Component](mut self, e: Entity)",
   "summary": "Records removing T from e; apply skips a missing T, raises if e is dead.",
   "url": "/docs/api/ecs/#commandbuffer-remove",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "__len__",
   "qualified": "cinder.ecs.commands.CommandBuffer.__len__",
   "kind": "method",
   "module": "cinder.ecs.commands",
   "parent": "CommandBuffer",
   "signature": "__len__(self) -> Int",
   "summary": "",
   "url": "/docs/api/ecs/#commandbuffer-__len__",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "apply",
   "qualified": "cinder.ecs.commands.CommandBuffer.apply",
   "kind": "method",
   "module": "cinder.ecs.commands",
   "parent": "CommandBuffer",
   "signature": "apply(mut self, mut world: World) raises -> Int",
   "summary": "Applies every command in order and clears the buffer. Returns how many were applied. Payload values are moved into the world through the world's registered move function, so the world must already know the component type (register it or add it once directly). When a command raises (unregistered component, dead target), the commands before it have taken effect and are removed from the buffer; the failing command and the ones after it stay, still owning their values, and the error propagates. A later apply continues with them (placeholder spawns already made keep their entity in resolved); clear or dropping the buffer discards them instead.",
   "url": "/docs/api/ecs/#commandbuffer-apply",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "hierarchy",
   "qualified": "cinder.ecs.hierarchy",
   "kind": "module",
   "module": "cinder.ecs.hierarchy",
   "signature": "",
   "summary": "Parent-child transforms: Parent, LocalTransform, WorldTransform and their propagation.",
   "url": "/docs/api/ecs/#cinderecshierarchy",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "Parent",
   "qualified": "cinder.ecs.hierarchy.Parent",
   "kind": "struct",
   "module": "cinder.ecs.hierarchy",
   "signature": "struct Parent(Component)",
   "summary": "Parent link for propagate_transforms (id 1); a dead parent or a self link is ignored.",
   "url": "/docs/api/ecs/#struct-parent",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "component_id",
   "qualified": "cinder.ecs.hierarchy.Parent.component_id",
   "kind": "method",
   "module": "cinder.ecs.hierarchy",
   "parent": "Parent",
   "signature": "component_id() -> Int",
   "summary": "",
   "url": "/docs/api/ecs/#parent-component_id",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "LocalTransform",
   "qualified": "cinder.ecs.hierarchy.LocalTransform",
   "kind": "struct",
   "module": "cinder.ecs.hierarchy",
   "signature": "struct LocalTransform(Component)",
   "summary": "Transform relative to the Parent (to world space without one); component id 2.",
   "url": "/docs/api/ecs/#struct-localtransform",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "component_id",
   "qualified": "cinder.ecs.hierarchy.LocalTransform.component_id",
   "kind": "method",
   "module": "cinder.ecs.hierarchy",
   "parent": "LocalTransform",
   "signature": "component_id() -> Int",
   "summary": "",
   "url": "/docs/api/ecs/#localtransform-component_id",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "WorldTransform",
   "qualified": "cinder.ecs.hierarchy.WorldTransform",
   "kind": "struct",
   "module": "cinder.ecs.hierarchy",
   "signature": "struct WorldTransform(Component)",
   "summary": "World-space transform, parent world * local, written by propagate_transforms; id 3.",
   "url": "/docs/api/ecs/#struct-worldtransform",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "component_id",
   "qualified": "cinder.ecs.hierarchy.WorldTransform.component_id",
   "kind": "method",
   "module": "cinder.ecs.hierarchy",
   "parent": "WorldTransform",
   "signature": "component_id() -> Int",
   "summary": "",
   "url": "/docs/api/ecs/#worldtransform-component_id",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "propagate_transforms",
   "qualified": "cinder.ecs.hierarchy.propagate_transforms",
   "kind": "def",
   "module": "cinder.ecs.hierarchy",
   "signature": "def propagate_transforms(mut world: World) raises -> Int",
   "summary": "Writes WorldTransform = parent world * LocalTransform for every entity with a local transform (adding the component when missing). Parents are resolved recursively with memoisation, so the order of entities does not matter and each is computed once. Only transforms whose value changed are marked changed. Scratch lists live in the world, so a steady-state call allocates nothing. Returns the…",
   "url": "/docs/api/ecs/#def-propagate_transforms",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "schedule",
   "qualified": "cinder.ecs.schedule",
   "kind": "module",
   "module": "cinder.ecs.schedule",
   "signature": "",
   "summary": "System scheduling by declared component access. Each system names the components it reads and writes. Schedule.build groups systems into stages in declaration order: a system joins the current stage unless it conflicts with one already there (write/write or read/write on the same component, or a declared exclusive world access), in which case a new stage starts. Systems within a stage run in…",
   "url": "/docs/api/ecs/#cinderecsschedule",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "SystemDesc",
   "qualified": "cinder.ecs.schedule.SystemDesc",
   "kind": "struct",
   "module": "cinder.ecs.schedule",
   "signature": "struct SystemDesc(Copyable, Movable)",
   "summary": "A named system plus the component ids it reads and writes, used by Schedule for staging. The declarations are trusted: nothing checks what run actually accesses.",
   "url": "/docs/api/ecs/#struct-systemdesc",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.ecs.schedule.SystemDesc.__init__",
   "kind": "method",
   "module": "cinder.ecs.schedule",
   "parent": "SystemDesc",
   "signature": "__init__( out self, name: String, run: SystemFn, exclusive: Bool = False )",
   "summary": "",
   "url": "/docs/api/ecs/#systemdesc-__init__",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "reads_",
   "qualified": "cinder.ecs.schedule.SystemDesc.reads_",
   "kind": "method",
   "module": "cinder.ecs.schedule",
   "parent": "SystemDesc",
   "signature": "reads_[T: Component](var self) -> SystemDesc",
   "summary": "Declares a read of T; returns the description for chaining.",
   "url": "/docs/api/ecs/#systemdesc-reads_",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "writes_",
   "qualified": "cinder.ecs.schedule.SystemDesc.writes_",
   "kind": "method",
   "module": "cinder.ecs.schedule",
   "parent": "SystemDesc",
   "signature": "writes_[T: Component](var self) -> SystemDesc",
   "summary": "Declares a write of T; returns the description for chaining.",
   "url": "/docs/api/ecs/#systemdesc-writes_",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "conflicts_with",
   "qualified": "cinder.ecs.schedule.SystemDesc.conflicts_with",
   "kind": "method",
   "module": "cinder.ecs.schedule",
   "parent": "SystemDesc",
   "signature": "conflicts_with(self, other: SystemDesc) -> Bool",
   "summary": "Whether the two systems may not share a stage. True when either is exclusive or one writes a component id the other reads or writes; two readers of the same component never conflict.",
   "url": "/docs/api/ecs/#systemdesc-conflicts_with",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "Schedule",
   "qualified": "cinder.ecs.schedule.Schedule",
   "kind": "struct",
   "module": "cinder.ecs.schedule",
   "signature": "struct Schedule(Movable)",
   "summary": "Systems grouped into stages by declared access (see the module docstring).",
   "url": "/docs/api/ecs/#struct-schedule",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.ecs.schedule.Schedule.__init__",
   "kind": "method",
   "module": "cinder.ecs.schedule",
   "parent": "Schedule",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/ecs/#schedule-__init__",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "add",
   "qualified": "cinder.ecs.schedule.Schedule.add",
   "kind": "method",
   "module": "cinder.ecs.schedule",
   "parent": "Schedule",
   "signature": "add(mut self, var system: SystemDesc)",
   "summary": "Appends a system after those already added and marks the stages for rebuilding.",
   "url": "/docs/api/ecs/#schedule-add",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "build",
   "qualified": "cinder.ecs.schedule.Schedule.build",
   "kind": "method",
   "module": "cinder.ecs.schedule",
   "parent": "Schedule",
   "signature": "build(mut self)",
   "summary": "Assigns systems to stages in declaration order. A system joins the last stage unless it conflicts with any system there, otherwise it opens a new stage; earlier stages are never revisited, so the order affects packing.",
   "url": "/docs/api/ecs/#schedule-build",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "stage_count",
   "qualified": "cinder.ecs.schedule.Schedule.stage_count",
   "kind": "method",
   "module": "cinder.ecs.schedule",
   "parent": "Schedule",
   "signature": "stage_count(mut self) -> Int",
   "summary": "Number of stages, building them first when systems changed since the last build.",
   "url": "/docs/api/ecs/#schedule-stage_count",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "run",
   "qualified": "cinder.ecs.schedule.Schedule.run",
   "kind": "method",
   "module": "cinder.ecs.schedule",
   "parent": "Schedule",
   "signature": "run( mut self, mut world: World, jobs: Optional[Pointer[JobSystem, MutUntrackedOrigin]], )",
   "summary": "Runs every stage. With a job system, systems in one stage run as parallel jobs; without one (or for single-system stages) they run inline on the calling thread.",
   "url": "/docs/api/ecs/#schedule-run",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "world",
   "qualified": "cinder.ecs.world",
   "kind": "module",
   "module": "cinder.ecs.world",
   "signature": "",
   "summary": "Archetype ECS: entities, type-erased component columns, typed queries, change detection. Components are structs conforming to Component (a unique component_id()). The world registers a component type on first use, recording its size, alignment, and type-erased move/destroy functions, so columns can hold any Movable type. Entities with the same component set live in one archetype, one…",
   "url": "/docs/api/ecs/#cinderecsworld",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "Component",
   "qualified": "cinder.ecs.world.Component",
   "kind": "trait",
   "module": "cinder.ecs.world",
   "signature": "trait Component(Copyable, Deinitable, Movable)",
   "summary": "A component type. component_id() must be unique per type (0 .. MAX_COMPONENTS - 1).",
   "url": "/docs/api/ecs/#trait-component",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "component_id",
   "qualified": "cinder.ecs.world.Component.component_id",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Component",
   "signature": "component_id() -> Int",
   "summary": "The type's id, unique among component types and in 0 .. MAX_COMPONENTS - 1.",
   "url": "/docs/api/ecs/#component-component_id",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "Entity",
   "qualified": "cinder.ecs.world.Entity",
   "kind": "struct",
   "module": "cinder.ecs.world",
   "signature": "struct Entity( Equatable, Hashable, ImplicitlyCopyable, RegisterPassable, Writable )",
   "summary": "Generational entity id: index + generation. Entity.null() is never live.",
   "url": "/docs/api/ecs/#struct-entity",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "null",
   "qualified": "cinder.ecs.world.Entity.null",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Entity",
   "signature": "null() -> Entity",
   "summary": "The null entity (index 0xFFFFFFFF, generation 0): never alive, False as a Bool.",
   "url": "/docs/api/ecs/#entity-null",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "is_null",
   "qualified": "cinder.ecs.world.Entity.is_null",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Entity",
   "signature": "is_null(self) -> Bool",
   "summary": "Whether the index is the null index 0xFFFFFFFF (the generation is not compared).",
   "url": "/docs/api/ecs/#entity-is_null",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "packed",
   "qualified": "cinder.ecs.world.Entity.packed",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Entity",
   "signature": "packed(self) -> UInt64",
   "summary": "Index in the low 32 bits, generation in the high 32; from_packed inverts it.",
   "url": "/docs/api/ecs/#entity-packed",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "from_packed",
   "qualified": "cinder.ecs.world.Entity.from_packed",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Entity",
   "signature": "from_packed(v: UInt64) -> Entity",
   "summary": "Inverse of packed(): index from the low 32 bits, generation from the high 32.",
   "url": "/docs/api/ecs/#entity-from_packed",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.ecs.world.Entity.write_to",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Entity",
   "signature": "write_to(self, mut w: Some[Writer])",
   "summary": "",
   "url": "/docs/api/ecs/#entity-write_to",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "component_stride",
   "qualified": "cinder.ecs.world.component_stride",
   "kind": "def",
   "module": "cinder.ecs.world",
   "signature": "def component_stride[T: Component]() -> Int",
   "summary": "Element stride: the size rounded up to the type's alignment, so arrays stay tight (an 8-byte component takes 8 bytes per row) while every element is correctly aligned.",
   "url": "/docs/api/ecs/#def-component_stride",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "ComponentInfo",
   "qualified": "cinder.ecs.world.ComponentInfo",
   "kind": "struct",
   "module": "cinder.ecs.world",
   "signature": "struct ComponentInfo(ImplicitlyCopyable, Movable)",
   "summary": "Registration record per component id: size, alignment, row stride, type name and type-erased destroy/move. Every id has one; ids that were never registered hold no-op functions, size 0, an empty type name and registered False.",
   "url": "/docs/api/ecs/#struct-componentinfo",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "Column",
   "qualified": "cinder.ecs.world.Column",
   "kind": "struct",
   "module": "cinder.ecs.world",
   "signature": "struct Column(Movable)",
   "summary": "One component's storage inside an archetype: count elements of stride bytes.",
   "url": "/docs/api/ecs/#struct-column",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.ecs.world.Column.__init__",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Column",
   "signature": "__init__(out self, component: Int, stride: Int, capacity: Int)",
   "summary": "",
   "url": "/docs/api/ecs/#column-__init__",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "capacity",
   "qualified": "cinder.ecs.world.Column.capacity",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Column",
   "signature": "capacity(self) -> Int",
   "summary": "Rows that fit in the allocated blocks before the column must grow.",
   "url": "/docs/api/ecs/#column-capacity",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "base",
   "qualified": "cinder.ecs.world.Column.base",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Column",
   "signature": "base(self) -> ErasedPtr",
   "summary": "Untyped pointer to row 0; dangles once the column grows.",
   "url": "/docs/api/ecs/#column-base",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "element",
   "qualified": "cinder.ecs.world.Column.element",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Column",
   "signature": "element(self, row: Int) -> ErasedPtr",
   "summary": "Untyped pointer to row (row * stride bytes past base); no bounds check.",
   "url": "/docs/api/ecs/#column-element",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "grow",
   "qualified": "cinder.ecs.world.Column.grow",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Column",
   "signature": "grow(mut self, needed: Int)",
   "summary": "Ensures room for needed rows, at least doubling the capacity. Existing rows are relocated bytewise (no move constructor runs), so stored values must not point into themselves, and pointers from base/element dangle afterwards. ticks is left to the caller.",
   "url": "/docs/api/ecs/#column-grow",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "Archetype",
   "qualified": "cinder.ecs.world.Archetype",
   "kind": "struct",
   "module": "cinder.ecs.world",
   "signature": "struct Archetype(Movable)",
   "summary": "Entities sharing one component set. Columns are parallel to entities.",
   "url": "/docs/api/ecs/#struct-archetype",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.ecs.world.Archetype.__init__",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Archetype",
   "signature": "__init__( out self, var signature: List[Int], infos: List[ComponentInfo] )",
   "summary": "",
   "url": "/docs/api/ecs/#archetype-__init__",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "count",
   "qualified": "cinder.ecs.world.Archetype.count",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Archetype",
   "signature": "count(self) -> Int",
   "summary": "Number of entities (rows) stored in this archetype.",
   "url": "/docs/api/ecs/#archetype-count",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "has",
   "qualified": "cinder.ecs.world.Archetype.has",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Archetype",
   "signature": "has(self, component: Int) -> Bool",
   "summary": "Whether component id component is in this archetype's signature.",
   "url": "/docs/api/ecs/#archetype-has",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "matches",
   "qualified": "cinder.ecs.world.Archetype.matches",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Archetype",
   "signature": "matches(self, with_: List[Int], without: List[Int]) -> Bool",
   "summary": "Whether the archetype has every id in with_ and none of the ids in without.",
   "url": "/docs/api/ecs/#archetype-matches",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "reserve_row",
   "qualified": "cinder.ecs.world.Archetype.reserve_row",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Archetype",
   "signature": "reserve_row(mut self, entity: Entity, tick: UInt32) -> Int",
   "summary": "Appends entity with a new row stamped tick in every column; returns the row index. Component values in the new row are uninitialised: the caller must write every column.",
   "url": "/docs/api/ecs/#archetype-reserve_row",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "swap_remove",
   "qualified": "cinder.ecs.world.Archetype.swap_remove",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Archetype",
   "signature": "swap_remove( mut self, row: Int, infos: List[ComponentInfo], destroy: Bool ) -> Entity",
   "summary": "Removes row, moving the last row into it. Returns the entity that moved (or null).",
   "url": "/docs/api/ecs/#archetype-swap_remove",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "World",
   "qualified": "cinder.ecs.world.World",
   "kind": "struct",
   "module": "cinder.ecs.world",
   "signature": "struct World(Movable)",
   "summary": "The entity store: component registry, archetypes, entity locations and the change tick. New entities start in archetype 0 (no components); archetypes are created on demand and never removed. The world has no locks and belongs to the main thread: structural changes, register and advance_tick must not overlap any other access. Dropping the world destroys every stored component.",
   "url": "/docs/api/ecs/#struct-world",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.ecs.world.World.__init__",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/ecs/#world-__init__",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "register",
   "qualified": "cinder.ecs.world.World.register",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "register[T: Component](mut self) raises -> Int",
   "summary": "Registers T under its component_id() and returns the id; repeat calls are no-ops. Raises when the id is outside 0 .. MAX_COMPONENTS - 1, when the id is already registered by another type (different type name, size or alignment), or when T needs alignment above 16 bytes. add registers implicitly; CommandBuffer.apply needs the type registered beforehand.",
   "url": "/docs/api/ecs/#world-register",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "advance_tick",
   "qualified": "cinder.ecs.world.World.advance_tick",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "advance_tick(mut self) -> UInt32",
   "summary": "Increments the change tick and returns it; later writes are stamped with it.",
   "url": "/docs/api/ecs/#world-advance_tick",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "spawn",
   "qualified": "cinder.ecs.world.World.spawn",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "spawn(mut self) -> Entity",
   "summary": "Creates an entity without components and returns it. A freed index is reused with its generation incremented, so handles to the despawned entity stay dead; otherwise a new index starts at generation 1.",
   "url": "/docs/api/ecs/#world-spawn",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "is_alive",
   "qualified": "cinder.ecs.world.World.is_alive",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "is_alive(self, e: Entity) -> Bool",
   "summary": "Whether e is not null, in range, alive, and of the index's current generation.",
   "url": "/docs/api/ecs/#world-is_alive",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "despawn",
   "qualified": "cinder.ecs.world.World.despawn",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "despawn(mut self, e: Entity) raises",
   "summary": "Destroys the entity's components and frees its index for reuse. Raises when e is not alive. The row is swap-removed, so the archetype's last entity moves into it (pointers into that archetype dangle).",
   "url": "/docs/api/ecs/#world-despawn",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "count",
   "qualified": "cinder.ecs.world.World.count",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "count(self) -> Int",
   "summary": "Number of live entities.",
   "url": "/docs/api/ecs/#world-count",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "add",
   "qualified": "cinder.ecs.world.World.add",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "add[T: Component](mut self, e: Entity, var value: T) raises",
   "summary": "Adds (or replaces) a component. Replacing marks it changed.",
   "url": "/docs/api/ecs/#world-add",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "remove",
   "qualified": "cinder.ecs.world.World.remove",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "remove[T: Component](mut self, e: Entity) raises -> Bool",
   "summary": "Removes a component; False when the entity did not have it.",
   "url": "/docs/api/ecs/#world-remove",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "has",
   "qualified": "cinder.ecs.world.World.has",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "has[T: Component](self, e: Entity) -> Bool",
   "summary": "Whether e is alive and has a T; False (no raise) for dead or null entities.",
   "url": "/docs/api/ecs/#world-has",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "get",
   "qualified": "cinder.ecs.world.World.get",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "get[T: Component](self, e: Entity) raises -> T",
   "summary": "A copy of the component.",
   "url": "/docs/api/ecs/#world-get",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "get_ptr",
   "qualified": "cinder.ecs.world.World.get_ptr",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "get_ptr[ T: Component ](self, e: Entity) raises -> Pointer[T, MutUntrackedOrigin]",
   "summary": "Direct pointer, valid until the next structural change. Does not mark the row changed.",
   "url": "/docs/api/ecs/#world-get_ptr",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "get_mut",
   "qualified": "cinder.ecs.world.World.get_mut",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "get_mut[ T: Component ](mut self, e: Entity) raises -> Pointer[T, MutUntrackedOrigin]",
   "summary": "Like get_ptr and marks the component changed at the current tick.",
   "url": "/docs/api/ecs/#world-get_mut",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "set",
   "qualified": "cinder.ecs.world.World.set",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "set[T: Component](mut self, e: Entity, var value: T) raises",
   "summary": "Overwrites an existing T and marks it changed (via get_mut). Raises when e is not alive or has no T; use add to attach a new component.",
   "url": "/docs/api/ecs/#world-set",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "changed_tick",
   "qualified": "cinder.ecs.world.World.changed_tick",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "changed_tick[T: Component](self, e: Entity) raises -> UInt32",
   "summary": "The tick at which e's T was last written. Raises when e is dead or has no T.",
   "url": "/docs/api/ecs/#world-changed_tick",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "entities",
   "qualified": "cinder.ecs.world.World.entities",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "entities(self) -> List[Entity]",
   "summary": "A new list of every live entity, grouped by archetype (not in spawn order).",
   "url": "/docs/api/ecs/#world-entities",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "archetype_count",
   "qualified": "cinder.ecs.world.World.archetype_count",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "archetype_count(self) -> Int",
   "summary": "Archetypes created so far, including the empty one (they are never removed).",
   "url": "/docs/api/ecs/#world-archetype_count",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "query",
   "qualified": "cinder.ecs.world.World.query",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "query(self) -> Query",
   "summary": "Starts a Query builder over this world. The query keeps an untracked pointer to the world and must not outlive it. Systems that run every frame should keep a QuerySpec and use collect_chunks, which reuses its list.",
   "url": "/docs/api/ecs/#world-query",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "collect_prop_chunks",
   "qualified": "cinder.ecs.world.World.collect_prop_chunks",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "collect_prop_chunks(mut self)",
   "summary": "collect_chunks of prop_spec into the world's own prop_chunks scratch (transform propagation).",
   "url": "/docs/api/ecs/#world-collect_prop_chunks",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "collect_chunks",
   "qualified": "cinder.ecs.world.World.collect_chunks",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "World",
   "signature": "collect_chunks(self, spec: QuerySpec, mut out: List[Chunk])",
   "summary": "Fills out (cleared first, capacity kept) with the chunks matching spec. Systems keep their QuerySpec and chunk list across frames so steady-state frames allocate nothing.",
   "url": "/docs/api/ecs/#world-collect_chunks",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "pass_through",
   "qualified": "cinder.ecs.world.pass_through",
   "kind": "def",
   "module": "cinder.ecs.world",
   "signature": "def pass_through(p: ErasedPtr)",
   "summary": "Hands p to keep; the body of the no-op destroy/move used for unregistered ids.",
   "url": "/docs/api/ecs/#def-pass_through",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "Chunk",
   "qualified": "cinder.ecs.world.Chunk",
   "kind": "struct",
   "module": "cinder.ecs.world",
   "signature": "struct Chunk(ImplicitlyCopyable, Movable)",
   "summary": "One archetype's rows matched by a query: typed column access by row index.",
   "url": "/docs/api/ecs/#struct-chunk",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.ecs.world.Chunk.__init__",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Chunk",
   "signature": "__init__( out self, world: Pointer[World, MutUntrackedOrigin], archetype: Int )",
   "summary": "",
   "url": "/docs/api/ecs/#chunk-__init__",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "has",
   "qualified": "cinder.ecs.world.Chunk.has",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Chunk",
   "signature": "has[T: Component](self) -> Bool",
   "summary": "Whether every entity in this chunk has T.",
   "url": "/docs/api/ecs/#chunk-has",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "entity",
   "qualified": "cinder.ecs.world.Chunk.entity",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Chunk",
   "signature": "entity(self, row: Int) -> Entity",
   "summary": "The entity at row of this chunk's archetype.",
   "url": "/docs/api/ecs/#chunk-entity",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "column",
   "qualified": "cinder.ecs.world.Chunk.column",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Chunk",
   "signature": "column[T: Component](self) -> Pointer[T, MutUntrackedOrigin]",
   "summary": "Base pointer of the component column (element row is column[T]()[unsafe_offset=row]). Aborts when the chunk has no T (use has for optional components).",
   "url": "/docs/api/ecs/#chunk-column",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "stride",
   "qualified": "cinder.ecs.world.Chunk.stride",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Chunk",
   "signature": "stride[T: Component]() -> Int",
   "summary": "Bytes between consecutive T elements of a column (component_stride[T]()).",
   "url": "/docs/api/ecs/#chunk-stride",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "get",
   "qualified": "cinder.ecs.world.Chunk.get",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Chunk",
   "signature": "get[T: Component](self, row: Int) -> Pointer[T, MutUntrackedOrigin]",
   "summary": "Pointer to the T at row; does not mark it changed (see mark_changed). Aborts when the chunk has no T (use has); row is not range-checked. The pointer dangles after the next structural change.",
   "url": "/docs/api/ecs/#chunk-get",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "mark_changed",
   "qualified": "cinder.ecs.world.Chunk.mark_changed",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Chunk",
   "signature": "mark_changed[T: Component](self, row: Int)",
   "summary": "Stamps the T at row with the world's current tick; aborts when the chunk has no T.",
   "url": "/docs/api/ecs/#chunk-mark_changed",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "changed_since",
   "qualified": "cinder.ecs.world.Chunk.changed_since",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Chunk",
   "signature": "changed_since[T: Component](self, row: Int, tick: UInt32) -> Bool",
   "summary": "Whether the T at row was written after tick (a write at exactly tick is not). Aborts when the chunk has no T.",
   "url": "/docs/api/ecs/#chunk-changed_since",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "QuerySpec",
   "qualified": "cinder.ecs.world.QuerySpec",
   "kind": "struct",
   "module": "cinder.ecs.world",
   "signature": "struct QuerySpec(Copyable, Movable)",
   "summary": "The filters of a query without a world pointer: safe to keep in a system struct.",
   "url": "/docs/api/ecs/#struct-queryspec",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.ecs.world.QuerySpec.__init__",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "QuerySpec",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/ecs/#queryspec-__init__",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "with_",
   "qualified": "cinder.ecs.world.QuerySpec.with_",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "QuerySpec",
   "signature": "with_[T: Component](var self) -> QuerySpec",
   "summary": "Requires component T; returns the spec for chaining.",
   "url": "/docs/api/ecs/#queryspec-with_",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "without",
   "qualified": "cinder.ecs.world.QuerySpec.without",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "QuerySpec",
   "signature": "without[T: Component](var self) -> QuerySpec",
   "summary": "Excludes archetypes that have T; returns the spec for chaining.",
   "url": "/docs/api/ecs/#queryspec-without",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "Query",
   "qualified": "cinder.ecs.world.Query",
   "kind": "struct",
   "module": "cinder.ecs.world",
   "signature": "struct Query(Movable)",
   "summary": "Builder: world.query().with_[A]().with_[B]().without[C]().chunks() lists matching chunks. Component access inside a chunk is typed (chunk.column[A]()); the filters decide which archetypes take part.",
   "url": "/docs/api/ecs/#struct-query",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.ecs.world.Query.__init__",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Query",
   "signature": "__init__(out self, world: Pointer[World, MutUntrackedOrigin])",
   "summary": "",
   "url": "/docs/api/ecs/#query-__init__",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "with_",
   "qualified": "cinder.ecs.world.Query.with_",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Query",
   "signature": "with_[T: Component](var self) -> Query",
   "summary": "Requires component T; returns the query for chaining.",
   "url": "/docs/api/ecs/#query-with_",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "without",
   "qualified": "cinder.ecs.world.Query.without",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Query",
   "signature": "without[T: Component](var self) -> Query",
   "summary": "Excludes archetypes that have T; returns the query for chaining.",
   "url": "/docs/api/ecs/#query-without",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "chunks",
   "qualified": "cinder.ecs.world.Query.chunks",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Query",
   "signature": "chunks(self) -> List[Chunk]",
   "summary": "A new list with one Chunk per non-empty matching archetype, in archetype order. Each chunk's count is captured here and goes stale after a structural change.",
   "url": "/docs/api/ecs/#query-chunks",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "count",
   "qualified": "cinder.ecs.world.Query.count",
   "kind": "method",
   "module": "cinder.ecs.world",
   "parent": "Query",
   "signature": "count(self) -> Int",
   "summary": "Number of matching entities (builds the chunk list to sum it).",
   "url": "/docs/api/ecs/#query-count",
   "md": "/docs/api/ecs.md"
  },
  {
   "name": "gfx",
   "qualified": "cinder.gfx",
   "kind": "module",
   "module": "cinder.gfx",
   "signature": "",
   "summary": "Safe, typed layer over wgpu-native. Gfx owns the instance, adapter, device and queue and drains the shim's event queue into diagnostics (validation errors, device loss, wgpu log). Resource modules build on it with one distinct handle type per resource kind and ownership through __deinit__.",
   "url": "/docs/api/gfx/#cindergfx-1",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "commands",
   "qualified": "cinder.gfx.commands",
   "kind": "module",
   "module": "cinder.gfx.commands",
   "signature": "",
   "summary": "Command recording: encoders, render and compute passes, copies, submission and readback.",
   "url": "/docs/api/gfx/#cindergfxcommands",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ColorAttachment",
   "qualified": "cinder.gfx.commands.ColorAttachment",
   "kind": "struct",
   "module": "cinder.gfx.commands",
   "signature": "struct ColorAttachment(Copyable, Movable)",
   "summary": "A colour target of a render pass. view may be a swapchain view obtained outside Resources; resolve is the single-sample target when view is multisampled (null otherwise).",
   "url": "/docs/api/gfx/#struct-colorattachment",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.commands.ColorAttachment.__init__",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "ColorAttachment",
   "signature": "__init__( out self, view: WGPUTextureView, clear: Bool, var clear_color: WGPUColor, store: Bool, resolve: WGPUTextureView = WGPUTextureView(), )",
   "summary": "",
   "url": "/docs/api/gfx/#colorattachment-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "cleared",
   "qualified": "cinder.gfx.commands.ColorAttachment.cleared",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "ColorAttachment",
   "signature": "cleared( view: WGPUTextureView, r: Float64, g: Float64, b: Float64, a: Float64 ) -> ColorAttachment",
   "summary": "Clears view to (r, g, b, a) at load and stores the result; no resolve target.",
   "url": "/docs/api/gfx/#colorattachment-cleared",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "cleared_resolving",
   "qualified": "cinder.gfx.commands.ColorAttachment.cleared_resolving",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "ColorAttachment",
   "signature": "cleared_resolving( view: WGPUTextureView, resolve: WGPUTextureView, r: Float64, g: Float64, b: Float64, a: Float64, ) -> ColorAttachment",
   "summary": "Clears the multisampled view to (r, g, b, a), resolves into resolve and discards the multisampled contents (store op Discard).",
   "url": "/docs/api/gfx/#colorattachment-cleared_resolving",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "loaded",
   "qualified": "cinder.gfx.commands.ColorAttachment.loaded",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "ColorAttachment",
   "signature": "loaded(view: WGPUTextureView) -> ColorAttachment",
   "summary": "Keeps the existing contents of view (load op Load) and stores the result.",
   "url": "/docs/api/gfx/#colorattachment-loaded",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "DepthAttachment",
   "qualified": "cinder.gfx.commands.DepthAttachment",
   "kind": "struct",
   "module": "cinder.gfx.commands",
   "signature": "struct DepthAttachment(ImplicitlyCopyable, Movable)",
   "summary": "Depth target. Reverse-Z clears to 0.0 (far).",
   "url": "/docs/api/gfx/#struct-depthattachment",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "none",
   "qualified": "cinder.gfx.commands.DepthAttachment.none",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "DepthAttachment",
   "signature": "none() -> DepthAttachment",
   "summary": "No depth target: begin_render_pass then passes no depth-stencil attachment.",
   "url": "/docs/api/gfx/#depthattachment-none",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "cleared_reverse_z",
   "qualified": "cinder.gfx.commands.DepthAttachment.cleared_reverse_z",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "DepthAttachment",
   "signature": "cleared_reverse_z(view: WGPUTextureView) -> DepthAttachment",
   "summary": "Clears view to 0.0 (the far plane under reverse-Z) and stores the result.",
   "url": "/docs/api/gfx/#depthattachment-cleared_reverse_z",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "RenderPass",
   "qualified": "cinder.gfx.commands.RenderPass",
   "kind": "struct",
   "module": "cinder.gfx.commands",
   "signature": "struct RenderPass(Movable)",
   "summary": "An open render pass. end must be called exactly once.",
   "url": "/docs/api/gfx/#struct-renderpass",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.commands.RenderPass.__init__",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "RenderPass",
   "signature": "__init__( out self, gfx: Pointer[Gfx, MutUntrackedOrigin], res: Pointer[Resources, MutUntrackedOrigin], raw: WGPURenderPassEncoder, )",
   "summary": "",
   "url": "/docs/api/gfx/#renderpass-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "set_pipeline",
   "qualified": "cinder.gfx.commands.RenderPass.set_pipeline",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "RenderPass",
   "signature": "set_pipeline(self, h: RenderPipelineHandle) raises",
   "summary": "Binds the render pipeline; raises if the handle is not live in Resources.",
   "url": "/docs/api/gfx/#renderpass-set_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "set_bind_group",
   "qualified": "cinder.gfx.commands.RenderPass.set_bind_group",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "RenderPass",
   "signature": "set_bind_group(self, index: UInt32, h: BindGroupHandle) raises",
   "summary": "Binds a bind group at group index with no dynamic offsets; raises on an invalid handle.",
   "url": "/docs/api/gfx/#renderpass-set_bind_group",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "set_bind_group_dynamic",
   "qualified": "cinder.gfx.commands.RenderPass.set_bind_group_dynamic",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "RenderPass",
   "signature": "set_bind_group_dynamic( self, index: UInt32, h: BindGroupHandle, mut offsets: List[UInt32] ) raises",
   "summary": "Binds a bind group at group index with one dynamic offset per dynamic binding. offsets is read during the call only. Raises on an invalid handle; a wrong offset count or alignment surfaces as a validation diagnostic through Gfx.pump.",
   "url": "/docs/api/gfx/#renderpass-set_bind_group_dynamic",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "set_vertex_buffer",
   "qualified": "cinder.gfx.commands.RenderPass.set_vertex_buffer",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "RenderPass",
   "signature": "set_vertex_buffer( self, slot: UInt32, h: BufferHandle, offset: UInt64 = 0 ) raises",
   "summary": "Binds h to vertex slot slot from offset to the end of the buffer. Raises on an invalid handle or when offset is not below the buffer size (nothing is bound then).",
   "url": "/docs/api/gfx/#renderpass-set_vertex_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "set_index_buffer",
   "qualified": "cinder.gfx.commands.RenderPass.set_index_buffer",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "RenderPass",
   "signature": "set_index_buffer( self, h: BufferHandle, format: WGPUIndexFormat, offset: UInt64 = 0 ) raises",
   "summary": "Binds h as the index buffer with format from offset to the end of the buffer. Raises on an invalid handle or when offset is not below the buffer size (nothing is bound then).",
   "url": "/docs/api/gfx/#renderpass-set_index_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "set_viewport",
   "qualified": "cinder.gfx.commands.RenderPass.set_viewport",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "RenderPass",
   "signature": "set_viewport( self, x: Float32, y: Float32, width: Float32, height: Float32 )",
   "summary": "Sets the viewport rectangle in pixels with depth range 0..1.",
   "url": "/docs/api/gfx/#renderpass-set_viewport",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "set_scissor",
   "qualified": "cinder.gfx.commands.RenderPass.set_scissor",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "RenderPass",
   "signature": "set_scissor(self, x: UInt32, y: UInt32, width: UInt32, height: UInt32)",
   "summary": "Sets the scissor rectangle in pixels.",
   "url": "/docs/api/gfx/#renderpass-set_scissor",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "draw",
   "qualified": "cinder.gfx.commands.RenderPass.draw",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "RenderPass",
   "signature": "draw( self, vertex_count: UInt32, instance_count: UInt32 = 1, first_vertex: UInt32 = 0, first_instance: UInt32 = 0, )",
   "summary": "Draws non-indexed primitives with the bound pipeline and vertex buffers.",
   "url": "/docs/api/gfx/#renderpass-draw",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "draw_indexed",
   "qualified": "cinder.gfx.commands.RenderPass.draw_indexed",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "RenderPass",
   "signature": "draw_indexed( self, index_count: UInt32, instance_count: UInt32 = 1, first_index: UInt32 = 0, base_vertex: Int32 = 0, first_instance: UInt32 = 0, )",
   "summary": "Draws indexed primitives from the bound index buffer; base_vertex is added to each index.",
   "url": "/docs/api/gfx/#renderpass-draw_indexed",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "end",
   "qualified": "cinder.gfx.commands.RenderPass.end",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "RenderPass",
   "signature": "end(mut self)",
   "summary": "Ends and releases the pass encoder. Later calls do nothing. A pass dropped without end is ended and released by its destructor, which runs right after the pass's last use, so the encoder is never left with an open pass.",
   "url": "/docs/api/gfx/#renderpass-end",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ComputePass",
   "qualified": "cinder.gfx.commands.ComputePass",
   "kind": "struct",
   "module": "cinder.gfx.commands",
   "signature": "struct ComputePass(Movable)",
   "summary": "An open compute pass from CommandEncoder.begin_compute_pass. end must be called exactly once.",
   "url": "/docs/api/gfx/#struct-computepass",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.commands.ComputePass.__init__",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "ComputePass",
   "signature": "__init__( out self, gfx: Pointer[Gfx, MutUntrackedOrigin], res: Pointer[Resources, MutUntrackedOrigin], raw: WGPUComputePassEncoder, )",
   "summary": "",
   "url": "/docs/api/gfx/#computepass-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "set_pipeline",
   "qualified": "cinder.gfx.commands.ComputePass.set_pipeline",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "ComputePass",
   "signature": "set_pipeline(self, h: ComputePipelineHandle) raises",
   "summary": "Binds the compute pipeline; raises if the handle is not live in Resources.",
   "url": "/docs/api/gfx/#computepass-set_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "set_bind_group",
   "qualified": "cinder.gfx.commands.ComputePass.set_bind_group",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "ComputePass",
   "signature": "set_bind_group(self, index: UInt32, h: BindGroupHandle) raises",
   "summary": "Binds a bind group at group index with no dynamic offsets; raises on an invalid handle.",
   "url": "/docs/api/gfx/#computepass-set_bind_group",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "set_bind_group_dynamic",
   "qualified": "cinder.gfx.commands.ComputePass.set_bind_group_dynamic",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "ComputePass",
   "signature": "set_bind_group_dynamic( self, index: UInt32, h: BindGroupHandle, mut offsets: List[UInt32] ) raises",
   "summary": "Binds a bind group at group index with one dynamic offset per dynamic binding. offsets is read during the call only. Raises on an invalid handle; a wrong offset count or alignment surfaces as a validation diagnostic through Gfx.pump.",
   "url": "/docs/api/gfx/#computepass-set_bind_group_dynamic",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "dispatch",
   "qualified": "cinder.gfx.commands.ComputePass.dispatch",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "ComputePass",
   "signature": "dispatch(self, x: UInt32, y: UInt32 = 1, z: UInt32 = 1)",
   "summary": "Dispatches an x by y by z grid of workgroups with the bound pipeline.",
   "url": "/docs/api/gfx/#computepass-dispatch",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "end",
   "qualified": "cinder.gfx.commands.ComputePass.end",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "ComputePass",
   "signature": "end(mut self)",
   "summary": "Ends and releases the pass encoder. Later calls do nothing. A pass dropped without end is ended and released by its destructor, which runs right after the pass's last use, so the encoder is never left with an open pass.",
   "url": "/docs/api/gfx/#computepass-end",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "command_encoder_descriptor",
   "qualified": "cinder.gfx.commands.command_encoder_descriptor",
   "kind": "def",
   "module": "cinder.gfx.commands",
   "signature": "def command_encoder_descriptor(ref label: String) -> WGPUCommandEncoderDescriptor",
   "summary": "The descriptor CommandEncoder creates its encoder with: no chain, label as the label. The view borrows label, which must outlive the wgpu call (keep it).",
   "url": "/docs/api/gfx/#def-command_encoder_descriptor",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "CommandEncoder",
   "qualified": "cinder.gfx.commands.CommandEncoder",
   "kind": "struct",
   "module": "cinder.gfx.commands",
   "signature": "struct CommandEncoder(Movable)",
   "summary": "Records one command buffer. finish_and_submit consumes it; an encoder dropped without it is released by its destructor and its commands are discarded.",
   "url": "/docs/api/gfx/#struct-commandencoder",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.commands.CommandEncoder.__init__",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "CommandEncoder",
   "signature": "__init__( out self, gfx: Pointer[Gfx, MutUntrackedOrigin], res: Pointer[Resources, MutUntrackedOrigin], label: String, ) raises",
   "summary": "",
   "url": "/docs/api/gfx/#commandencoder-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "begin_render_pass",
   "qualified": "cinder.gfx.commands.CommandEncoder.begin_render_pass",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "CommandEncoder",
   "signature": "begin_render_pass( self, colors: List[ColorAttachment], depth: DepthAttachment ) raises -> RenderPass",
   "summary": "Begins a render pass on the given colour targets and optional depth target. Raises when there are more than MAX_COLOR_ATTACHMENTS colours or wgpu returns NULL. The depth attachment is used only when depth.view is non-null; stencil is not used. Call RenderPass.end before recording anything else on this encoder.",
   "url": "/docs/api/gfx/#commandencoder-begin_render_pass",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "begin_compute_pass",
   "qualified": "cinder.gfx.commands.CommandEncoder.begin_compute_pass",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "CommandEncoder",
   "signature": "begin_compute_pass(self) raises -> ComputePass",
   "summary": "Begins a compute pass without timestamp writes; raises if wgpu returns NULL. Call ComputePass.end before recording anything else on this encoder.",
   "url": "/docs/api/gfx/#commandencoder-begin_compute_pass",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "copy_buffer_to_buffer",
   "qualified": "cinder.gfx.commands.CommandEncoder.copy_buffer_to_buffer",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "CommandEncoder",
   "signature": "copy_buffer_to_buffer( self, src: BufferHandle, src_offset: UInt64, dst: BufferHandle, dst_offset: UInt64, size: UInt64, ) raises",
   "summary": "Records a copy of size bytes between two buffers. Raises on an invalid handle; range and usage errors surface as validation diagnostics through Gfx.pump.",
   "url": "/docs/api/gfx/#commandencoder-copy_buffer_to_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "copy_texture_to_buffer",
   "qualified": "cinder.gfx.commands.CommandEncoder.copy_texture_to_buffer",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "CommandEncoder",
   "signature": "copy_texture_to_buffer( self, texture: TextureHandle, dst: BufferHandle, bytes_per_row: UInt32, width: UInt32, height: UInt32, ) raises",
   "summary": "Copies mip 0, layer 0 of a Resources texture into dst at offset 0, with bytes_per_row stride and height rows per image. Raises on an invalid handle.",
   "url": "/docs/api/gfx/#commandencoder-copy_texture_to_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "copy_raw_texture_to_buffer",
   "qualified": "cinder.gfx.commands.CommandEncoder.copy_raw_texture_to_buffer",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "CommandEncoder",
   "signature": "copy_raw_texture_to_buffer( self, texture: WGPUTexture, dst: BufferHandle, bytes_per_row: UInt32, width: UInt32, height: UInt32, ) raises",
   "summary": "Copies mip 0 of a texture outside Resources (a swapchain texture) into dst.",
   "url": "/docs/api/gfx/#commandencoder-copy_raw_texture_to_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "finish_and_submit",
   "qualified": "cinder.gfx.commands.CommandEncoder.finish_and_submit",
   "kind": "method",
   "module": "cinder.gfx.commands",
   "parent": "CommandEncoder",
   "signature": "finish_and_submit(deinit self) raises",
   "summary": "Finishes the encoder, submits the command buffer to the queue and releases both. Raises if wgpuCommandEncoderFinish returns NULL (the encoder is still released). Does not wait for the GPU; use wait_for_queue for that.",
   "url": "/docs/api/gfx/#commandencoder-finish_and_submit",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "wait_for_queue",
   "qualified": "cinder.gfx.commands.wait_for_queue",
   "kind": "def",
   "module": "cinder.gfx.commands",
   "signature": "def wait_for_queue(mut gfx: Gfx) raises GfxError",
   "summary": "Blocks until all submitted work has completed (tests and shutdown; never in the frame loop).",
   "url": "/docs/api/gfx/#def-wait_for_queue",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "read_buffer",
   "qualified": "cinder.gfx.commands.read_buffer",
   "kind": "def",
   "module": "cinder.gfx.commands",
   "signature": "def read_buffer( mut gfx: Gfx, res: Resources, buffer: BufferHandle, size: Int ) raises -> List[UInt8]",
   "summary": "Maps a MapRead buffer, copies size bytes out and unmaps it (tests and tools only).",
   "url": "/docs/api/gfx/#def-read_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "debug_draw",
   "qualified": "cinder.gfx.debug_draw",
   "kind": "module",
   "module": "cinder.gfx.debug_draw",
   "signature": "",
   "summary": "Immediate-mode debug lines: segments, boxes, spheres, axes and grids drawn in one line-list pass. Vertices accumulate on the CPU each frame (line, aabb, ...) and are uploaded once in flush, which records the draw into an open RenderPass. The vertex buffer grows by doubling and is never shrunk, so the steady state allocates nothing. Depth testing is reverse-Z when a depth format is given;…",
   "url": "/docs/api/gfx/#cindergfxdebug_draw",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "Color8",
   "qualified": "cinder.gfx.debug_draw.Color8",
   "kind": "struct",
   "module": "cinder.gfx.debug_draw",
   "signature": "struct Color8(Equatable, ImplicitlyCopyable, RegisterPassable)",
   "summary": "8-bit RGBA colour.",
   "url": "/docs/api/gfx/#struct-color8",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "red",
   "qualified": "cinder.gfx.debug_draw.Color8.red",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "Color8",
   "signature": "red() -> Color8",
   "summary": "Opaque red (255, 0, 0, 255).",
   "url": "/docs/api/gfx/#color8-red",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "green",
   "qualified": "cinder.gfx.debug_draw.Color8.green",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "Color8",
   "signature": "green() -> Color8",
   "summary": "Opaque green (0, 255, 0, 255).",
   "url": "/docs/api/gfx/#color8-green",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "blue",
   "qualified": "cinder.gfx.debug_draw.Color8.blue",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "Color8",
   "signature": "blue() -> Color8",
   "summary": "Opaque blue (0, 0, 255, 255).",
   "url": "/docs/api/gfx/#color8-blue",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "white",
   "qualified": "cinder.gfx.debug_draw.Color8.white",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "Color8",
   "signature": "white() -> Color8",
   "summary": "Opaque white (255, 255, 255, 255).",
   "url": "/docs/api/gfx/#color8-white",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "yellow",
   "qualified": "cinder.gfx.debug_draw.Color8.yellow",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "Color8",
   "signature": "yellow() -> Color8",
   "summary": "Opaque yellow (255, 255, 0, 255).",
   "url": "/docs/api/gfx/#color8-yellow",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "DebugDraw",
   "qualified": "cinder.gfx.debug_draw.DebugDraw",
   "kind": "struct",
   "module": "cinder.gfx.debug_draw",
   "signature": "struct DebugDraw(Movable)",
   "summary": "Per-frame line accumulator plus the GPU objects that draw it.",
   "url": "/docs/api/gfx/#struct-debugdraw",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.debug_draw.DebugDraw.__init__",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "DebugDraw",
   "signature": "__init__( out self, gfx: Pointer[Gfx, MutUntrackedOrigin], res: Pointer[Resources, MutUntrackedOrigin], mut shaders: ShaderManager, color_format: WGPUTextureFormat, depth_format: WGPUTextureFormat = WGPUTextureFormat_Undefined, initial_capacity: Int = 4096, ) raises",
   "summary": "",
   "url": "/docs/api/gfx/#debugdraw-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "clear",
   "qualified": "cinder.gfx.debug_draw.DebugDraw.clear",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "DebugDraw",
   "signature": "clear(mut self)",
   "summary": "Drops this frame's lines (called by flush).",
   "url": "/docs/api/gfx/#debugdraw-clear",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "line",
   "qualified": "cinder.gfx.debug_draw.DebugDraw.line",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "DebugDraw",
   "signature": "line(mut self, a: Vec3, b: Vec3, color: Color8)",
   "summary": "Queues one world-space segment from a to b for this frame (two vertices). Only CPU memory grows here; upload enlarges the GPU buffer if needed, flush draws and clears.",
   "url": "/docs/api/gfx/#debugdraw-line",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "aabb",
   "qualified": "cinder.gfx.debug_draw.DebugDraw.aabb",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "DebugDraw",
   "signature": "aabb(mut self, min: Vec3, max: Vec3, color: Color8)",
   "summary": "The 12 edges of an axis-aligned box.",
   "url": "/docs/api/gfx/#debugdraw-aabb",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "sphere",
   "qualified": "cinder.gfx.debug_draw.DebugDraw.sphere",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "DebugDraw",
   "signature": "sphere( mut self, centre: Vec3, radius: Float32, color: Color8, segments: Int = 24, )",
   "summary": "Three great circles (XY, XZ, YZ).",
   "url": "/docs/api/gfx/#debugdraw-sphere",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "axes",
   "qualified": "cinder.gfx.debug_draw.DebugDraw.axes",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "DebugDraw",
   "signature": "axes(mut self, origin: Vec3, length: Float32)",
   "summary": "X red, Y green, Z blue.",
   "url": "/docs/api/gfx/#debugdraw-axes",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "grid",
   "qualified": "cinder.gfx.debug_draw.DebugDraw.grid",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "DebugDraw",
   "signature": "grid(mut self, half_extent: Int, spacing: Float32, color: Color8)",
   "summary": "An XZ ground grid centred on the origin with 2 * half_extent + 1 lines per axis.",
   "url": "/docs/api/gfx/#debugdraw-grid",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "upload",
   "qualified": "cinder.gfx.debug_draw.DebugDraw.upload",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "DebugDraw",
   "signature": "upload(mut self, view_proj: Mat4) raises",
   "summary": "Writes the camera and this frame's vertices to the GPU (before the render pass opens).",
   "url": "/docs/api/gfx/#debugdraw-upload",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "flush",
   "qualified": "cinder.gfx.debug_draw.DebugDraw.flush",
   "kind": "method",
   "module": "cinder.gfx.debug_draw",
   "parent": "DebugDraw",
   "signature": "flush(mut self, pass_: RenderPass) raises",
   "summary": "Records the draw for the vertices uploaded by upload, then clears them.",
   "url": "/docs/api/gfx/#debugdraw-flush",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "device",
   "qualified": "cinder.gfx.device",
   "kind": "module",
   "module": "cinder.gfx.device",
   "signature": "",
   "summary": "Gfx: instance, adapter, device and queue, with every wgpu callback pulled from the shim queue.",
   "url": "/docs/api/gfx/#cindergfxdevice",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "GfxError",
   "qualified": "cinder.gfx.device.GfxError",
   "kind": "struct",
   "module": "cinder.gfx.device",
   "signature": "struct GfxError(Copyable, Movable, Writable)",
   "summary": "A recoverable graphics failure (adapter/device request, timeout, lost device).",
   "url": "/docs/api/gfx/#struct-gfxerror",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.gfx.device.GfxError.write_to",
   "kind": "method",
   "module": "cinder.gfx.device",
   "parent": "GfxError",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/gfx/#gfxerror-write_to",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "Gfx",
   "qualified": "cinder.gfx.device.Gfx",
   "kind": "struct",
   "module": "cinder.gfx.device",
   "signature": "struct Gfx(Movable)",
   "summary": "Owns one wgpu instance, adapter, device and queue. Callbacks never run in Mojo: pump drives wgpu and drains the shim's event queue, turning log lines, uncaptured validation errors and device loss into diagnostics (LogRecords for the engine logger) while returning every other event to the caller that awaits it.",
   "url": "/docs/api/gfx/#struct-gfx",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.device.Gfx.__init__",
   "kind": "method",
   "module": "cinder.gfx.device",
   "parent": "Gfx",
   "signature": "__init__( out self, lib: NativePtr, surface: WGPUSurface ) raises GfxError",
   "summary": "Creates instance, adapter (compatible with surface when given) and device.",
   "url": "/docs/api/gfx/#gfx-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.device.Gfx.__init__",
   "kind": "method",
   "module": "cinder.gfx.device",
   "parent": "Gfx",
   "signature": "__init__(out self, lib: NativePtr, ref window: Window) raises GfxError",
   "summary": "Creates instance, a surface for window, a compatible adapter and device. Gfx keeps the surface (surface field) and destroys it at teardown.",
   "url": "/docs/api/gfx/#gfx-__init__-1",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.device.Gfx.__init__",
   "kind": "method",
   "module": "cinder.gfx.device",
   "parent": "Gfx",
   "signature": "__init__( out self, lib: NativePtr, surface: WGPUSurface, window: Optional[Pointer[Window, MutUntrackedOrigin]], ) raises GfxError",
   "summary": "",
   "url": "/docs/api/gfx/#gfx-__init__-2",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "next_request_id",
   "qualified": "cinder.gfx.device.Gfx.next_request_id",
   "kind": "method",
   "module": "cinder.gfx.device",
   "parent": "Gfx",
   "signature": "next_request_id(mut self) -> UInt64",
   "summary": "Returns a fresh id (1, 2, ...) that tags an async shim request so its reply event can be matched by await_event / take_pending.",
   "url": "/docs/api/gfx/#gfx-next_request_id",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "pump",
   "qualified": "cinder.gfx.device.Gfx.pump",
   "kind": "method",
   "module": "cinder.gfx.device",
   "parent": "Gfx",
   "signature": "pump(mut self, wait: Bool)",
   "summary": "Drives wgpu callbacks and drains the shim queue. Log, error and device-lost events become diagnostics; everything else is held for await_event / take_pending.",
   "url": "/docs/api/gfx/#gfx-pump",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "await_event",
   "qualified": "cinder.gfx.device.Gfx.await_event",
   "kind": "method",
   "module": "cinder.gfx.device",
   "parent": "Gfx",
   "signature": "await_event( mut self, kind: UInt32, request_id: UInt64, timeout_ns: Int = DEFAULT_TIMEOUT_NS, ) raises GfxError -> CnEvent",
   "summary": "Pumps until the event (kind, request id) arrives; raises GfxError on timeout.",
   "url": "/docs/api/gfx/#gfx-await_event",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "take_pending",
   "qualified": "cinder.gfx.device.Gfx.take_pending",
   "kind": "method",
   "module": "cinder.gfx.device",
   "parent": "Gfx",
   "signature": "take_pending( mut self, kind: UInt32, request_id: UInt64, mut out: List[CnEvent] )",
   "summary": "Moves every pending event matching (kind, request id) into out, in arrival order.",
   "url": "/docs/api/gfx/#gfx-take_pending",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "take_diagnostics",
   "qualified": "cinder.gfx.device.Gfx.take_diagnostics",
   "kind": "method",
   "module": "cinder.gfx.device",
   "parent": "Gfx",
   "signature": "take_diagnostics(mut self) -> List[LogRecord]",
   "summary": "Returns and clears the LogRecords collected by pump: wgpu log lines (wgpu), uncaptured validation errors (wgpu.validation) and device loss (wgpu.device). error_count and lost are not reset.",
   "url": "/docs/api/gfx/#gfx-take_diagnostics",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "pipeline",
   "qualified": "cinder.gfx.pipeline",
   "kind": "module",
   "module": "cinder.gfx.pipeline",
   "signature": "",
   "summary": "Typed descriptors for bind group layouts, bind groups, pipeline layouts and pipelines. Each create_* builds the wgpu descriptor from engine-side structs, calls wgpu with every pointee kept alive for the call, and adopts the result into Resources under a typed handle.",
   "url": "/docs/api/gfx/#cindergfxpipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "BindingKind",
   "qualified": "cinder.gfx.pipeline.BindingKind",
   "kind": "struct",
   "module": "cinder.gfx.pipeline",
   "signature": "struct BindingKind(Equatable, ImplicitlyCopyable, RegisterPassable)",
   "summary": "What a bind group layout slot holds.",
   "url": "/docs/api/gfx/#struct-bindingkind",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "uniform_buffer",
   "qualified": "cinder.gfx.pipeline.BindingKind.uniform_buffer",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "uniform_buffer() -> BindingKind",
   "summary": "Uniform buffer; LayoutEntry.dynamic_offset and min_binding_size apply.",
   "url": "/docs/api/gfx/#bindingkind-uniform_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "storage_buffer",
   "qualified": "cinder.gfx.pipeline.BindingKind.storage_buffer",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "storage_buffer() -> BindingKind",
   "summary": "Read-write storage buffer; dynamic_offset and min_binding_size apply.",
   "url": "/docs/api/gfx/#bindingkind-storage_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "readonly_storage_buffer",
   "qualified": "cinder.gfx.pipeline.BindingKind.readonly_storage_buffer",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "readonly_storage_buffer() -> BindingKind",
   "summary": "Read-only storage buffer; dynamic_offset and min_binding_size apply.",
   "url": "/docs/api/gfx/#bindingkind-readonly_storage_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "texture_2d",
   "qualified": "cinder.gfx.pipeline.BindingKind.texture_2d",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "texture_2d() -> BindingKind",
   "summary": "Filterable float texture with a 2D view dimension.",
   "url": "/docs/api/gfx/#bindingkind-texture_2d",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "sampler",
   "qualified": "cinder.gfx.pipeline.BindingKind.sampler",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "sampler() -> BindingKind",
   "summary": "Filtering sampler.",
   "url": "/docs/api/gfx/#bindingkind-sampler",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "comparison_sampler",
   "qualified": "cinder.gfx.pipeline.BindingKind.comparison_sampler",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "comparison_sampler() -> BindingKind",
   "summary": "Comparison sampler, as made by Resources.create_comparison_sampler.",
   "url": "/docs/api/gfx/#bindingkind-comparison_sampler",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "depth_texture_2d",
   "qualified": "cinder.gfx.pipeline.BindingKind.depth_texture_2d",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "depth_texture_2d() -> BindingKind",
   "summary": "Depth texture with a 2D view dimension.",
   "url": "/docs/api/gfx/#bindingkind-depth_texture_2d",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "depth_texture_2d_array",
   "qualified": "cinder.gfx.pipeline.BindingKind.depth_texture_2d_array",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "depth_texture_2d_array() -> BindingKind",
   "summary": "Depth texture with a 2D-array view dimension.",
   "url": "/docs/api/gfx/#bindingkind-depth_texture_2d_array",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "texture_cube",
   "qualified": "cinder.gfx.pipeline.BindingKind.texture_cube",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "texture_cube() -> BindingKind",
   "summary": "Filterable float texture with a cube view dimension.",
   "url": "/docs/api/gfx/#bindingkind-texture_cube",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "texture_2d_array",
   "qualified": "cinder.gfx.pipeline.BindingKind.texture_2d_array",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "texture_2d_array() -> BindingKind",
   "summary": "Filterable float texture with a 2D-array view dimension.",
   "url": "/docs/api/gfx/#bindingkind-texture_2d_array",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "storage_texture_2d_write",
   "qualified": "cinder.gfx.pipeline.BindingKind.storage_texture_2d_write",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "storage_texture_2d_write() -> BindingKind",
   "summary": "Write-only storage texture; LayoutEntry.format names the texel format.",
   "url": "/docs/api/gfx/#bindingkind-storage_texture_2d_write",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "storage_texture_2d_array_write",
   "qualified": "cinder.gfx.pipeline.BindingKind.storage_texture_2d_array_write",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "storage_texture_2d_array_write() -> BindingKind",
   "summary": "Write-only storage texture with a 2D-array view; LayoutEntry.format names the texel format.",
   "url": "/docs/api/gfx/#bindingkind-storage_texture_2d_array_write",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "depth_texture_multisampled_2d",
   "qualified": "cinder.gfx.pipeline.BindingKind.depth_texture_multisampled_2d",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "depth_texture_multisampled_2d() -> BindingKind",
   "summary": "Multisampled depth texture with a 2D view dimension.",
   "url": "/docs/api/gfx/#bindingkind-depth_texture_multisampled_2d",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "non_filtering_sampler",
   "qualified": "cinder.gfx.pipeline.BindingKind.non_filtering_sampler",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "non_filtering_sampler() -> BindingKind",
   "summary": "Non-filtering sampler, for use with texture_2d_unfilterable textures.",
   "url": "/docs/api/gfx/#bindingkind-non_filtering_sampler",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "texture_2d_unfilterable",
   "qualified": "cinder.gfx.pipeline.BindingKind.texture_2d_unfilterable",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingKind",
   "signature": "texture_2d_unfilterable() -> BindingKind",
   "summary": "Float texture read with textureLoad or a non-filtering sampler (RGBA32Float).",
   "url": "/docs/api/gfx/#bindingkind-texture_2d_unfilterable",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "LayoutEntry",
   "qualified": "cinder.gfx.pipeline.LayoutEntry",
   "kind": "struct",
   "module": "cinder.gfx.pipeline",
   "signature": "struct LayoutEntry(ImplicitlyCopyable, Movable)",
   "summary": "One slot of a bind group layout. format matters for storage textures only.",
   "url": "/docs/api/gfx/#struct-layoutentry",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.pipeline.LayoutEntry.__init__",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "LayoutEntry",
   "signature": "__init__( out self, binding: UInt32, visibility: UInt64, kind: BindingKind, dynamic_offset: Bool = False, min_binding_size: UInt64 = 0, format: WGPUTextureFormat = WGPUTextureFormat_Undefined, )",
   "summary": "",
   "url": "/docs/api/gfx/#layoutentry-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "BindingResource",
   "qualified": "cinder.gfx.pipeline.BindingResource",
   "kind": "struct",
   "module": "cinder.gfx.pipeline",
   "signature": "struct BindingResource(ImplicitlyCopyable, Movable)",
   "summary": "What to bind in a slot: exactly one of buffer, texture view or sampler is non-null.",
   "url": "/docs/api/gfx/#struct-bindingresource",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "for_buffer",
   "qualified": "cinder.gfx.pipeline.BindingResource.for_buffer",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingResource",
   "signature": "for_buffer( binding: UInt32, buffer: BufferHandle, offset: UInt64, size: UInt64 ) -> BindingResource",
   "summary": "Binds size bytes of buffer from offset; a size of 0 binds from offset to the end of the buffer (resolved in create_bind_group).",
   "url": "/docs/api/gfx/#bindingresource-for_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "for_texture",
   "qualified": "cinder.gfx.pipeline.BindingResource.for_texture",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingResource",
   "signature": "for_texture( binding: UInt32, view: TextureViewHandle ) -> BindingResource",
   "summary": "Binds a texture view from Resources (owned or imported).",
   "url": "/docs/api/gfx/#bindingresource-for_texture",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "for_sampler",
   "qualified": "cinder.gfx.pipeline.BindingResource.for_sampler",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BindingResource",
   "signature": "for_sampler(binding: UInt32, sampler: SamplerHandle) -> BindingResource",
   "summary": "Binds a sampler from Resources.",
   "url": "/docs/api/gfx/#bindingresource-for_sampler",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "VertexAttribute",
   "qualified": "cinder.gfx.pipeline.VertexAttribute",
   "kind": "struct",
   "module": "cinder.gfx.pipeline",
   "signature": "struct VertexAttribute(ImplicitlyCopyable, Movable)",
   "summary": "One vertex attribute: its format, byte offset within the vertex and shader location.",
   "url": "/docs/api/gfx/#struct-vertexattribute",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "VertexLayout",
   "qualified": "cinder.gfx.pipeline.VertexLayout",
   "kind": "struct",
   "module": "cinder.gfx.pipeline",
   "signature": "struct VertexLayout(Copyable, Movable)",
   "summary": "One vertex buffer slot: stride, step mode and attributes.",
   "url": "/docs/api/gfx/#struct-vertexlayout",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.pipeline.VertexLayout.__init__",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "VertexLayout",
   "signature": "__init__( out self, stride: UInt64, var attributes: List[VertexAttribute], step_mode: WGPUVertexStepMode = WGPUVertexStepMode_Vertex, )",
   "summary": "",
   "url": "/docs/api/gfx/#vertexlayout-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "DepthState",
   "qualified": "cinder.gfx.pipeline.DepthState",
   "kind": "struct",
   "module": "cinder.gfx.pipeline",
   "signature": "struct DepthState(ImplicitlyCopyable, Movable)",
   "summary": "Depth testing. Reverse-Z means GreaterEqual is the engine's default compare.",
   "url": "/docs/api/gfx/#struct-depthstate",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.pipeline.DepthState.__init__",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "DepthState",
   "signature": "__init__( out self, format: WGPUTextureFormat, write: Bool, compare: WGPUCompareFunction, bias: Int32 = 0, bias_slope: Float32 = 0.0, bias_clamp: Float32 = 0.0, )",
   "summary": "",
   "url": "/docs/api/gfx/#depthstate-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "none",
   "qualified": "cinder.gfx.pipeline.DepthState.none",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "DepthState",
   "signature": "none() -> DepthState",
   "summary": "No depth-stencil state: build_render_pipeline omits it because the format is Undefined.",
   "url": "/docs/api/gfx/#depthstate-none",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "reverse_z",
   "qualified": "cinder.gfx.pipeline.DepthState.reverse_z",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "DepthState",
   "signature": "reverse_z(format: WGPUTextureFormat, write: Bool = True) -> DepthState",
   "summary": "Reverse-Z depth test (GreaterEqual) on format, writing depth unless write is False, with no bias.",
   "url": "/docs/api/gfx/#depthstate-reverse_z",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "reverse_z_biased",
   "qualified": "cinder.gfx.pipeline.DepthState.reverse_z_biased",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "DepthState",
   "signature": "reverse_z_biased( format: WGPUTextureFormat, bias: Int32, bias_slope: Float32 ) -> DepthState",
   "summary": "Shadow-map depth: reverse-Z, written, with constant and slope bias (negative values push depth away from the light in reverse-Z).",
   "url": "/docs/api/gfx/#depthstate-reverse_z_biased",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "BlendMode",
   "qualified": "cinder.gfx.pipeline.BlendMode",
   "kind": "struct",
   "module": "cinder.gfx.pipeline",
   "signature": "struct BlendMode(Equatable, ImplicitlyCopyable, RegisterPassable)",
   "summary": "Colour blending preset of a ColorTarget, expanded to a WGPUBlendState when a pipeline is built. Any value other than alpha or additive builds as opaque.",
   "url": "/docs/api/gfx/#struct-blendmode",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "opaque",
   "qualified": "cinder.gfx.pipeline.BlendMode.opaque",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BlendMode",
   "signature": "opaque() -> BlendMode",
   "summary": "No blending: the source replaces the destination (One, Zero).",
   "url": "/docs/api/gfx/#blendmode-opaque",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "alpha",
   "qualified": "cinder.gfx.pipeline.BlendMode.alpha",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BlendMode",
   "signature": "alpha() -> BlendMode",
   "summary": "Premultiplied-free source-over: src * a + dst * (1 - a).",
   "url": "/docs/api/gfx/#blendmode-alpha",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "additive",
   "qualified": "cinder.gfx.pipeline.BlendMode.additive",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "BlendMode",
   "signature": "additive() -> BlendMode",
   "summary": "Adds source to destination for colour and alpha (One, One).",
   "url": "/docs/api/gfx/#blendmode-additive",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ColorTarget",
   "qualified": "cinder.gfx.pipeline.ColorTarget",
   "kind": "struct",
   "module": "cinder.gfx.pipeline",
   "signature": "struct ColorTarget(ImplicitlyCopyable, Movable)",
   "summary": "One colour output of a render pipeline: its texture format and blend mode, written with all channels enabled.",
   "url": "/docs/api/gfx/#struct-colortarget",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "RenderPipelineDesc",
   "qualified": "cinder.gfx.pipeline.RenderPipelineDesc",
   "kind": "struct",
   "module": "cinder.gfx.pipeline",
   "signature": "struct RenderPipelineDesc(Copyable, Movable)",
   "summary": "Everything needed for a render pipeline. Entry points name functions in shader.",
   "url": "/docs/api/gfx/#struct-renderpipelinedesc",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.pipeline.RenderPipelineDesc.__init__",
   "kind": "method",
   "module": "cinder.gfx.pipeline",
   "parent": "RenderPipelineDesc",
   "signature": "__init__( out self, label: String, layout: PipelineLayoutHandle, shader: ShaderHandle, vertex_entry: String, fragment_entry: String, var vertex_layouts: List[VertexLayout], var color_targets: List[ColorTarget], depth: DepthState = DepthState.none(), topology: WGPUPrimitiveTopology = WGPUPrimitiveTopology_TriangleList, cull_mode: WGPUCullMode = WGPUCullMode_None, sample_count: UInt32 = 1, wireframe: Bool = False, front_face_cw: Bool = False, )",
   "summary": "",
   "url": "/docs/api/gfx/#renderpipelinedesc-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "create_bind_group_layout",
   "qualified": "cinder.gfx.pipeline.create_bind_group_layout",
   "kind": "def",
   "module": "cinder.gfx.pipeline",
   "signature": "def create_bind_group_layout( mut res: Resources, label: String, entries: List[LayoutEntry] ) raises -> BindGroupLayoutHandle",
   "summary": "Creates a WGPUBindGroupLayout from entries and adopts it into res. Each entry becomes a buffer, sampler, texture or storage-texture layout according to its BindingKind; a kind not handled here leaves every binding type unused. Raises if wgpu returns NULL; other validation errors surface through Gfx.pump diagnostics. The caller destroys the handle with Resources.destroy_bind_group_layout.",
   "url": "/docs/api/gfx/#def-create_bind_group_layout",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "create_pipeline_layout",
   "qualified": "cinder.gfx.pipeline.create_pipeline_layout",
   "kind": "def",
   "module": "cinder.gfx.pipeline",
   "signature": "def create_pipeline_layout( mut res: Resources, label: String, layouts: List[BindGroupLayoutHandle] ) raises -> PipelineLayoutHandle",
   "summary": "Creates a WGPUPipelineLayout whose bind group layouts are in group order and adopts it. Raises on an invalid layout handle or a NULL result. The caller destroys the handle with Resources.destroy_pipeline_layout.",
   "url": "/docs/api/gfx/#def-create_pipeline_layout",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "create_bind_group",
   "qualified": "cinder.gfx.pipeline.create_bind_group",
   "kind": "def",
   "module": "cinder.gfx.pipeline",
   "signature": "def create_bind_group( mut res: Resources, label: String, layout: BindGroupLayoutHandle, bindings: List[BindingResource], ) raises -> BindGroupHandle",
   "summary": "Creates a WGPUBindGroup for layout from bindings and adopts it into res. The raw wgpu objects behind the handles are captured at creation time; replacing them behind the same handle later does not update this bind group. Raises on any invalid handle or a NULL result; mismatches with the layout surface through Gfx.pump diagnostics. The caller destroys the handle with Resources.destroy_bind_group.",
   "url": "/docs/api/gfx/#def-create_bind_group",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "build_render_pipeline",
   "qualified": "cinder.gfx.pipeline.build_render_pipeline",
   "kind": "def",
   "module": "cinder.gfx.pipeline",
   "signature": "def build_render_pipeline( res: Resources, desc: RenderPipelineDesc ) raises -> WGPURenderPipeline",
   "summary": "Creates the raw pipeline object (used by create_render_pipeline and by hot reload). Raises on an invalid handle, a NULL result, or a validation error drained right after creation; the invalid object is then released and the error carries wgpu's validation message. The caller owns the returned object.",
   "url": "/docs/api/gfx/#def-build_render_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "create_render_pipeline",
   "qualified": "cinder.gfx.pipeline.create_render_pipeline",
   "kind": "def",
   "module": "cinder.gfx.pipeline",
   "signature": "def create_render_pipeline( mut res: Resources, desc: RenderPipelineDesc ) raises -> RenderPipelineHandle",
   "summary": "Builds a render pipeline with build_render_pipeline and adopts it into res. Raises if creation fails, including validation errors drained right after creation. The caller destroys the handle with Resources.destroy_render_pipeline.",
   "url": "/docs/api/gfx/#def-create_render_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "build_compute_pipeline",
   "qualified": "cinder.gfx.pipeline.build_compute_pipeline",
   "kind": "def",
   "module": "cinder.gfx.pipeline",
   "signature": "def build_compute_pipeline( res: Resources, label: String, layout: PipelineLayoutHandle, shader: ShaderHandle, entry: String, ) raises -> WGPUComputePipeline",
   "summary": "Creates the raw compute pipeline object, adopted by create_compute_pipeline or passed to Resources.replace_compute_pipeline to swap it behind an existing handle. A null layout handle passes a null pipeline layout to wgpu. Raises on an invalid handle, a NULL result, or a validation error drained right after creation; the invalid object is then released and the error carries wgpu's validation…",
   "url": "/docs/api/gfx/#def-build_compute_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "create_compute_pipeline",
   "qualified": "cinder.gfx.pipeline.create_compute_pipeline",
   "kind": "def",
   "module": "cinder.gfx.pipeline",
   "signature": "def create_compute_pipeline( mut res: Resources, label: String, layout: PipelineLayoutHandle, shader: ShaderHandle, entry: String, ) raises -> ComputePipelineHandle",
   "summary": "Builds a compute pipeline with build_compute_pipeline and adopts it into res. The caller destroys the handle with Resources.destroy_compute_pipeline.",
   "url": "/docs/api/gfx/#def-create_compute_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "resources",
   "qualified": "cinder.gfx.resources",
   "kind": "module",
   "module": "cinder.gfx.resources",
   "signature": "",
   "summary": "Typed GPU resources: one handle type per kind, pooled records, ownership and leak tracking. Every resource created through Resources is tracked in a generational pool for its kind, so a BufferHandle cannot be passed where a TextureHandle is expected (compile error), stale handles fail validation (raise), and live_counts() reports exactly what is still alive. Check live_counts().total() == 0…",
   "url": "/docs/api/gfx/#cindergfxresources",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "BufferTag",
   "qualified": "cinder.gfx.resources.BufferTag",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct BufferTag",
   "summary": "Phantom tag that makes BufferHandle a distinct type.",
   "url": "/docs/api/gfx/#struct-buffertag",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "TextureTag",
   "qualified": "cinder.gfx.resources.TextureTag",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct TextureTag",
   "summary": "Phantom tag that makes TextureHandle a distinct type.",
   "url": "/docs/api/gfx/#struct-texturetag",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "TextureViewTag",
   "qualified": "cinder.gfx.resources.TextureViewTag",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct TextureViewTag",
   "summary": "Phantom tag that makes TextureViewHandle a distinct type.",
   "url": "/docs/api/gfx/#struct-textureviewtag",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "SamplerTag",
   "qualified": "cinder.gfx.resources.SamplerTag",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct SamplerTag",
   "summary": "Phantom tag that makes SamplerHandle a distinct type.",
   "url": "/docs/api/gfx/#struct-samplertag",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ShaderTag",
   "qualified": "cinder.gfx.resources.ShaderTag",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct ShaderTag",
   "summary": "Phantom tag that makes ShaderHandle a distinct type.",
   "url": "/docs/api/gfx/#struct-shadertag",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "BindGroupLayoutTag",
   "qualified": "cinder.gfx.resources.BindGroupLayoutTag",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct BindGroupLayoutTag",
   "summary": "Phantom tag that makes BindGroupLayoutHandle a distinct type.",
   "url": "/docs/api/gfx/#struct-bindgrouplayouttag",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "PipelineLayoutTag",
   "qualified": "cinder.gfx.resources.PipelineLayoutTag",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct PipelineLayoutTag",
   "summary": "Phantom tag that makes PipelineLayoutHandle a distinct type.",
   "url": "/docs/api/gfx/#struct-pipelinelayouttag",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "BindGroupTag",
   "qualified": "cinder.gfx.resources.BindGroupTag",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct BindGroupTag",
   "summary": "Phantom tag that makes BindGroupHandle a distinct type.",
   "url": "/docs/api/gfx/#struct-bindgrouptag",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "RenderPipelineTag",
   "qualified": "cinder.gfx.resources.RenderPipelineTag",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct RenderPipelineTag",
   "summary": "Phantom tag that makes RenderPipelineHandle a distinct type.",
   "url": "/docs/api/gfx/#struct-renderpipelinetag",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ComputePipelineTag",
   "qualified": "cinder.gfx.resources.ComputePipelineTag",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct ComputePipelineTag",
   "summary": "Phantom tag that makes ComputePipelineHandle a distinct type.",
   "url": "/docs/api/gfx/#struct-computepipelinetag",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "BufferDesc",
   "qualified": "cinder.gfx.resources.BufferDesc",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct BufferDesc(Copyable, Movable)",
   "summary": "What to create a buffer with. usage is a WGPUBufferUsage bit set.",
   "url": "/docs/api/gfx/#struct-bufferdesc",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "TextureDesc",
   "qualified": "cinder.gfx.resources.TextureDesc",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct TextureDesc(Copyable, Movable)",
   "summary": "A 2D texture (array layers and 3D arrive with the renderer). usage is WGPUTextureUsage bits.",
   "url": "/docs/api/gfx/#struct-texturedesc",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "SamplerDesc",
   "qualified": "cinder.gfx.resources.SamplerDesc",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct SamplerDesc(Copyable, Movable)",
   "summary": "Filtering and addressing. linear selects trilinear filtering; otherwise nearest.",
   "url": "/docs/api/gfx/#struct-samplerdesc",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "BufferRecord",
   "qualified": "cinder.gfx.resources.BufferRecord",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct BufferRecord(Copyable, Movable)",
   "summary": "Pool entry for a buffer: the WGPUBuffer plus the size and usage it was created with. Copies handed out by Resources.buffer share the raw object; only the pool releases it.",
   "url": "/docs/api/gfx/#struct-bufferrecord",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "TextureRecord",
   "qualified": "cinder.gfx.resources.TextureRecord",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct TextureRecord(Copyable, Movable)",
   "summary": "Pool entry for a texture: the WGPUTexture plus the extent, mip count, format and usage it was created with. Copies share the raw object; only the pool releases it.",
   "url": "/docs/api/gfx/#struct-texturerecord",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "TextureViewRecord",
   "qualified": "cinder.gfx.resources.TextureViewRecord",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct TextureViewRecord(Copyable, Movable)",
   "summary": "Pool entry for a view: the WGPUTextureView and the texture it views. texture is null for views wrapped by import_texture_view, whose raw object the caller owns (is_imported).",
   "url": "/docs/api/gfx/#struct-textureviewrecord",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "is_imported",
   "qualified": "cinder.gfx.resources.TextureViewRecord.is_imported",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "TextureViewRecord",
   "signature": "is_imported(self) -> Bool",
   "summary": "True for a view wrapped by import_texture_view: Resources never releases it.",
   "url": "/docs/api/gfx/#textureviewrecord-is_imported",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "SamplerRecord",
   "qualified": "cinder.gfx.resources.SamplerRecord",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct SamplerRecord(Copyable, Movable)",
   "summary": "Pool entry for a sampler: the WGPUSampler, released by Resources.destroy_sampler.",
   "url": "/docs/api/gfx/#struct-samplerrecord",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ShaderRecord",
   "qualified": "cinder.gfx.resources.ShaderRecord",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct ShaderRecord(Copyable, Movable)",
   "summary": "Pool entry for a shader: the WGPUShaderModule and the WGSL path it was compiled from. ShaderManager swaps raw in place on hot reload, keeping the handle stable.",
   "url": "/docs/api/gfx/#struct-shaderrecord",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "BindGroupLayoutRecord",
   "qualified": "cinder.gfx.resources.BindGroupLayoutRecord",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct BindGroupLayoutRecord(Copyable, Movable)",
   "summary": "Pool entry for a bind group layout: the WGPUBindGroupLayout the pool owns.",
   "url": "/docs/api/gfx/#struct-bindgrouplayoutrecord",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "PipelineLayoutRecord",
   "qualified": "cinder.gfx.resources.PipelineLayoutRecord",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct PipelineLayoutRecord(Copyable, Movable)",
   "summary": "Pool entry for a pipeline layout: the WGPUPipelineLayout the pool owns.",
   "url": "/docs/api/gfx/#struct-pipelinelayoutrecord",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "BindGroupRecord",
   "qualified": "cinder.gfx.resources.BindGroupRecord",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct BindGroupRecord(Copyable, Movable)",
   "summary": "Pool entry for a bind group: the WGPUBindGroup the pool owns.",
   "url": "/docs/api/gfx/#struct-bindgrouprecord",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "RenderPipelineRecord",
   "qualified": "cinder.gfx.resources.RenderPipelineRecord",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct RenderPipelineRecord(Copyable, Movable)",
   "summary": "Pool entry for a render pipeline: the WGPURenderPipeline the pool owns.",
   "url": "/docs/api/gfx/#struct-renderpipelinerecord",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ComputePipelineRecord",
   "qualified": "cinder.gfx.resources.ComputePipelineRecord",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct ComputePipelineRecord(Copyable, Movable)",
   "summary": "Pool entry for a compute pipeline: the WGPUComputePipeline the pool owns.",
   "url": "/docs/api/gfx/#struct-computepipelinerecord",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "LiveCounts",
   "qualified": "cinder.gfx.resources.LiveCounts",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct LiveCounts(ImplicitlyCopyable, Movable, Writable)",
   "summary": "Resources alive per kind.",
   "url": "/docs/api/gfx/#struct-livecounts",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "total",
   "qualified": "cinder.gfx.resources.LiveCounts.total",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "LiveCounts",
   "signature": "total(self) -> Int",
   "summary": "Sum over every kind; zero means nothing is left to release.",
   "url": "/docs/api/gfx/#livecounts-total",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.gfx.resources.LiveCounts.write_to",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "LiveCounts",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/gfx/#livecounts-write_to",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "Resources",
   "qualified": "cinder.gfx.resources.Resources",
   "kind": "struct",
   "module": "cinder.gfx.resources",
   "signature": "struct Resources(Movable)",
   "summary": "Pools of every GPU resource kind, owning the wgpu objects behind typed handles.",
   "url": "/docs/api/gfx/#struct-resources",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.resources.Resources.__init__",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "__init__( out self, gfx: Pointer[Gfx, MutUntrackedOrigin], capacity: Int = 4096 ) raises",
   "summary": "",
   "url": "/docs/api/gfx/#resources-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "live_counts",
   "qualified": "cinder.gfx.resources.Resources.live_counts",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "live_counts(self) -> LiveCounts",
   "summary": "Live handles per pool right now. Imported texture views count until they are forgotten. A non-zero total() just before teardown is what __deinit__ reports as left alive.",
   "url": "/docs/api/gfx/#resources-live_counts",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "create_buffer",
   "qualified": "cinder.gfx.resources.Resources.create_buffer",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "create_buffer(mut self, desc: BufferDesc) raises -> BufferHandle",
   "summary": "Creates a GPU buffer. Validation failures surface through Gfx.pump diagnostics; a NULL object (out of memory) raises, as does a full buffer pool (the new buffer is then released).",
   "url": "/docs/api/gfx/#resources-create_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "buffer",
   "qualified": "cinder.gfx.resources.Resources.buffer",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "buffer(self, h: BufferHandle) raises -> BufferRecord",
   "summary": "A copy of the buffer's record; raises on a null, stale or foreign handle.",
   "url": "/docs/api/gfx/#resources-buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "destroy_buffer",
   "qualified": "cinder.gfx.resources.Resources.destroy_buffer",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "destroy_buffer(mut self, h: BufferHandle) raises",
   "summary": "Removes the handle, then destroys and releases the WGPUBuffer. Raises on an invalid handle, in which case nothing is released.",
   "url": "/docs/api/gfx/#resources-destroy_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "write_buffer",
   "qualified": "cinder.gfx.resources.Resources.write_buffer",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "write_buffer( self, h: BufferHandle, offset: UInt64, data: Span[UInt8, _] ) raises",
   "summary": "Uploads data through the queue (copied immediately; no mapping).",
   "url": "/docs/api/gfx/#resources-write_buffer",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "write_texture",
   "qualified": "cinder.gfx.resources.Resources.write_texture",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "write_texture( self, h: TextureHandle, mip_level: UInt32, width: UInt32, height: UInt32, layer: UInt32, data: Span[UInt8, _], bytes_per_row: UInt32, rows_per_image: UInt32 = 0, ) raises",
   "summary": "Uploads one mip level of one array layer through the queue (copied immediately). rows_per_image is the number of rows in data; it defaults to height and must be the block-row count for block-compressed formats.",
   "url": "/docs/api/gfx/#resources-write_texture",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "create_texture",
   "qualified": "cinder.gfx.resources.Resources.create_texture",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "create_texture(mut self, desc: TextureDesc) raises -> TextureHandle",
   "summary": "Creates a 2D WGPUTexture (depth_or_layers array layers) and returns its handle. Validation failures surface through Gfx.pump diagnostics; a NULL object raises, as does a full texture pool (the new texture is then released).",
   "url": "/docs/api/gfx/#resources-create_texture",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "texture",
   "qualified": "cinder.gfx.resources.Resources.texture",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "texture(self, h: TextureHandle) raises -> TextureRecord",
   "summary": "A copy of the texture's record; raises on a null, stale or foreign handle.",
   "url": "/docs/api/gfx/#resources-texture",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "texture_view_count",
   "qualified": "cinder.gfx.resources.Resources.texture_view_count",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "texture_view_count(self, h: TextureHandle) raises -> Int",
   "summary": "How many live views created through Resources view this texture; raises on an invalid handle.",
   "url": "/docs/api/gfx/#resources-texture_view_count",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "destroy_texture",
   "qualified": "cinder.gfx.resources.Resources.destroy_texture",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "destroy_texture(mut self, h: TextureHandle) raises",
   "summary": "Removes the handle, then destroys and releases the WGPUTexture. Raises, releasing nothing, on an invalid handle or while views created from the texture are still alive: destroy those views first (destroy_texture_view), so no live view handle is left pointing at a destroyed texture.",
   "url": "/docs/api/gfx/#resources-destroy_texture",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "create_texture_view_ex",
   "qualified": "cinder.gfx.resources.Resources.create_texture_view_ex",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "create_texture_view_ex( mut self, texture: TextureHandle, dimension: WGPUTextureViewDimension, base_mip: UInt32, mip_count: UInt32, base_layer: UInt32, layer_count: UInt32, ) raises -> TextureViewHandle",
   "summary": "A view of a mip range and layer range with an explicit dimension (2D array, cube, one layer of an array as 2D, one mip as a storage target).",
   "url": "/docs/api/gfx/#resources-create_texture_view_ex",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "create_texture_view",
   "qualified": "cinder.gfx.resources.Resources.create_texture_view",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "create_texture_view( mut self, texture: TextureHandle ) raises -> TextureViewHandle",
   "summary": "A view of the whole texture with its own format and dimension.",
   "url": "/docs/api/gfx/#resources-create_texture_view",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "import_texture_view",
   "qualified": "cinder.gfx.resources.Resources.import_texture_view",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "import_texture_view( mut self, raw: WGPUTextureView ) raises -> TextureViewHandle",
   "summary": "Wraps a view the caller owns (a swapchain frame) so renderers can target it. Drop it with forget_texture_view; the raw view is never released here, not even at teardown, and destroy_texture_view refuses it.",
   "url": "/docs/api/gfx/#resources-import_texture_view",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "forget_texture_view",
   "qualified": "cinder.gfx.resources.Resources.forget_texture_view",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "forget_texture_view(mut self, h: TextureViewHandle) raises",
   "summary": "Drops an imported view without releasing the wgpu object. Raises, dropping nothing, on an invalid handle or on a view created by Resources (that one must be released with destroy_texture_view, or it would leak).",
   "url": "/docs/api/gfx/#resources-forget_texture_view",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "texture_view",
   "qualified": "cinder.gfx.resources.Resources.texture_view",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "texture_view(self, h: TextureViewHandle) raises -> TextureViewRecord",
   "summary": "A copy of the view's record; raises on a null, stale or foreign handle.",
   "url": "/docs/api/gfx/#resources-texture_view",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "destroy_texture_view",
   "qualified": "cinder.gfx.resources.Resources.destroy_texture_view",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "destroy_texture_view(mut self, h: TextureViewHandle) raises",
   "summary": "Removes the handle and releases the WGPUTextureView. Raises, releasing nothing, on an invalid handle or on an imported view (the caller owns that one; drop it with forget_texture_view).",
   "url": "/docs/api/gfx/#resources-destroy_texture_view",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "create_sampler",
   "qualified": "cinder.gfx.resources.Resources.create_sampler",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "create_sampler(mut self, desc: SamplerDesc) raises -> SamplerHandle",
   "summary": "Creates a sampler with the same address mode on u, v and w and LOD clamp 0..32. linear picks linear min/mag/mip filtering, otherwise nearest. A NULL object raises; invalid settings surface as validation diagnostics through Gfx.pump.",
   "url": "/docs/api/gfx/#resources-create_sampler",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "create_comparison_sampler",
   "qualified": "cinder.gfx.resources.Resources.create_comparison_sampler",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "create_comparison_sampler( mut self, label: String ) raises -> SamplerHandle",
   "summary": "Linear PCF sampler: clamp to edge, compare GreaterEqual (reverse-Z shadow maps).",
   "url": "/docs/api/gfx/#resources-create_comparison_sampler",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "sampler",
   "qualified": "cinder.gfx.resources.Resources.sampler",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "sampler(self, h: SamplerHandle) raises -> SamplerRecord",
   "summary": "A copy of the sampler's record; raises on a null, stale or foreign handle.",
   "url": "/docs/api/gfx/#resources-sampler",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "destroy_sampler",
   "qualified": "cinder.gfx.resources.Resources.destroy_sampler",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "destroy_sampler(mut self, h: SamplerHandle) raises",
   "summary": "Removes the handle and releases the WGPUSampler; raises on an invalid handle.",
   "url": "/docs/api/gfx/#resources-destroy_sampler",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "adopt_shader",
   "qualified": "cinder.gfx.resources.Resources.adopt_shader",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "adopt_shader( mut self, raw: WGPUShaderModule, source_path: String ) raises -> ShaderHandle",
   "summary": "Takes ownership of a compiled module (from ShaderManager) and returns its handle. Raises on a null module. Ownership passes even when this raises: if the pool is full the module is released before the error propagates.",
   "url": "/docs/api/gfx/#resources-adopt_shader",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "shader",
   "qualified": "cinder.gfx.resources.Resources.shader",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "shader(self, h: ShaderHandle) raises -> ShaderRecord",
   "summary": "A copy of the shader's record; raises on a null, stale or foreign handle.",
   "url": "/docs/api/gfx/#resources-shader",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "destroy_shader",
   "qualified": "cinder.gfx.resources.Resources.destroy_shader",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "destroy_shader(mut self, h: ShaderHandle) raises",
   "summary": "Removes the handle and releases the WGPUShaderModule. A ShaderManager that loaded it keeps watching the file; a later change then fails to reload and logs an error.",
   "url": "/docs/api/gfx/#resources-destroy_shader",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "adopt_bind_group_layout",
   "qualified": "cinder.gfx.resources.Resources.adopt_bind_group_layout",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "adopt_bind_group_layout( mut self, raw: WGPUBindGroupLayout ) raises -> BindGroupLayoutHandle",
   "summary": "Takes ownership of a WGPUBindGroupLayout built in pipeline.mojo. Raises on a null raw; a full pool releases raw and raises.",
   "url": "/docs/api/gfx/#resources-adopt_bind_group_layout",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "bind_group_layout",
   "qualified": "cinder.gfx.resources.Resources.bind_group_layout",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "bind_group_layout( self, h: BindGroupLayoutHandle ) raises -> BindGroupLayoutRecord",
   "summary": "A copy of the layout's record; raises on a null, stale or foreign handle.",
   "url": "/docs/api/gfx/#resources-bind_group_layout",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "destroy_bind_group_layout",
   "qualified": "cinder.gfx.resources.Resources.destroy_bind_group_layout",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "destroy_bind_group_layout(mut self, h: BindGroupLayoutHandle) raises",
   "summary": "Removes the handle and releases the WGPUBindGroupLayout; raises on an invalid handle.",
   "url": "/docs/api/gfx/#resources-destroy_bind_group_layout",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "adopt_pipeline_layout",
   "qualified": "cinder.gfx.resources.Resources.adopt_pipeline_layout",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "adopt_pipeline_layout( mut self, raw: WGPUPipelineLayout ) raises -> PipelineLayoutHandle",
   "summary": "Takes ownership of a WGPUPipelineLayout built in pipeline.mojo. Raises on a null raw; a full pool releases raw and raises.",
   "url": "/docs/api/gfx/#resources-adopt_pipeline_layout",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "pipeline_layout",
   "qualified": "cinder.gfx.resources.Resources.pipeline_layout",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "pipeline_layout( self, h: PipelineLayoutHandle ) raises -> PipelineLayoutRecord",
   "summary": "A copy of the layout's record; raises on a null, stale or foreign handle.",
   "url": "/docs/api/gfx/#resources-pipeline_layout",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "destroy_pipeline_layout",
   "qualified": "cinder.gfx.resources.Resources.destroy_pipeline_layout",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "destroy_pipeline_layout(mut self, h: PipelineLayoutHandle) raises",
   "summary": "Removes the handle and releases the WGPUPipelineLayout; raises on an invalid handle.",
   "url": "/docs/api/gfx/#resources-destroy_pipeline_layout",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "adopt_bind_group",
   "qualified": "cinder.gfx.resources.Resources.adopt_bind_group",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "adopt_bind_group( mut self, raw: WGPUBindGroup ) raises -> BindGroupHandle",
   "summary": "Takes ownership of a WGPUBindGroup built in pipeline.mojo. Raises on a null raw; a full pool releases raw and raises.",
   "url": "/docs/api/gfx/#resources-adopt_bind_group",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "bind_group",
   "qualified": "cinder.gfx.resources.Resources.bind_group",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "bind_group(self, h: BindGroupHandle) raises -> BindGroupRecord",
   "summary": "A copy of the bind group's record; raises on a null, stale or foreign handle.",
   "url": "/docs/api/gfx/#resources-bind_group",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "destroy_bind_group",
   "qualified": "cinder.gfx.resources.Resources.destroy_bind_group",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "destroy_bind_group(mut self, h: BindGroupHandle) raises",
   "summary": "Removes the handle and releases the WGPUBindGroup; raises on an invalid handle.",
   "url": "/docs/api/gfx/#resources-destroy_bind_group",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "adopt_render_pipeline",
   "qualified": "cinder.gfx.resources.Resources.adopt_render_pipeline",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "adopt_render_pipeline( mut self, raw: WGPURenderPipeline ) raises -> RenderPipelineHandle",
   "summary": "Takes ownership of a WGPURenderPipeline built in pipeline.mojo. Raises on a null raw; a full pool releases raw and raises.",
   "url": "/docs/api/gfx/#resources-adopt_render_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "render_pipeline",
   "qualified": "cinder.gfx.resources.Resources.render_pipeline",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "render_pipeline( self, h: RenderPipelineHandle ) raises -> RenderPipelineRecord",
   "summary": "A copy of the pipeline's record; raises on a null, stale or foreign handle.",
   "url": "/docs/api/gfx/#resources-render_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "replace_render_pipeline",
   "qualified": "cinder.gfx.resources.Resources.replace_render_pipeline",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "replace_render_pipeline( mut self, h: RenderPipelineHandle, raw: WGPURenderPipeline ) raises",
   "summary": "Swaps the object behind an existing handle (hot reload), releasing the old one. Takes ownership of raw in every case: on a null raw or an invalid handle it raises, and a non-null raw is released first, so a failed hot reload never leaks.",
   "url": "/docs/api/gfx/#resources-replace_render_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "destroy_render_pipeline",
   "qualified": "cinder.gfx.resources.Resources.destroy_render_pipeline",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "destroy_render_pipeline(mut self, h: RenderPipelineHandle) raises",
   "summary": "Removes the handle and releases the WGPURenderPipeline; raises on an invalid handle.",
   "url": "/docs/api/gfx/#resources-destroy_render_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "adopt_compute_pipeline",
   "qualified": "cinder.gfx.resources.Resources.adopt_compute_pipeline",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "adopt_compute_pipeline( mut self, raw: WGPUComputePipeline ) raises -> ComputePipelineHandle",
   "summary": "Takes ownership of a WGPUComputePipeline built in pipeline.mojo. Raises on a null raw; a full pool releases raw and raises.",
   "url": "/docs/api/gfx/#resources-adopt_compute_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "compute_pipeline",
   "qualified": "cinder.gfx.resources.Resources.compute_pipeline",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "compute_pipeline( self, h: ComputePipelineHandle ) raises -> ComputePipelineRecord",
   "summary": "A copy of the pipeline's record; raises on a null, stale or foreign handle.",
   "url": "/docs/api/gfx/#resources-compute_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "replace_compute_pipeline",
   "qualified": "cinder.gfx.resources.Resources.replace_compute_pipeline",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "replace_compute_pipeline( mut self, h: ComputePipelineHandle, raw: WGPUComputePipeline ) raises",
   "summary": "Swaps the object behind an existing handle (hot reload), releasing the old one. Takes ownership of raw in every case: on a null raw or an invalid handle it raises, and a non-null raw is released first, so a failed hot reload never leaks.",
   "url": "/docs/api/gfx/#resources-replace_compute_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "destroy_compute_pipeline",
   "qualified": "cinder.gfx.resources.Resources.destroy_compute_pipeline",
   "kind": "method",
   "module": "cinder.gfx.resources",
   "parent": "Resources",
   "signature": "destroy_compute_pipeline(mut self, h: ComputePipelineHandle) raises",
   "summary": "Removes the handle and releases the WGPUComputePipeline; raises on an invalid handle.",
   "url": "/docs/api/gfx/#resources-destroy_compute_pipeline",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "shaders",
   "qualified": "cinder.gfx.shaders",
   "kind": "module",
   "module": "cinder.gfx.shaders",
   "signature": "",
   "summary": "ShaderManager: WGSL modules from files, compile diagnostics with file:line:column, hot reload. Every loaded shader remembers its path and modification time. check_for_changes recompiles files that changed on disk; a successful recompile swaps the module behind the same ShaderHandle and reports the handle so pipeline owners rebuild, a failed one keeps the last good module and reports the error.…",
   "url": "/docs/api/gfx/#cindergfxshaders",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ShaderMessage",
   "qualified": "cinder.gfx.shaders.ShaderMessage",
   "kind": "struct",
   "module": "cinder.gfx.shaders",
   "signature": "struct ShaderMessage(Copyable, Movable, Writable)",
   "summary": "One compiler diagnostic, already formatted with its source location.",
   "url": "/docs/api/gfx/#struct-shadermessage",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.gfx.shaders.ShaderMessage.write_to",
   "kind": "method",
   "module": "cinder.gfx.shaders",
   "parent": "ShaderMessage",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/gfx/#shadermessage-write_to",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ShaderError",
   "qualified": "cinder.gfx.shaders.ShaderError",
   "kind": "struct",
   "module": "cinder.gfx.shaders",
   "signature": "struct ShaderError(Copyable, Movable, Writable)",
   "summary": "Raised when a WGSL file fails to compile. messages holds every diagnostic.",
   "url": "/docs/api/gfx/#struct-shadererror",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.gfx.shaders.ShaderError.write_to",
   "kind": "method",
   "module": "cinder.gfx.shaders",
   "parent": "ShaderError",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/gfx/#shadererror-write_to",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ShaderSource",
   "qualified": "cinder.gfx.shaders.ShaderSource",
   "kind": "struct",
   "module": "cinder.gfx.shaders",
   "signature": "struct ShaderSource(Copyable, Movable)",
   "summary": "A loaded shader file and its on-disk state.",
   "url": "/docs/api/gfx/#struct-shadersource",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ReloadResult",
   "qualified": "cinder.gfx.shaders.ReloadResult",
   "kind": "struct",
   "module": "cinder.gfx.shaders",
   "signature": "struct ReloadResult(Copyable, Movable)",
   "summary": "Outcome of check_for_changes for one changed file.",
   "url": "/docs/api/gfx/#struct-reloadresult",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "parse_wgsl_report",
   "qualified": "cinder.gfx.shaders.parse_wgsl_report",
   "kind": "def",
   "module": "cinder.gfx.shaders",
   "signature": "def parse_wgsl_report(path: String, report: String) -> List[ShaderMessage]",
   "summary": "Turns a naga validation report into messages with locations. naga marks each location as wgsl:LINE:COLUMN; every such mark becomes one error message carrying the whole report text. A report with no mark yields one message at line 0.",
   "url": "/docs/api/gfx/#def-parse_wgsl_report",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ShaderManager",
   "qualified": "cinder.gfx.shaders.ShaderManager",
   "kind": "struct",
   "module": "cinder.gfx.shaders",
   "signature": "struct ShaderManager(Movable)",
   "summary": "Owns the list of shader files; the modules themselves live in Resources.",
   "url": "/docs/api/gfx/#struct-shadermanager",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.shaders.ShaderManager.__init__",
   "kind": "method",
   "module": "cinder.gfx.shaders",
   "parent": "ShaderManager",
   "signature": "__init__( out self, gfx: Pointer[Gfx, MutUntrackedOrigin], resources: Pointer[Resources, MutUntrackedOrigin], )",
   "summary": "",
   "url": "/docs/api/gfx/#shadermanager-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "compile_source",
   "qualified": "cinder.gfx.shaders.ShaderManager.compile_source",
   "kind": "method",
   "module": "cinder.gfx.shaders",
   "parent": "ShaderManager",
   "signature": "compile_source( mut self, path: String, source: String ) raises -> WGPUShaderModule",
   "summary": "Compiles WGSL text and returns the module, or raises ShaderError with every diagnostic. wgpu-native 29 does not implement the compilation-info callback, so the module is created inside a validation error scope; naga's report (which names wgsl:line:column locations) is popped through the shim queue and parsed into ShaderMessages.",
   "url": "/docs/api/gfx/#shadermanager-compile_source",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "load",
   "qualified": "cinder.gfx.shaders.ShaderManager.load",
   "kind": "method",
   "module": "cinder.gfx.shaders",
   "parent": "ShaderManager",
   "signature": "load(mut self, path: String) raises -> ShaderHandle",
   "summary": "Loads and compiles a WGSL file, registering it for hot reload.",
   "url": "/docs/api/gfx/#shadermanager-load",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "check_for_changes",
   "qualified": "cinder.gfx.shaders.ShaderManager.check_for_changes",
   "kind": "method",
   "module": "cinder.gfx.shaders",
   "parent": "ShaderManager",
   "signature": "check_for_changes(mut self) -> List[ReloadResult]",
   "summary": "Recompiles every registered file whose modification time changed. On success the module behind the handle is replaced (old one released); on failure the last good module stays and an error diagnostic with file:line:column is recorded.",
   "url": "/docs/api/gfx/#shadermanager-check_for_changes",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "take_diagnostics",
   "qualified": "cinder.gfx.shaders.ShaderManager.take_diagnostics",
   "kind": "method",
   "module": "cinder.gfx.shaders",
   "parent": "ShaderManager",
   "signature": "take_diagnostics(mut self) -> List[LogRecord]",
   "summary": "Returns and clears the reload LogRecords from check_for_changes (info on a successful reload, error with the reason when the last good module was kept).",
   "url": "/docs/api/gfx/#shadermanager-take_diagnostics",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "swapchain",
   "qualified": "cinder.gfx.swapchain",
   "kind": "module",
   "module": "cinder.gfx.swapchain",
   "signature": "",
   "summary": "Swapchain: surface configuration, per-frame texture acquisition and presentation. Handles the three real-world cases a frame loop meets: resize (reconfigure on the next acquire), minimise (zero-sized window; frames are skipped until it is restored) and surface loss/outdated (reconfigure and retry once, then report). Device loss is Gfx.lost and is the caller's decision.",
   "url": "/docs/api/gfx/#cindergfxswapchain",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "SurfaceFrame",
   "qualified": "cinder.gfx.swapchain.SurfaceFrame",
   "kind": "struct",
   "module": "cinder.gfx.swapchain",
   "signature": "struct SurfaceFrame(Movable)",
   "summary": "The acquired swapchain texture for one frame. present consumes it.",
   "url": "/docs/api/gfx/#struct-surfaceframe",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "Swapchain",
   "qualified": "cinder.gfx.swapchain.Swapchain",
   "kind": "struct",
   "module": "cinder.gfx.swapchain",
   "signature": "struct Swapchain(Movable)",
   "summary": "Owns the configuration of a wgpu surface created by Window.create_surface.",
   "url": "/docs/api/gfx/#struct-swapchain",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.gfx.swapchain.Swapchain.__init__",
   "kind": "method",
   "module": "cinder.gfx.swapchain",
   "parent": "Swapchain",
   "signature": "__init__( out self, gfx: Pointer[Gfx, MutUntrackedOrigin], surface: WGPUSurface, width: Int, height: Int, prefer_srgb: Bool = True, readback: Bool = False, ) raises GfxError",
   "summary": "Picks a surface format (8-bit BGRA/RGBA, sRGB when prefer_srgb) and configures.",
   "url": "/docs/api/gfx/#swapchain-__init__",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "resize",
   "qualified": "cinder.gfx.swapchain.Swapchain.resize",
   "kind": "method",
   "module": "cinder.gfx.swapchain",
   "parent": "Swapchain",
   "signature": "resize(mut self, width: Int, height: Int)",
   "summary": "Records a new size; the surface is reconfigured on the next acquire.",
   "url": "/docs/api/gfx/#swapchain-resize",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "acquire",
   "qualified": "cinder.gfx.swapchain.Swapchain.acquire",
   "kind": "method",
   "module": "cinder.gfx.swapchain",
   "parent": "Swapchain",
   "signature": "acquire(mut self) raises GfxError -> Optional[SurfaceFrame]",
   "summary": "Returns the frame's texture, or None when the window is minimised. Outdated and lost surfaces are reconfigured and retried once; a second failure raises.",
   "url": "/docs/api/gfx/#swapchain-acquire",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "present",
   "qualified": "cinder.gfx.swapchain.Swapchain.present",
   "kind": "method",
   "module": "cinder.gfx.swapchain",
   "parent": "Swapchain",
   "signature": "present(self, var frame: SurfaceFrame)",
   "summary": "Presents the acquired frame and releases its view and texture.",
   "url": "/docs/api/gfx/#swapchain-present",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "discard",
   "qualified": "cinder.gfx.swapchain.Swapchain.discard",
   "kind": "method",
   "module": "cinder.gfx.swapchain",
   "parent": "Swapchain",
   "signature": "discard(self, var frame: SurfaceFrame)",
   "summary": "Releases an acquired frame without presenting (used when a frame is abandoned).",
   "url": "/docs/api/gfx/#swapchain-discard",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "util",
   "qualified": "cinder.gfx.util",
   "kind": "module",
   "module": "cinder.gfx.util",
   "signature": "",
   "summary": "Small conversions shared by the gfx modules.",
   "url": "/docs/api/gfx/#cindergfxutil",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "string_view",
   "qualified": "cinder.gfx.util.string_view",
   "kind": "def",
   "module": "cinder.gfx.util",
   "signature": "def string_view(ref text: String) -> WGPUStringView",
   "summary": "A non-owning WGPUStringView over text. text must outlive every use of the view.",
   "url": "/docs/api/gfx/#def-string_view",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "empty_string_view",
   "qualified": "cinder.gfx.util.empty_string_view",
   "kind": "def",
   "module": "cinder.gfx.util",
   "signature": "def empty_string_view() -> WGPUStringView",
   "summary": "A WGPUStringView with a null pointer and zero length, for absent labels and strings.",
   "url": "/docs/api/gfx/#def-empty_string_view",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "c_message",
   "qualified": "cinder.gfx.util.c_message",
   "kind": "def",
   "module": "cinder.gfx.util",
   "signature": "def c_message(ev: CnEvent) -> String",
   "summary": "The NUL-terminated message of a shim event as a String, decoded as UTF-8 (invalid sequences become U+FFFD). Reads at most the 1000-byte message buffer.",
   "url": "/docs/api/gfx/#def-c_message",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "zero_event",
   "qualified": "cinder.gfx.util.zero_event",
   "kind": "def",
   "module": "cinder.gfx.util",
   "signature": "def zero_event() -> CnEvent",
   "summary": "An all-zero CnEvent, used as the out-parameter that cn_event_queue_pop fills.",
   "url": "/docs/api/gfx/#def-zero_event",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "ptr_to",
   "qualified": "cinder.gfx.util.ptr_to",
   "kind": "def",
   "module": "cinder.gfx.util",
   "signature": "def ptr_to[ T: AnyType ](ref value: T) -> Optional[Pointer[T, MutUntrackedOrigin]]",
   "summary": "Raw pointer for a C call. The pointee must stay alive past the call (keep it).",
   "url": "/docs/api/gfx/#def-ptr_to",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "opaque_to",
   "qualified": "cinder.gfx.util.opaque_to",
   "kind": "def",
   "module": "cinder.gfx.util",
   "signature": "def opaque_to[ T: AnyType ](ref value: T) -> Optional[OpaquePointer[MutUntrackedOrigin]]",
   "summary": "ptr_to for void* parameters.",
   "url": "/docs/api/gfx/#def-opaque_to",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "handle_from",
   "qualified": "cinder.gfx.util.handle_from",
   "kind": "def",
   "module": "cinder.gfx.util",
   "signature": "def handle_from[ T: AnyType ](address: UInt64) -> Optional[Pointer[T, MutUntrackedOrigin]]",
   "summary": "Rebuilds a wgpu object handle delivered through a CnEvent.",
   "url": "/docs/api/gfx/#def-handle_from",
   "md": "/docs/api/gfx.md"
  },
  {
   "name": "input",
   "qualified": "cinder.input",
   "kind": "module",
   "module": "cinder.input",
   "signature": "",
   "summary": "Input: action and axis mapping over keyboard, mouse and gamepad, rebindable and saved to disk.",
   "url": "/docs/api/input/#cinderinput-1",
   "md": "/docs/api/input.md"
  },
  {
   "name": "map",
   "qualified": "cinder.input.map",
   "kind": "module",
   "module": "cinder.input.map",
   "signature": "",
   "summary": "Input mapping: named actions (buttons) and axes over keyboard, mouse and gamepad, rebindable at runtime and saved as a diffable text file. Feed every platform Event to process, call end_frame once per frame (it clears the just-pressed and just-released edges and the per-frame mouse deltas), and query by name. An axis sums its bindings: a key contributes scale while held, an analog source its…",
   "url": "/docs/api/input/#cinderinputmap",
   "md": "/docs/api/input.md"
  },
  {
   "name": "Binding",
   "qualified": "cinder.input.map.Binding",
   "kind": "struct",
   "module": "cinder.input.map",
   "signature": "struct Binding(Equatable, ImplicitlyCopyable, Movable, Writable)",
   "summary": "One source: device and its code (scancode, button or axis index). scale multiplies the contribution to an axis (digital sources contribute scale while held), dead_zone applies to analog sources.",
   "url": "/docs/api/input/#struct-binding",
   "md": "/docs/api/input.md"
  },
  {
   "name": "key",
   "qualified": "cinder.input.map.Binding.key",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "Binding",
   "signature": "key(scancode: Int, scale: Float32 = 1.0) -> Binding",
   "summary": "A keyboard binding for SDL scancode scancode.",
   "url": "/docs/api/input/#binding-key",
   "md": "/docs/api/input.md"
  },
  {
   "name": "mouse_button",
   "qualified": "cinder.input.map.Binding.mouse_button",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "Binding",
   "signature": "mouse_button(button: Int, scale: Float32 = 1.0) -> Binding",
   "summary": "A mouse button binding (1 = left, 2 = middle, 3 = right).",
   "url": "/docs/api/input/#binding-mouse_button",
   "md": "/docs/api/input.md"
  },
  {
   "name": "mouse_axis",
   "qualified": "cinder.input.map.Binding.mouse_axis",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "Binding",
   "signature": "mouse_axis(axis: Int, scale: Float32 = 1.0) -> Binding",
   "summary": "A mouse axis binding: 0 = x delta, 1 = y delta, any other code = wheel.",
   "url": "/docs/api/input/#binding-mouse_axis",
   "md": "/docs/api/input.md"
  },
  {
   "name": "gamepad_button",
   "qualified": "cinder.input.map.Binding.gamepad_button",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "Binding",
   "signature": "gamepad_button(button: Int, scale: Float32 = 1.0) -> Binding",
   "summary": "A gamepad button binding (SDL_GamepadButton index).",
   "url": "/docs/api/input/#binding-gamepad_button",
   "md": "/docs/api/input.md"
  },
  {
   "name": "gamepad_axis",
   "qualified": "cinder.input.map.Binding.gamepad_axis",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "Binding",
   "signature": "gamepad_axis( axis: Int, scale: Float32 = 1.0, dead_zone: Float32 = 0.15 ) -> Binding",
   "summary": "An analog gamepad axis binding (SDL_GamepadAxis index) with a dead zone.",
   "url": "/docs/api/input/#binding-gamepad_axis",
   "md": "/docs/api/input.md"
  },
  {
   "name": "same_source",
   "qualified": "cinder.input.map.Binding.same_source",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "Binding",
   "signature": "same_source(self, o: Binding) -> Bool",
   "summary": "True when both bindings read the same device and code, whatever their scale and dead zone.",
   "url": "/docs/api/input/#binding-same_source",
   "md": "/docs/api/input.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.input.map.Binding.write_to",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "Binding",
   "signature": "write_to(self, mut w: Some[Writer])",
   "summary": "",
   "url": "/docs/api/input/#binding-write_to",
   "md": "/docs/api/input.md"
  },
  {
   "name": "InputMap",
   "qualified": "cinder.input.map.InputMap",
   "kind": "struct",
   "module": "cinder.input.map",
   "signature": "struct InputMap(Movable)",
   "summary": "Named actions and axes with their bindings, plus the device state they are evaluated against. Text format (to_text, from_text): a cinder-input 1 header, then one action NAME DEVICE CODE SCALE DEAD_ZONE or axis NAME ... line per binding, where DEVICE is key, mouse_button, mouse_axis, gamepad_button or gamepad_axis; an entry without bindings is a bare action NAME or axis NAME line. Fields are…",
   "url": "/docs/api/input/#struct-inputmap",
   "md": "/docs/api/input.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.input.map.InputMap.__init__",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/input/#inputmap-__init__",
   "md": "/docs/api/input.md"
  },
  {
   "name": "add_action",
   "qualified": "cinder.input.map.InputMap.add_action",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "add_action(mut self, name: String) raises -> Int",
   "summary": "Adds an action without bindings and returns its index; raises when the name is taken.",
   "url": "/docs/api/input/#inputmap-add_action",
   "md": "/docs/api/input.md"
  },
  {
   "name": "add_axis",
   "qualified": "cinder.input.map.InputMap.add_axis",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "add_axis(mut self, name: String) raises -> Int",
   "summary": "Adds an axis without bindings and returns its index; raises when the name is taken.",
   "url": "/docs/api/input/#inputmap-add_axis",
   "md": "/docs/api/input.md"
  },
  {
   "name": "find_action",
   "qualified": "cinder.input.map.InputMap.find_action",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "find_action(self, name: String) -> Int",
   "summary": "Index of the action called name, or -1.",
   "url": "/docs/api/input/#inputmap-find_action",
   "md": "/docs/api/input.md"
  },
  {
   "name": "find_axis",
   "qualified": "cinder.input.map.InputMap.find_axis",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "find_axis(self, name: String) -> Int",
   "summary": "Index of the axis called name, or -1.",
   "url": "/docs/api/input/#inputmap-find_axis",
   "md": "/docs/api/input.md"
  },
  {
   "name": "bind_action",
   "qualified": "cinder.input.map.InputMap.bind_action",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "bind_action(mut self, name: String, binding: Binding) raises",
   "summary": "Appends binding to the action, creating the action when it does not exist. When the new source is already down the action becomes held (with a just-pressed edge).",
   "url": "/docs/api/input/#inputmap-bind_action",
   "md": "/docs/api/input.md"
  },
  {
   "name": "bind_axis",
   "qualified": "cinder.input.map.InputMap.bind_axis",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "bind_axis(mut self, name: String, binding: Binding) raises",
   "summary": "Appends binding to the axis, creating the axis when it does not exist.",
   "url": "/docs/api/input/#inputmap-bind_axis",
   "md": "/docs/api/input.md"
  },
  {
   "name": "clear_action_bindings",
   "qualified": "cinder.input.map.InputMap.clear_action_bindings",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "clear_action_bindings(mut self, name: String) raises",
   "summary": "Removes every binding of the action; raises for an unknown action. An action held at that moment is released (pressed turns False and just_released fires), so it cannot stay stuck with no binding to release it.",
   "url": "/docs/api/input/#inputmap-clear_action_bindings",
   "md": "/docs/api/input.md"
  },
  {
   "name": "clear_axis_bindings",
   "qualified": "cinder.input.map.InputMap.clear_axis_bindings",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "clear_axis_bindings(mut self, name: String) raises",
   "summary": "Removes every binding of the axis; raises for an unknown axis.",
   "url": "/docs/api/input/#inputmap-clear_axis_bindings",
   "md": "/docs/api/input.md"
  },
  {
   "name": "rebind_action",
   "qualified": "cinder.input.map.InputMap.rebind_action",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "rebind_action(mut self, name: String, binding: Binding) raises",
   "summary": "Replaces every binding of the action with binding.",
   "url": "/docs/api/input/#inputmap-rebind_action",
   "md": "/docs/api/input.md"
  },
  {
   "name": "action_bindings",
   "qualified": "cinder.input.map.InputMap.action_bindings",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "action_bindings(self, name: String) raises -> List[Binding]",
   "summary": "A copy of the action's bindings; raises for an unknown action.",
   "url": "/docs/api/input/#inputmap-action_bindings",
   "md": "/docs/api/input.md"
  },
  {
   "name": "axis_bindings",
   "qualified": "cinder.input.map.InputMap.axis_bindings",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "axis_bindings(self, name: String) raises -> List[Binding]",
   "summary": "A copy of the axis' bindings; raises for an unknown axis.",
   "url": "/docs/api/input/#inputmap-axis_bindings",
   "md": "/docs/api/input.md"
  },
  {
   "name": "listen_action",
   "qualified": "cinder.input.map.InputMap.listen_action",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "listen_action(mut self, name: String) raises",
   "summary": "The next key, mouse button or gamepad button event replaces the action's bindings. An action held through its old bindings is released at that point (see clear_action_bindings).",
   "url": "/docs/api/input/#inputmap-listen_action",
   "md": "/docs/api/input.md"
  },
  {
   "name": "listen_axis",
   "qualified": "cinder.input.map.InputMap.listen_axis",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "listen_axis(mut self, name: String, scale: Float32 = 1.0) raises",
   "summary": "The next key, button or analog event is added to the axis with scale.",
   "url": "/docs/api/input/#inputmap-listen_axis",
   "md": "/docs/api/input.md"
  },
  {
   "name": "is_listening",
   "qualified": "cinder.input.map.InputMap.is_listening",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "is_listening(self) -> Bool",
   "summary": "True while listen_action or listen_axis waits for an event.",
   "url": "/docs/api/input/#inputmap-is_listening",
   "md": "/docs/api/input.md"
  },
  {
   "name": "cancel_listening",
   "qualified": "cinder.input.map.InputMap.cancel_listening",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "cancel_listening(mut self)",
   "summary": "Disarms a pending listen_action or listen_axis without changing any binding.",
   "url": "/docs/api/input/#inputmap-cancel_listening",
   "md": "/docs/api/input.md"
  },
  {
   "name": "process",
   "qualified": "cinder.input.map.InputMap.process",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "process(mut self, ev: Event)",
   "summary": "Updates device state from one platform event (and captures it while listening).",
   "url": "/docs/api/input/#inputmap-process",
   "md": "/docs/api/input.md"
  },
  {
   "name": "end_frame",
   "qualified": "cinder.input.map.InputMap.end_frame",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "end_frame(mut self)",
   "summary": "Clears edges and per-frame deltas; call once per frame after reading input.",
   "url": "/docs/api/input/#inputmap-end_frame",
   "md": "/docs/api/input.md"
  },
  {
   "name": "pressed",
   "qualified": "cinder.input.map.InputMap.pressed",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "pressed(self, name: String) raises -> Bool",
   "summary": "True while any key or button bound to the action is held; mouse and gamepad axis bindings never press an action. Raises for an unknown action.",
   "url": "/docs/api/input/#inputmap-pressed",
   "md": "/docs/api/input.md"
  },
  {
   "name": "just_pressed",
   "qualified": "cinder.input.map.InputMap.just_pressed",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "just_pressed(self, name: String) raises -> Bool",
   "summary": "True when the action went from released to held since the last end_frame; raises for an unknown action.",
   "url": "/docs/api/input/#inputmap-just_pressed",
   "md": "/docs/api/input.md"
  },
  {
   "name": "just_released",
   "qualified": "cinder.input.map.InputMap.just_released",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "just_released(self, name: String) raises -> Bool",
   "summary": "True when the action went from held to released since the last end_frame; raises for an unknown action.",
   "url": "/docs/api/input/#inputmap-just_released",
   "md": "/docs/api/input.md"
  },
  {
   "name": "axis",
   "qualified": "cinder.input.map.InputMap.axis",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "axis(self, name: String) raises -> Float32",
   "summary": "Sum of the axis' bindings, clamped to [-1, 1] for digital-only axes; analog and mouse contributions are not clamped (mouse deltas are in pixels).",
   "url": "/docs/api/input/#inputmap-axis",
   "md": "/docs/api/input.md"
  },
  {
   "name": "to_text",
   "qualified": "cinder.input.map.InputMap.to_text",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "to_text(self) -> String",
   "summary": "Diffable text: one action/axis line per binding, sorted as defined.",
   "url": "/docs/api/input/#inputmap-to_text",
   "md": "/docs/api/input.md"
  },
  {
   "name": "from_text",
   "qualified": "cinder.input.map.InputMap.from_text",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "from_text(text: String) raises -> InputMap",
   "summary": "Parses the text format written by to_text; blank lines are skipped. Raises on a missing header, another version, a line that is not 2 or 6 fields, an unknown entry or device, or a malformed number.",
   "url": "/docs/api/input/#inputmap-from_text",
   "md": "/docs/api/input.md"
  },
  {
   "name": "save",
   "qualified": "cinder.input.map.InputMap.save",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "save(self, path: String) raises",
   "summary": "Writes to_text() to path; raises when the file cannot be written.",
   "url": "/docs/api/input/#inputmap-save",
   "md": "/docs/api/input.md"
  },
  {
   "name": "load",
   "qualified": "cinder.input.map.InputMap.load",
   "kind": "method",
   "module": "cinder.input.map",
   "parent": "InputMap",
   "signature": "load(path: String) raises -> InputMap",
   "summary": "Reads path and parses it with from_text; raises when the file cannot be read or does not parse.",
   "url": "/docs/api/input/#inputmap-load",
   "md": "/docs/api/input.md"
  },
  {
   "name": "physics",
   "qualified": "cinder.physics",
   "kind": "module",
   "module": "cinder.physics",
   "signature": "",
   "summary": "Physics over Jolt: rigid-body world, queries, character controller and ECS synchronisation.",
   "url": "/docs/api/physics/#cinderphysics-1",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "character",
   "qualified": "cinder.physics.character",
   "kind": "module",
   "module": "cinder.physics.character",
   "signature": "",
   "summary": "Character controller over Jolt's CharacterVirtual: slopes, steps and moving platforms. The character is a capsule whose position is at its feet. update applies the engine's standard velocity rules (stick to the ground and inherit its velocity, otherwise fall under gravity), then runs Jolt's extended update which walks stairs up to step_height and sticks to the floor when walking down. Contacts…",
   "url": "/docs/api/physics/#cinderphysicscharacter",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "GroundState",
   "qualified": "cinder.physics.character.GroundState",
   "kind": "struct",
   "module": "cinder.physics.character",
   "signature": "struct GroundState(Equatable, ImplicitlyCopyable, Movable, Writable)",
   "summary": "Ground contact state of a CharacterController, mirrored from Jolt's ground state.",
   "url": "/docs/api/physics/#struct-groundstate",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "on_ground",
   "qualified": "cinder.physics.character.GroundState.on_ground",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "GroundState",
   "signature": "on_ground() -> GroundState",
   "summary": "Standing on a surface no steeper than max_slope_degrees.",
   "url": "/docs/api/physics/#groundstate-on_ground",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "on_steep_ground",
   "qualified": "cinder.physics.character.GroundState.on_steep_ground",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "GroundState",
   "signature": "on_steep_ground() -> GroundState",
   "summary": "Touching a surface steeper than max_slope_degrees; update treats it like the air and applies gravity.",
   "url": "/docs/api/physics/#groundstate-on_steep_ground",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "not_supported",
   "qualified": "cinder.physics.character.GroundState.not_supported",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "GroundState",
   "signature": "not_supported() -> GroundState",
   "summary": "Touching something that cannot hold the character (its edge, a falling body).",
   "url": "/docs/api/physics/#groundstate-not_supported",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "in_air",
   "qualified": "cinder.physics.character.GroundState.in_air",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "GroundState",
   "signature": "in_air() -> GroundState",
   "summary": "Touching nothing; update applies gravity.",
   "url": "/docs/api/physics/#groundstate-in_air",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.physics.character.GroundState.write_to",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "GroundState",
   "signature": "write_to(self, mut w: Some[Writer])",
   "summary": "",
   "url": "/docs/api/physics/#groundstate-write_to",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "CharacterDesc",
   "qualified": "cinder.physics.character.CharacterDesc",
   "kind": "struct",
   "module": "cinder.physics.character",
   "signature": "struct CharacterDesc(Copyable, Movable)",
   "summary": "Parameters of a CharacterController in metres, kilograms and degrees. radius and height size the capsule (height must exceed 2 * radius + 0.01); max_slope_degrees is the steepest walkable slope and step_height the tallest step walked up; mass and max_strength set how hard dynamic bodies are pushed; layer is the object layer the character collides as; gravity (m/s^2, default -9.81 on Y) applies…",
   "url": "/docs/api/physics/#struct-characterdesc",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.physics.character.CharacterDesc.__init__",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterDesc",
   "signature": "__init__( out self, radius: Float32 = 0.3, height: Float32 = 1.8, layer: Int = 1, max_slope_degrees: Float32 = 50.0, step_height: Float32 = 0.4, mass: Float32 = 70.0, )",
   "summary": "",
   "url": "/docs/api/physics/#characterdesc-__init__",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "CharacterController",
   "qualified": "cinder.physics.character.CharacterController",
   "kind": "struct",
   "module": "cinder.physics.character",
   "signature": "struct CharacterController(Movable)",
   "summary": "A capsule character over Jolt's CharacterVirtual, positioned at its feet. It is not a rigid body: it has no body id. It creates and owns its capsule shape and counts itself in world.live_characters; its destructor destroys the character and the shape and decrements the count. It keeps a raw pointer to the PhysicsWorld, so the world must not move and must outlive the controller; use it from the…",
   "url": "/docs/api/physics/#struct-charactercontroller",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.physics.character.CharacterController.__init__",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterController",
   "signature": "__init__( out self, world: Pointer[PhysicsWorld, MutUntrackedOrigin], desc: CharacterDesc, position: Vec3, ) raises",
   "summary": "",
   "url": "/docs/api/physics/#charactercontroller-__init__",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "position",
   "qualified": "cinder.physics.character.CharacterController.position",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterController",
   "signature": "position(self) -> Vec3",
   "summary": "World position of the character's feet, in metres.",
   "url": "/docs/api/physics/#charactercontroller-position",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "set_position",
   "qualified": "cinder.physics.character.CharacterController.set_position",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterController",
   "signature": "set_position(self, position: Vec3)",
   "summary": "Teleports the character so its feet are at position (metres).",
   "url": "/docs/api/physics/#charactercontroller-set_position",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "rotation",
   "qualified": "cinder.physics.character.CharacterController.rotation",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterController",
   "signature": "rotation(self) -> Quat",
   "summary": "World rotation of the character.",
   "url": "/docs/api/physics/#charactercontroller-rotation",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "set_rotation",
   "qualified": "cinder.physics.character.CharacterController.set_rotation",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterController",
   "signature": "set_rotation(self, rotation: Quat)",
   "summary": "Sets the world rotation of the character.",
   "url": "/docs/api/physics/#charactercontroller-set_rotation",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "velocity",
   "qualified": "cinder.physics.character.CharacterController.velocity",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterController",
   "signature": "velocity(self) -> Vec3",
   "summary": "Linear velocity of the character in metres per second.",
   "url": "/docs/api/physics/#charactercontroller-velocity",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "ground_state",
   "qualified": "cinder.physics.character.CharacterController.ground_state",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterController",
   "signature": "ground_state(self) -> GroundState",
   "summary": "Ground contact state from Jolt's last character update (see GroundState).",
   "url": "/docs/api/physics/#charactercontroller-ground_state",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "is_supported",
   "qualified": "cinder.physics.character.CharacterController.is_supported",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterController",
   "signature": "is_supported(self) -> Bool",
   "summary": "Whether Jolt considers the character supported by the ground it touches.",
   "url": "/docs/api/physics/#charactercontroller-is_supported",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "ground_normal",
   "qualified": "cinder.physics.character.CharacterController.ground_normal",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterController",
   "signature": "ground_normal(self) -> Vec3",
   "summary": "World-space surface normal of the ground contact.",
   "url": "/docs/api/physics/#charactercontroller-ground_normal",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "ground_velocity",
   "qualified": "cinder.physics.character.CharacterController.ground_velocity",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterController",
   "signature": "ground_velocity(self) -> Vec3",
   "summary": "Velocity of the ground under the character in metres per second (a moving platform's), refreshed at the start of update.",
   "url": "/docs/api/physics/#charactercontroller-ground_velocity",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "ground_body",
   "qualified": "cinder.physics.character.CharacterController.ground_body",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterController",
   "signature": "ground_body(self) -> UInt32",
   "summary": "Id of the body under the character's feet; INVALID_BODY when Jolt reports none.",
   "url": "/docs/api/physics/#charactercontroller-ground_body",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "update",
   "qualified": "cinder.physics.character.CharacterController.update",
   "kind": "method",
   "module": "cinder.physics.character",
   "parent": "CharacterController",
   "signature": "update( mut self, dt: Float32, desired_velocity: Vec3, jump_speed: Float32 = 0.0 )",
   "summary": "Moves the character for one step. desired_velocity is the horizontal velocity the player asks for (its Y is ignored); a positive jump_speed launches the character when it stands on the ground. Call before PhysicsWorld.step with the same dt.",
   "url": "/docs/api/physics/#charactercontroller-update",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "sync",
   "qualified": "cinder.physics.sync",
   "kind": "module",
   "module": "cinder.physics.sync",
   "signature": "",
   "summary": "ECS <-> physics synchronisation with interpolation. RigidBody links an entity to a Jolt body and stores the two most recent simulated poses. The fixed-step loop is: push_kinematics(world, physics, dt)   # moved LocalTransforms drive kinematic bodies physics.step(dt) pull_bodies(world, physics)           # dynamic bodies: previous <- current <- Jolt ... write_transforms(world, alpha)        #…",
   "url": "/docs/api/physics/#cinderphysicssync",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "RigidBody",
   "qualified": "cinder.physics.sync.RigidBody",
   "kind": "struct",
   "module": "cinder.physics.sync",
   "signature": "struct RigidBody(Component)",
   "summary": "The physics side of an entity. scale is preserved when the body writes the transform (Jolt bodies carry no scale).",
   "url": "/docs/api/physics/#struct-rigidbody",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.physics.sync.RigidBody.__init__",
   "kind": "method",
   "module": "cinder.physics.sync",
   "parent": "RigidBody",
   "signature": "__init__( out self, body: UInt32, motion: MotionType, position: Vec3, rotation: Quat, scale: Vec3 = Vec3.one(), interpolate: Bool = True, )",
   "summary": "",
   "url": "/docs/api/physics/#rigidbody-__init__",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "component_id",
   "qualified": "cinder.physics.sync.RigidBody.component_id",
   "kind": "method",
   "module": "cinder.physics.sync",
   "parent": "RigidBody",
   "signature": "component_id() -> Int",
   "summary": "",
   "url": "/docs/api/physics/#rigidbody-component_id",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "PhysicsSync",
   "qualified": "cinder.physics.sync.PhysicsSync",
   "kind": "struct",
   "module": "cinder.physics.sync",
   "signature": "struct PhysicsSync(Movable)",
   "summary": "Per-frame physics <-> ECS synchronisation with persistent query specs and scratch buffers, so steady-state frames allocate nothing. The free functions below are convenience wrappers that build a temporary instance.",
   "url": "/docs/api/physics/#struct-physicssync",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.physics.sync.PhysicsSync.__init__",
   "kind": "method",
   "module": "cinder.physics.sync",
   "parent": "PhysicsSync",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/physics/#physicssync-__init__",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "pull_bodies",
   "qualified": "cinder.physics.sync.PhysicsSync.pull_bodies",
   "kind": "method",
   "module": "cinder.physics.sync",
   "parent": "PhysicsSync",
   "signature": "pull_bodies( mut self, mut world: World, physics: PhysicsWorld ) raises -> Int",
   "summary": "After a physics step: copies each dynamic body's pose into its RigidBody, keeping the previous pose for interpolation. Returns the number of bodies read.",
   "url": "/docs/api/physics/#physicssync-pull_bodies",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "push_kinematics",
   "qualified": "cinder.physics.sync.PhysicsSync.push_kinematics",
   "kind": "method",
   "module": "cinder.physics.sync",
   "parent": "PhysicsSync",
   "signature": "push_kinematics( mut self, mut world: World, physics: PhysicsWorld, dt: Float32 ) raises -> Int",
   "summary": "Before a physics step: kinematic bodies whose LocalTransform changed since the last push are moved so they reach the new pose during this step. Returns the count.",
   "url": "/docs/api/physics/#physicssync-push_kinematics",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "write_transforms",
   "qualified": "cinder.physics.sync.PhysicsSync.write_transforms",
   "kind": "method",
   "module": "cinder.physics.sync",
   "parent": "PhysicsSync",
   "signature": "write_transforms( mut self, mut world: World, alpha: Float32 ) raises -> Int",
   "summary": "Writes LocalTransform for dynamic bodies at alpha in [0, 1] between the previous and current poses. Bodies whose id is INVALID_BODY are skipped, as in pull_bodies. Only changed transforms are marked. Returns the count updated.",
   "url": "/docs/api/physics/#physicssync-write_transforms",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "pull_bodies",
   "qualified": "cinder.physics.sync.pull_bodies",
   "kind": "def",
   "module": "cinder.physics.sync",
   "signature": "def pull_bodies(mut world: World, physics: PhysicsWorld) raises -> Int",
   "summary": "PhysicsSync.pull_bodies through a temporary PhysicsSync, so it allocates query scratch on every call. Returns the number of dynamic bodies read.",
   "url": "/docs/api/physics/#def-pull_bodies",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "push_kinematics",
   "qualified": "cinder.physics.sync.push_kinematics",
   "kind": "def",
   "module": "cinder.physics.sync",
   "signature": "def push_kinematics( mut world: World, physics: PhysicsWorld, dt: Float32 ) raises -> Int",
   "summary": "PhysicsSync.push_kinematics through a temporary PhysicsSync, so it allocates query scratch on every call. Returns the number of kinematic bodies moved.",
   "url": "/docs/api/physics/#def-push_kinematics",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "write_transforms",
   "qualified": "cinder.physics.sync.write_transforms",
   "kind": "def",
   "module": "cinder.physics.sync",
   "signature": "def write_transforms(mut world: World, alpha: Float32) raises -> Int",
   "summary": "PhysicsSync.write_transforms through a temporary PhysicsSync, so it allocates scratch on every call. Returns the number of transforms written.",
   "url": "/docs/api/physics/#def-write_transforms",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "world",
   "qualified": "cinder.physics.world",
   "kind": "module",
   "module": "cinder.physics.world",
   "signature": "",
   "summary": "Rigid-body world over Jolt (joltc): layers, shapes, bodies, queries and queued events. Every Jolt object created here is counted; live_objects() must be zero before the world is destroyed. The destructor does not abort on leaks (an abort would hide the real failure of a test that raised): it prints an ERROR record naming the leaked counts (leak_report()), and tests and App.live_objects()…",
   "url": "/docs/api/physics/#cinderphysicsworld",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "to_jolt",
   "qualified": "cinder.physics.world.to_jolt",
   "kind": "def",
   "module": "cinder.physics.world",
   "signature": "def to_jolt(v: Vec3) -> JPH_Vec3",
   "summary": "Converts an engine Vec3 to a joltc JPH_Vec3.",
   "url": "/docs/api/physics/#def-to_jolt",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "from_jolt",
   "qualified": "cinder.physics.world.from_jolt",
   "kind": "def",
   "module": "cinder.physics.world",
   "signature": "def from_jolt(v: JPH_Vec3) -> Vec3",
   "summary": "Converts a joltc JPH_Vec3 to an engine Vec3.",
   "url": "/docs/api/physics/#def-from_jolt",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "quat_to_jolt",
   "qualified": "cinder.physics.world.quat_to_jolt",
   "kind": "def",
   "module": "cinder.physics.world",
   "signature": "def quat_to_jolt(q: Quat) -> JPH_Quat",
   "summary": "Converts an engine Quat to a joltc JPH_Quat (x, y, z, w).",
   "url": "/docs/api/physics/#def-quat_to_jolt",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "quat_from_jolt",
   "qualified": "cinder.physics.world.quat_from_jolt",
   "kind": "def",
   "module": "cinder.physics.world",
   "signature": "def quat_from_jolt(q: JPH_Quat) -> Quat",
   "summary": "Converts a joltc JPH_Quat to an engine Quat.",
   "url": "/docs/api/physics/#def-quat_from_jolt",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "mat_to_jolt",
   "qualified": "cinder.physics.world.mat_to_jolt",
   "kind": "def",
   "module": "cinder.physics.world",
   "signature": "def mat_to_jolt(m: Mat4) -> JPH_Mat4",
   "summary": "Column-major on both sides.",
   "url": "/docs/api/physics/#def-mat_to_jolt",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "LayerConfig",
   "qualified": "cinder.physics.world.LayerConfig",
   "kind": "struct",
   "module": "cinder.physics.world",
   "signature": "struct LayerConfig(Copyable, Movable)",
   "summary": "Object layers and which pairs collide. Layer i is bit i in query masks. Layers flagged static go to a separate broad-phase layer so static geometry is never tested against itself.",
   "url": "/docs/api/physics/#struct-layerconfig",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.physics.world.LayerConfig.__init__",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "LayerConfig",
   "signature": "__init__(out self, count: Int, static_mask: UInt32 = 1)",
   "summary": "",
   "url": "/docs/api/physics/#layerconfig-__init__",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "collide",
   "qualified": "cinder.physics.world.LayerConfig.collide",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "LayerConfig",
   "signature": "collide(mut self, a: Int, b: Int)",
   "summary": "Enables collision between layers a and b (symmetric).",
   "url": "/docs/api/physics/#layerconfig-collide",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "default",
   "qualified": "cinder.physics.world.LayerConfig.default",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "LayerConfig",
   "signature": "default() -> LayerConfig",
   "summary": "Two layers: 0 static, 1 moving; moving collides with both.",
   "url": "/docs/api/physics/#layerconfig-default",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "MotionType",
   "qualified": "cinder.physics.world.MotionType",
   "kind": "struct",
   "module": "cinder.physics.world",
   "signature": "struct MotionType(Equatable, ImplicitlyCopyable, Movable)",
   "summary": "How a body moves: static, kinematic (driven by the caller) or dynamic (simulated).",
   "url": "/docs/api/physics/#struct-motiontype",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "static",
   "qualified": "cinder.physics.world.MotionType.static",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "MotionType",
   "signature": "static() -> MotionType",
   "summary": "A body that never moves.",
   "url": "/docs/api/physics/#motiontype-static",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "kinematic",
   "qualified": "cinder.physics.world.MotionType.kinematic",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "MotionType",
   "signature": "kinematic() -> MotionType",
   "summary": "A body moved by the caller (move_kinematic, set_position_rotation), not by forces or contacts.",
   "url": "/docs/api/physics/#motiontype-kinematic",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "dynamic",
   "qualified": "cinder.physics.world.MotionType.dynamic",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "MotionType",
   "signature": "dynamic() -> MotionType",
   "summary": "A body simulated by Jolt: gravity, forces, impulses and contacts move it.",
   "url": "/docs/api/physics/#motiontype-dynamic",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "to_jolt",
   "qualified": "cinder.physics.world.MotionType.to_jolt",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "MotionType",
   "signature": "to_jolt(self) -> JPH_MotionType",
   "summary": "The matching joltc JPH_MotionType; any value other than static or kinematic maps to dynamic.",
   "url": "/docs/api/physics/#motiontype-to_jolt",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "Shape",
   "qualified": "cinder.physics.world.Shape",
   "kind": "struct",
   "module": "cinder.physics.world",
   "signature": "struct Shape(ImplicitlyCopyable, Movable)",
   "summary": "A reference-counted Jolt shape that the world tracks; copy freely, destroy once.",
   "url": "/docs/api/physics/#struct-shape",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "BodyDesc",
   "qualified": "cinder.physics.world.BodyDesc",
   "kind": "struct",
   "module": "cinder.physics.world",
   "signature": "struct BodyDesc(Copyable, Movable)",
   "summary": "Creation parameters for PhysicsWorld.create_body. The constructor takes the shape, position (metres), motion type, object layer and rotation; the other fields keep their defaults until set: friction 0.5, restitution 0, linear and angular damping 0.05, gravity factor 1, not a sensor, discrete motion quality, sleeping allowed, user data 0, zero initial linear velocity (ignored for static bodies)…",
   "url": "/docs/api/physics/#struct-bodydesc",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.physics.world.BodyDesc.__init__",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "BodyDesc",
   "signature": "__init__( out self, shape: Shape, position: Vec3, motion: MotionType, layer: Int, rotation: Quat = Quat.identity(), )",
   "summary": "",
   "url": "/docs/api/physics/#bodydesc-__init__",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "PhysicsEventKind",
   "qualified": "cinder.physics.world.PhysicsEventKind",
   "kind": "struct",
   "module": "cinder.physics.world",
   "signature": "struct PhysicsEventKind(Equatable, ImplicitlyCopyable, Movable, Writable)",
   "summary": "Kind of a PhysicsEvent; writes as its snake_case name.",
   "url": "/docs/api/physics/#struct-physicseventkind",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "contact_added",
   "qualified": "cinder.physics.world.PhysicsEventKind.contact_added",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsEventKind",
   "signature": "contact_added() -> PhysicsEventKind",
   "summary": "Two bodies started touching.",
   "url": "/docs/api/physics/#physicseventkind-contact_added",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "contact_persisted",
   "qualified": "cinder.physics.world.PhysicsEventKind.contact_persisted",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsEventKind",
   "signature": "contact_persisted() -> PhysicsEventKind",
   "summary": "Two bodies that were touching are still touching.",
   "url": "/docs/api/physics/#physicseventkind-contact_persisted",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "contact_removed",
   "qualified": "cinder.physics.world.PhysicsEventKind.contact_removed",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsEventKind",
   "signature": "contact_removed() -> PhysicsEventKind",
   "summary": "Two bodies stopped touching; the event carries only the body ids.",
   "url": "/docs/api/physics/#physicseventkind-contact_removed",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "body_activated",
   "qualified": "cinder.physics.world.PhysicsEventKind.body_activated",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsEventKind",
   "signature": "body_activated() -> PhysicsEventKind",
   "summary": "A body woke up; the event carries the body and its user_data.",
   "url": "/docs/api/physics/#physicseventkind-body_activated",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "body_deactivated",
   "qualified": "cinder.physics.world.PhysicsEventKind.body_deactivated",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsEventKind",
   "signature": "body_deactivated() -> PhysicsEventKind",
   "summary": "A body went to sleep; the event carries the body and its user_data.",
   "url": "/docs/api/physics/#physicseventkind-body_deactivated",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.physics.world.PhysicsEventKind.write_to",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsEventKind",
   "signature": "write_to(self, mut w: Some[Writer])",
   "summary": "",
   "url": "/docs/api/physics/#physicseventkind-write_to",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "PhysicsEvent",
   "qualified": "cinder.physics.world.PhysicsEvent",
   "kind": "struct",
   "module": "cinder.physics.world",
   "signature": "struct PhysicsEvent(ImplicitlyCopyable, Movable)",
   "summary": "One queued Jolt event. Contacts: body1/body2, world normal (from body 1 to body 2), first contact point on body 1 and the manifold contact_count. Activation: body1 and the body's user_data.",
   "url": "/docs/api/physics/#struct-physicsevent",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "involves",
   "qualified": "cinder.physics.world.PhysicsEvent.involves",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsEvent",
   "signature": "involves(self, body: UInt32) -> Bool",
   "summary": "Whether body is body1 or body2.",
   "url": "/docs/api/physics/#physicsevent-involves",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "pair",
   "qualified": "cinder.physics.world.PhysicsEvent.pair",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsEvent",
   "signature": "pair(self, a: UInt32, b: UInt32) -> Bool",
   "summary": "Whether the event is between bodies a and b, in either order.",
   "url": "/docs/api/physics/#physicsevent-pair",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "RayHit",
   "qualified": "cinder.physics.world.RayHit",
   "kind": "struct",
   "module": "cinder.physics.world",
   "signature": "struct RayHit(ImplicitlyCopyable, Movable)",
   "summary": "Closest hit of PhysicsWorld.raycast: the body id, fraction of the ray (the hit is at origin + fraction * direction), the world point and the hit surface normal.",
   "url": "/docs/api/physics/#struct-rayhit",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "ShapeHit",
   "qualified": "cinder.physics.world.ShapeHit",
   "kind": "struct",
   "module": "cinder.physics.world",
   "signature": "struct ShapeHit(ImplicitlyCopyable, Movable)",
   "summary": "Closest hit of PhysicsWorld.shape_cast: the body id, fraction of the sweep, the contact point on the hit body, that body's surface normal, and penetration_depth, which is greater than zero when the shape already overlaps at the start.",
   "url": "/docs/api/physics/#struct-shapehit",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "PhysicsWorld",
   "qualified": "cinder.physics.world.PhysicsWorld",
   "kind": "struct",
   "module": "cinder.physics.world",
   "signature": "struct PhysicsWorld(Movable)",
   "summary": "One Jolt physics system with its thread pool, layer filters and event queue. Shapes are Shape handles that the caller destroys once with destroy_shape; bodies are UInt32 ids that the caller destroys with destroy_body. Shapes, bodies and characters are counted in live_objects(), which should be zero before the world is destroyed; the destructor prints leak_report() when it is not. Destroying an…",
   "url": "/docs/api/physics/#struct-physicsworld",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.physics.world.PhysicsWorld.__init__",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "__init__( out self, lib: NativePtr, layers: LayerConfig = LayerConfig.default(), max_bodies: Int = 4096, worker_threads: Int = 2, event_capacity: Int = 1 << 14, ) raises",
   "summary": "Creates the Jolt system. JPH_Init is idempotent in joltc, so every world calls it; the process-wide Jolt state is never shut down while a world exists.",
   "url": "/docs/api/physics/#physicsworld-__init__",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "set_gravity",
   "qualified": "cinder.physics.world.PhysicsWorld.set_gravity",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "set_gravity(self, g: Vec3)",
   "summary": "Sets the gravity acceleration in m/s^2 (scaled per body by BodyDesc.gravity_factor).",
   "url": "/docs/api/physics/#physicsworld-set_gravity",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "optimize_broad_phase",
   "qualified": "cinder.physics.world.PhysicsWorld.optimize_broad_phase",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "optimize_broad_phase(self)",
   "summary": "Call after creating many static bodies and before the first step.",
   "url": "/docs/api/physics/#physicsworld-optimize_broad_phase",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "live_objects",
   "qualified": "cinder.physics.world.PhysicsWorld.live_objects",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "live_objects(self) -> Int",
   "summary": "Shapes, bodies and characters still alive. Should be zero before the world is destroyed; the destructor prints leak_report() when it is not, but does not abort.",
   "url": "/docs/api/physics/#physicsworld-live_objects",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "leak_report",
   "qualified": "cinder.physics.world.PhysicsWorld.leak_report",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "leak_report(self) -> Optional[LogRecord]",
   "summary": "The ERROR record the destructor prints when live_objects() is not zero (category physics, with shapes, bodies and characters fields), or None without leaks.",
   "url": "/docs/api/physics/#physicsworld-leak_report",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "error_count",
   "qualified": "cinder.physics.world.PhysicsWorld.error_count",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "error_count(self) -> Int",
   "summary": "Number of ERROR records in diagnostics.",
   "url": "/docs/api/physics/#physicsworld-error_count",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "box",
   "qualified": "cinder.physics.world.PhysicsWorld.box",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "box( mut self, half_extents: Vec3, convex_radius: Float32 = 0.05 ) raises -> Shape",
   "summary": "Creates a box shape with half_extents in metres; convex_radius (metres) rounds its edges. The caller destroys it with destroy_shape. Raises when Jolt fails to create it.",
   "url": "/docs/api/physics/#physicsworld-box",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "sphere",
   "qualified": "cinder.physics.world.PhysicsWorld.sphere",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "sphere(mut self, radius: Float32) raises -> Shape",
   "summary": "Creates a sphere shape of radius metres. The caller destroys it with destroy_shape. Raises when Jolt fails to create it.",
   "url": "/docs/api/physics/#physicsworld-sphere",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "capsule",
   "qualified": "cinder.physics.world.PhysicsWorld.capsule",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "capsule( mut self, half_height: Float32, radius: Float32 ) raises -> Shape",
   "summary": "Capsule along Y: a cylinder of 2 * half_height capped by hemispheres of radius.",
   "url": "/docs/api/physics/#physicsworld-capsule",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "cylinder",
   "qualified": "cinder.physics.world.PhysicsWorld.cylinder",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "cylinder( mut self, half_height: Float32, radius: Float32 ) raises -> Shape",
   "summary": "Creates a cylinder along Y, 2 * half_height tall with radius (metres). The caller destroys it with destroy_shape. Raises when Jolt fails to create it.",
   "url": "/docs/api/physics/#physicsworld-cylinder",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "convex_hull",
   "qualified": "cinder.physics.world.PhysicsWorld.convex_hull",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "convex_hull( mut self, points: List[Vec3], convex_radius: Float32 = 0.05 ) raises -> Shape",
   "summary": "Creates the convex hull of points (metres, shape space); convex_radius rounds it. The caller destroys it with destroy_shape. Raises with fewer than 4 points or when Jolt cannot build the hull.",
   "url": "/docs/api/physics/#physicsworld-convex_hull",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "mesh",
   "qualified": "cinder.physics.world.PhysicsWorld.mesh",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "mesh( mut self, vertices: List[Vec3], indices: List[UInt32] ) raises -> Shape",
   "summary": "Static triangle mesh collider (Jolt mesh shapes only work on static or kinematic bodies).",
   "url": "/docs/api/physics/#physicsworld-mesh",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "scaled",
   "qualified": "cinder.physics.world.PhysicsWorld.scaled",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "scaled(mut self, shape: Shape, scale: Vec3) raises -> Shape",
   "summary": "Creates a shape that is shape scaled per axis by scale. It is a new tracked shape: destroy it with destroy_shape in addition to the original. Raises when Jolt fails to create it.",
   "url": "/docs/api/physics/#physicsworld-scaled",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "destroy_shape",
   "qualified": "cinder.physics.world.PhysicsWorld.destroy_shape",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "destroy_shape(mut self, shape: Shape)",
   "summary": "Releases the caller's reference to shape and decrements the live count; bodies created from it keep their own reference. Call once per created shape and do not use its copies afterwards; a null shape is ignored. A shape this world did not create, or one already destroyed, is not released again: the count is left alone and an ERROR record is added to diagnostics.",
   "url": "/docs/api/physics/#physicsworld-destroy_shape",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "create_body",
   "qualified": "cinder.physics.world.PhysicsWorld.create_body",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "create_body( mut self, desc: BodyDesc, activate: Bool = True ) raises -> UInt32",
   "summary": "Creates a body from desc, adds it to the world (awake when activate) and returns its id; destroy it with destroy_body. The body keeps its own reference to the shape, so the shape handle may be destroyed right after. A positive desc.mass is applied to dynamic bodies only. Raises when the layer is out of range, the shape is null, or Jolt's body limit (max_bodies) is reached.",
   "url": "/docs/api/physics/#physicsworld-create_body",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "destroy_body",
   "qualified": "cinder.physics.world.PhysicsWorld.destroy_body",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "destroy_body(mut self, id: UInt32)",
   "summary": "Removes body id from the world and destroys it. Jolt may reuse the index, but with a new sequence number, so a stale id never names the new body. An id that is not a live body of this world (INVALID_BODY, never created, already destroyed) is ignored: the live count is left alone and an ERROR record is added to diagnostics.",
   "url": "/docs/api/physics/#physicsworld-destroy_body",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "position",
   "qualified": "cinder.physics.world.PhysicsWorld.position",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "position(self, id: UInt32) -> Vec3",
   "summary": "World position of body id, in metres.",
   "url": "/docs/api/physics/#physicsworld-position",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "rotation",
   "qualified": "cinder.physics.world.PhysicsWorld.rotation",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "rotation(self, id: UInt32) -> Quat",
   "summary": "World rotation of body id.",
   "url": "/docs/api/physics/#physicsworld-rotation",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "transform",
   "qualified": "cinder.physics.world.PhysicsWorld.transform",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "transform(self, id: UInt32) -> Mat4",
   "summary": "World matrix of body id, with unit scale.",
   "url": "/docs/api/physics/#physicsworld-transform",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "set_position_rotation",
   "qualified": "cinder.physics.world.PhysicsWorld.set_position_rotation",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "set_position_rotation( self, id: UInt32, position: Vec3, rotation: Quat, activate: Bool = True )",
   "summary": "Teleports body id to position (metres) and rotation, waking it when activate. Kinematic bodies that should carry riders are moved with move_kinematic instead.",
   "url": "/docs/api/physics/#physicsworld-set_position_rotation",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "move_kinematic",
   "qualified": "cinder.physics.world.PhysicsWorld.move_kinematic",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "move_kinematic( self, id: UInt32, target_position: Vec3, target_rotation: Quat, dt: Float32, )",
   "summary": "Sets a kinematic body's velocity so it reaches the target over dt (next step).",
   "url": "/docs/api/physics/#physicsworld-move_kinematic",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "linear_velocity",
   "qualified": "cinder.physics.world.PhysicsWorld.linear_velocity",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "linear_velocity(self, id: UInt32) -> Vec3",
   "summary": "Linear velocity of body id, in metres per second.",
   "url": "/docs/api/physics/#physicsworld-linear_velocity",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "set_linear_velocity",
   "qualified": "cinder.physics.world.PhysicsWorld.set_linear_velocity",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "set_linear_velocity(self, id: UInt32, velocity: Vec3)",
   "summary": "Sets the linear velocity of body id, in metres per second.",
   "url": "/docs/api/physics/#physicsworld-set_linear_velocity",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "angular_velocity",
   "qualified": "cinder.physics.world.PhysicsWorld.angular_velocity",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "angular_velocity(self, id: UInt32) -> Vec3",
   "summary": "Angular velocity of body id, in radians per second.",
   "url": "/docs/api/physics/#physicsworld-angular_velocity",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "set_angular_velocity",
   "qualified": "cinder.physics.world.PhysicsWorld.set_angular_velocity",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "set_angular_velocity(self, id: UInt32, velocity: Vec3)",
   "summary": "Sets the angular velocity of body id, in radians per second.",
   "url": "/docs/api/physics/#physicsworld-set_angular_velocity",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "add_force",
   "qualified": "cinder.physics.world.PhysicsWorld.add_force",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "add_force(self, id: UInt32, force: Vec3)",
   "summary": "Adds force (newtons) to body id at its centre of mass.",
   "url": "/docs/api/physics/#physicsworld-add_force",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "add_impulse",
   "qualified": "cinder.physics.world.PhysicsWorld.add_impulse",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "add_impulse(self, id: UInt32, impulse: Vec3)",
   "summary": "Applies impulse (newton seconds) to body id at its centre of mass; wakes a sleeping body.",
   "url": "/docs/api/physics/#physicsworld-add_impulse",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "add_impulse_at",
   "qualified": "cinder.physics.world.PhysicsWorld.add_impulse_at",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "add_impulse_at(self, id: UInt32, impulse: Vec3, point: Vec3)",
   "summary": "Applies impulse (newton seconds) to body id at the world-space point (metres), which can also spin it.",
   "url": "/docs/api/physics/#physicsworld-add_impulse_at",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "is_active",
   "qualified": "cinder.physics.world.PhysicsWorld.is_active",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "is_active(self, id: UInt32) -> Bool",
   "summary": "Whether body id is awake.",
   "url": "/docs/api/physics/#physicsworld-is_active",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "activate",
   "qualified": "cinder.physics.world.PhysicsWorld.activate",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "activate(self, id: UInt32)",
   "summary": "Wakes body id.",
   "url": "/docs/api/physics/#physicsworld-activate",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "set_motion_type",
   "qualified": "cinder.physics.world.PhysicsWorld.set_motion_type",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "set_motion_type(self, id: UInt32, motion: MotionType)",
   "summary": "Changes the motion type of body id and wakes it. Mesh shapes work only on static or kinematic bodies.",
   "url": "/docs/api/physics/#physicsworld-set_motion_type",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "motion_type",
   "qualified": "cinder.physics.world.PhysicsWorld.motion_type",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "motion_type(self, id: UInt32) -> MotionType",
   "summary": "Current motion type of body id.",
   "url": "/docs/api/physics/#physicsworld-motion_type",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "user_data",
   "qualified": "cinder.physics.world.PhysicsWorld.user_data",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "user_data(self, id: UInt32) -> UInt64",
   "summary": "The 64-bit user value stored on body id (BodyDesc.user_data or set_user_data).",
   "url": "/docs/api/physics/#physicsworld-user_data",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "set_user_data",
   "qualified": "cinder.physics.world.PhysicsWorld.set_user_data",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "set_user_data(self, id: UInt32, value: UInt64)",
   "summary": "Stores a 64-bit user value on body id; activation events report it.",
   "url": "/docs/api/physics/#physicsworld-set_user_data",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "body_count",
   "qualified": "cinder.physics.world.PhysicsWorld.body_count",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "body_count(self) -> Int",
   "summary": "Number of bodies in the Jolt system.",
   "url": "/docs/api/physics/#physicsworld-body_count",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "step",
   "qualified": "cinder.physics.world.PhysicsWorld.step",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "step(mut self, dt: Float32, collision_steps: Int = 1) raises",
   "summary": "Advances the simulation by dt. Deterministic for a given sequence of calls and inputs (Jolt's deterministic mode is on by default).",
   "url": "/docs/api/physics/#physicsworld-step",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "poll_events",
   "qualified": "cinder.physics.world.PhysicsWorld.poll_events",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "poll_events(mut self) -> List[PhysicsEvent]",
   "summary": "Drains the listener queue (call once per step after step).",
   "url": "/docs/api/physics/#physicsworld-poll_events",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "raycast",
   "qualified": "cinder.physics.world.PhysicsWorld.raycast",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "raycast( mut self, origin: Vec3, direction: Vec3, layer_mask: UInt32 = 0xFFFFFFFF, ignore_body: UInt32 = INVALID_BODY, ) -> Optional[RayHit]",
   "summary": "Closest hit along origin + t * direction, t in [0, 1] (direction carries the range). layer_mask selects object layers; ignore_body is skipped.",
   "url": "/docs/api/physics/#physicsworld-raycast",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "shape_cast",
   "qualified": "cinder.physics.world.PhysicsWorld.shape_cast",
   "kind": "method",
   "module": "cinder.physics.world",
   "parent": "PhysicsWorld",
   "signature": "shape_cast( mut self, shape: Shape, transform: Mat4, direction: Vec3, layer_mask: UInt32 = 0xFFFFFFFF, ignore_body: UInt32 = INVALID_BODY, ) -> Optional[ShapeHit]",
   "summary": "Closest hit of shape at transform swept by direction (t in [0, 1]).",
   "url": "/docs/api/physics/#physicsworld-shape_cast",
   "md": "/docs/api/physics.md"
  },
  {
   "name": "platform",
   "qualified": "cinder.platform",
   "kind": "module",
   "module": "cinder.platform",
   "signature": "",
   "summary": "Platform layer: the native library, SDL3 windows, input events and wgpu surfaces. This is the only engine module with per-operating-system branches (library file names, surface creation inside the shim). Everything above it is platform-neutral.",
   "url": "/docs/api/platform/#cinderplatform-1",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "events",
   "qualified": "cinder.platform.events",
   "kind": "module",
   "module": "cinder.platform.events",
   "signature": "",
   "summary": "Platform events in engine terms, translated from SDL3's event union.",
   "url": "/docs/api/platform/#cinderplatformevents",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "EventKind",
   "qualified": "cinder.platform.events.EventKind",
   "kind": "struct",
   "module": "cinder.platform.events",
   "signature": "struct EventKind(Equatable, ImplicitlyCopyable, RegisterPassable, Writable)",
   "summary": "What an Event describes.",
   "url": "/docs/api/platform/#struct-eventkind",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "none",
   "qualified": "cinder.platform.events.EventKind.none",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "none() -> EventKind",
   "summary": "No event: an SDL event this layer does not translate (Platform.poll drops it).",
   "url": "/docs/api/platform/#eventkind-none",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "quit",
   "qualified": "cinder.platform.events.EventKind.quit",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "quit() -> EventKind",
   "summary": "The application was asked to quit (SDL_EVENT_QUIT).",
   "url": "/docs/api/platform/#eventkind-quit",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "window_close",
   "qualified": "cinder.platform.events.EventKind.window_close",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "window_close() -> EventKind",
   "summary": "The user asked to close the window window_id.",
   "url": "/docs/api/platform/#eventkind-window_close",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "window_resized",
   "qualified": "cinder.platform.events.EventKind.window_resized",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "window_resized() -> EventKind",
   "summary": "Pixel size changed; a/b carry the new width and height.",
   "url": "/docs/api/platform/#eventkind-window_resized",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "window_minimized",
   "qualified": "cinder.platform.events.EventKind.window_minimized",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "window_minimized() -> EventKind",
   "summary": "Window window_id was minimised.",
   "url": "/docs/api/platform/#eventkind-window_minimized",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "window_restored",
   "qualified": "cinder.platform.events.EventKind.window_restored",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "window_restored() -> EventKind",
   "summary": "Window window_id was restored.",
   "url": "/docs/api/platform/#eventkind-window_restored",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "window_focus_gained",
   "qualified": "cinder.platform.events.EventKind.window_focus_gained",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "window_focus_gained() -> EventKind",
   "summary": "Window window_id gained keyboard focus.",
   "url": "/docs/api/platform/#eventkind-window_focus_gained",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "window_focus_lost",
   "qualified": "cinder.platform.events.EventKind.window_focus_lost",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "window_focus_lost() -> EventKind",
   "summary": "Window window_id lost keyboard focus.",
   "url": "/docs/api/platform/#eventkind-window_focus_lost",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "key",
   "qualified": "cinder.platform.events.EventKind.key",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "key() -> EventKind",
   "summary": "scancode, keycode, mods, down, repeat.",
   "url": "/docs/api/platform/#eventkind-key",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "mouse_motion",
   "qualified": "cinder.platform.events.EventKind.mouse_motion",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "mouse_motion() -> EventKind",
   "summary": "x, y absolute; dx, dy relative.",
   "url": "/docs/api/platform/#eventkind-mouse_motion",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "mouse_button",
   "qualified": "cinder.platform.events.EventKind.mouse_button",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "mouse_button() -> EventKind",
   "summary": "button (1 = left, 2 = middle, 3 = right), down, x, y.",
   "url": "/docs/api/platform/#eventkind-mouse_button",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "mouse_wheel",
   "qualified": "cinder.platform.events.EventKind.mouse_wheel",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "mouse_wheel() -> EventKind",
   "summary": "dx, dy scroll amounts.",
   "url": "/docs/api/platform/#eventkind-mouse_wheel",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "gamepad_added",
   "qualified": "cinder.platform.events.EventKind.gamepad_added",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "gamepad_added() -> EventKind",
   "summary": "A gamepad was connected; device is its SDL joystick id (Platform.poll opens it).",
   "url": "/docs/api/platform/#eventkind-gamepad_added",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "gamepad_removed",
   "qualified": "cinder.platform.events.EventKind.gamepad_removed",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "gamepad_removed() -> EventKind",
   "summary": "A gamepad was disconnected; device is its SDL joystick id (Platform.poll closes it).",
   "url": "/docs/api/platform/#eventkind-gamepad_removed",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "gamepad_button",
   "qualified": "cinder.platform.events.EventKind.gamepad_button",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "gamepad_button() -> EventKind",
   "summary": "device, button (SDL_GamepadButton), down.",
   "url": "/docs/api/platform/#eventkind-gamepad_button",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "gamepad_axis",
   "qualified": "cinder.platform.events.EventKind.gamepad_axis",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "gamepad_axis() -> EventKind",
   "summary": "device, axis (SDL_GamepadAxis), value normalised to [-1, 1].",
   "url": "/docs/api/platform/#eventkind-gamepad_axis",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.platform.events.EventKind.write_to",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "EventKind",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/platform/#eventkind-write_to",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "Event",
   "qualified": "cinder.platform.events.Event",
   "kind": "struct",
   "module": "cinder.platform.events",
   "signature": "struct Event(ImplicitlyCopyable, RegisterPassable, Writable)",
   "summary": "One translated platform event. Fields are interpreted per kind (see EventKind docstrings).",
   "url": "/docs/api/platform/#struct-event",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "empty",
   "qualified": "cinder.platform.events.Event.empty",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "Event",
   "signature": "empty(kind: EventKind) -> Event",
   "summary": "An event of kind with every other field zero or False.",
   "url": "/docs/api/platform/#event-empty",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "write_to",
   "qualified": "cinder.platform.events.Event.write_to",
   "kind": "method",
   "module": "cinder.platform.events",
   "parent": "Event",
   "signature": "write_to(self, mut writer: Some[Writer])",
   "summary": "",
   "url": "/docs/api/platform/#event-write_to",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "translate_event",
   "qualified": "cinder.platform.events.translate_event",
   "kind": "def",
   "module": "cinder.platform.events",
   "signature": "def translate_event(ev: SDL_Event) -> Event",
   "summary": "Translates an SDL event into an Event; unknown SDL events become EventKind.none().",
   "url": "/docs/api/platform/#def-translate_event",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "native",
   "qualified": "cinder.platform.native",
   "kind": "module",
   "module": "cinder.platform.native",
   "signature": "",
   "summary": "Loading libcinder_native exactly once and sharing it by pointer. NativeLibrary keeps the generated CinderNative struct (library handle plus every resolved symbol) at a stable heap address for the life of the program. Subsystems hold a NativePtr to it and never copy function pointers out (docs/MOJO_NOTES.md: the handle must outlive every call).",
   "url": "/docs/api/platform/#cinderplatformnative",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "default_library_path",
   "qualified": "cinder.platform.native.default_library_path",
   "kind": "def",
   "module": "cinder.platform.native",
   "signature": "def default_library_path() -> String",
   "summary": "The library path for this OS relative to the repository root, unless CINDER_NATIVE_LIB is set.",
   "url": "/docs/api/platform/#def-default_library_path",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "NativeLibrary",
   "qualified": "cinder.platform.native.NativeLibrary",
   "kind": "struct",
   "module": "cinder.platform.native",
   "signature": "struct NativeLibrary(Movable)",
   "summary": "Owns the one loaded copy of libcinder_native.",
   "url": "/docs/api/platform/#struct-nativelibrary",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.platform.native.NativeLibrary.__init__",
   "kind": "method",
   "module": "cinder.platform.native",
   "parent": "NativeLibrary",
   "signature": "__init__(out self, path: String) raises",
   "summary": "Loads the library at path, resolving every bound symbol. Raises when the library is missing, a symbol is missing, or the shim's ABI version differs from the bindings'.",
   "url": "/docs/api/platform/#nativelibrary-__init__",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.platform.native.NativeLibrary.__init__",
   "kind": "method",
   "module": "cinder.platform.native",
   "parent": "NativeLibrary",
   "signature": "__init__(out self) raises",
   "summary": "Loads the library from default_library_path().",
   "url": "/docs/api/platform/#nativelibrary-__init__-1",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "ptr",
   "qualified": "cinder.platform.native.NativeLibrary.ptr",
   "kind": "method",
   "module": "cinder.platform.native",
   "parent": "NativeLibrary",
   "signature": "ptr(self) -> NativePtr",
   "summary": "Pointer to the loaded bindings, valid only while this NativeLibrary lives: it must be destroyed after every subsystem holding the pointer.",
   "url": "/docs/api/platform/#nativelibrary-ptr",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "window",
   "qualified": "cinder.platform.window",
   "kind": "module",
   "module": "cinder.platform.window",
   "signature": "",
   "summary": "SDL3 platform: initialisation, windows, event polling, gamepads and wgpu surface creation.",
   "url": "/docs/api/platform/#cinderplatformwindow",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "GamepadSlot",
   "qualified": "cinder.platform.window.GamepadSlot",
   "kind": "struct",
   "module": "cinder.platform.window",
   "signature": "struct GamepadSlot(ImplicitlyCopyable, Movable)",
   "summary": "An open gamepad: SDL joystick id and the SDL_Gamepad handle.",
   "url": "/docs/api/platform/#struct-gamepadslot",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "Platform",
   "qualified": "cinder.platform.window.Platform",
   "kind": "struct",
   "module": "cinder.platform.window",
   "signature": "struct Platform(Movable)",
   "summary": "SDL initialised for video, events and gamepads. Create one, before any Window, on the main thread. SDL's log goes to a shim queue and is drained into diagnostics by poll.",
   "url": "/docs/api/platform/#struct-platform",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.platform.window.Platform.__init__",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Platform",
   "signature": "__init__(out self, lib: NativePtr) raises",
   "summary": "",
   "url": "/docs/api/platform/#platform-__init__",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "video_driver",
   "qualified": "cinder.platform.window.Platform.video_driver",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Platform",
   "signature": "video_driver(self) -> String",
   "summary": "Name of the current SDL video driver; empty when SDL reports none.",
   "url": "/docs/api/platform/#platform-video_driver",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "last_error",
   "qualified": "cinder.platform.window.Platform.last_error",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Platform",
   "signature": "last_error(self) -> String",
   "summary": "SDL's most recent error message (SDL_GetError).",
   "url": "/docs/api/platform/#platform-last_error",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "poll",
   "qualified": "cinder.platform.window.Platform.poll",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Platform",
   "signature": "poll(mut self, mut events: List[Event])",
   "summary": "Drains SDL's event queue into events (cleared first; capacity is retained so a warmed-up list does not allocate), opening and closing gamepads as they come and go, and moves SDL log lines into diagnostics.",
   "url": "/docs/api/platform/#platform-poll",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "take_diagnostics",
   "qualified": "cinder.platform.window.Platform.take_diagnostics",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Platform",
   "signature": "take_diagnostics(mut self) -> List[LogRecord]",
   "summary": "Moves out the SDL log records collected by poll, leaving diagnostics empty.",
   "url": "/docs/api/platform/#platform-take_diagnostics",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "push_event",
   "qualified": "cinder.platform.window.Platform.push_event",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Platform",
   "signature": "push_event(self, ev: SDL_Event) -> Bool",
   "summary": "Injects an SDL event (tests and replay). Returns False when SDL refused it.",
   "url": "/docs/api/platform/#platform-push_event",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "Window",
   "qualified": "cinder.platform.window.Window",
   "kind": "struct",
   "module": "cinder.platform.window",
   "signature": "struct Window(Movable)",
   "summary": "An SDL window. Destroyed with the struct; create the wgpu surface through create_surface.",
   "url": "/docs/api/platform/#struct-window",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.platform.window.Window.__init__",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Window",
   "signature": "__init__( out self, platform: Platform, title: String, width: Int, height: Int, resizable: Bool = True, hidden: Bool = False, ) raises",
   "summary": "",
   "url": "/docs/api/platform/#window-__init__",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "pixel_size",
   "qualified": "cinder.platform.window.Window.pixel_size",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Window",
   "signature": "pixel_size(self) raises -> Tuple[Int, Int]",
   "summary": "Drawable size in pixels as (width, height); with high pixel density it can differ from the size the window was created with. Raises when SDL fails.",
   "url": "/docs/api/platform/#window-pixel_size",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "set_size",
   "qualified": "cinder.platform.window.Window.set_size",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Window",
   "signature": "set_size(self, width: Int, height: Int) raises",
   "summary": "Requests a new window size and waits for it to apply (SDL_SyncWindow, whose result is ignored); raises when SDL rejects the request.",
   "url": "/docs/api/platform/#window-set_size",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "set_title",
   "qualified": "cinder.platform.window.Window.set_title",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Window",
   "signature": "set_title(mut self, title: String)",
   "summary": "Sets the window title, keeping the text alive in the window; SDL failures are ignored.",
   "url": "/docs/api/platform/#window-set_title",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "show",
   "qualified": "cinder.platform.window.Window.show",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Window",
   "signature": "show(self)",
   "summary": "Shows the window (one created with hidden); SDL failures are ignored.",
   "url": "/docs/api/platform/#window-show",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "set_relative_mouse",
   "qualified": "cinder.platform.window.Window.set_relative_mouse",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Window",
   "signature": "set_relative_mouse(self, enabled: Bool) -> Bool",
   "summary": "Turns SDL relative mouse mode on or off for this window; returns False when SDL refused.",
   "url": "/docs/api/platform/#window-set_relative_mouse",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "create_surface",
   "qualified": "cinder.platform.window.Window.create_surface",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Window",
   "signature": "create_surface(self, instance: WGPUInstance) raises -> WGPUSurface",
   "summary": "Creates the wgpu surface for this window through the shim (X11, Wayland or Metal).",
   "url": "/docs/api/platform/#window-create_surface",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "destroy_surface",
   "qualified": "cinder.platform.window.Window.destroy_surface",
   "kind": "method",
   "module": "cinder.platform.window",
   "parent": "Window",
   "signature": "destroy_surface(self, surface: WGPUSurface)",
   "summary": "Destroys a surface returned by create_surface, through the shim with this window's handle.",
   "url": "/docs/api/platform/#window-destroy_surface",
   "md": "/docs/api/platform.md"
  },
  {
   "name": "render",
   "qualified": "cinder.render",
   "kind": "module",
   "module": "cinder.render",
   "signature": "",
   "summary": "Renderer: cameras, meshes, materials, textures, the frame graph and the forward+ pipeline. Everything here talks to the GPU only through cinder.gfx.",
   "url": "/docs/api/render/#cinderrender-1",
   "md": "/docs/api/render.md"
  },
  {
   "name": "camera",
   "qualified": "cinder.render.camera",
   "kind": "module",
   "module": "cinder.render.camera",
   "signature": "",
   "summary": "Cameras and frustum culling. Right-handed, Y up, camera looks down -Z. Projection is reverse-Z with an infinite far plane, so the frustum has five planes. cull_spheres tests four spheres at a time with SIMD.",
   "url": "/docs/api/render/#cinderrendercamera",
   "md": "/docs/api/render.md"
  },
  {
   "name": "Plane",
   "qualified": "cinder.render.camera.Plane",
   "kind": "struct",
   "module": "cinder.render.camera",
   "signature": "struct Plane(ImplicitlyCopyable, RegisterPassable)",
   "summary": "normal . p + d >= 0 is the inside half-space.",
   "url": "/docs/api/render/#struct-plane",
   "md": "/docs/api/render.md"
  },
  {
   "name": "from_row",
   "qualified": "cinder.render.camera.Plane.from_row",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Plane",
   "signature": "from_row(v: Vec4) -> Plane",
   "summary": "Plane from a clip-space row combination, scaled so normal has unit length.",
   "url": "/docs/api/render/#plane-from_row",
   "md": "/docs/api/render.md"
  },
  {
   "name": "distance",
   "qualified": "cinder.render.camera.Plane.distance",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Plane",
   "signature": "distance(self, p: Vec3) -> Float32",
   "summary": "Signed distance from p to the plane (positive inside), in the units of p.",
   "url": "/docs/api/render/#plane-distance",
   "md": "/docs/api/render.md"
  },
  {
   "name": "Frustum",
   "qualified": "cinder.render.camera.Frustum",
   "kind": "struct",
   "module": "cinder.render.camera",
   "signature": "struct Frustum(Copyable, Movable)",
   "summary": "Left, right, bottom, top, near planes extracted from a view-projection matrix (Gribb/Hartmann). Reverse-Z with infinite far: the near plane is row3 - row2 (clip z <= w); no far plane.",
   "url": "/docs/api/render/#struct-frustum",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.camera.Frustum.__init__",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Frustum",
   "signature": "__init__(out self, view_proj: Mat4)",
   "summary": "",
   "url": "/docs/api/render/#frustum-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "contains_sphere",
   "qualified": "cinder.render.camera.Frustum.contains_sphere",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Frustum",
   "signature": "contains_sphere(self, centre: Vec3, radius: Float32) -> Bool",
   "summary": "True unless the sphere lies entirely behind one of the five planes. Conservative: a sphere near a frustum edge or corner may pass without intersecting it.",
   "url": "/docs/api/render/#frustum-contains_sphere",
   "md": "/docs/api/render.md"
  },
  {
   "name": "contains_point",
   "qualified": "cinder.render.camera.Frustum.contains_point",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Frustum",
   "signature": "contains_point(self, p: Vec3) -> Bool",
   "summary": "True when p is on the inside of all five planes (near, left, right, bottom, top).",
   "url": "/docs/api/render/#frustum-contains_point",
   "md": "/docs/api/render.md"
  },
  {
   "name": "cull_spheres_into",
   "qualified": "cinder.render.camera.Frustum.cull_spheres_into",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Frustum",
   "signature": "cull_spheres_into(self, spheres: List[Vec4], mut out: List[Bool])",
   "summary": "Visibility per sphere (xyz centre, w radius), four spheres per SIMD step, written into a list supplied by the caller (cleared first, capacity kept).",
   "url": "/docs/api/render/#frustum-cull_spheres_into",
   "md": "/docs/api/render.md"
  },
  {
   "name": "cull_spheres",
   "qualified": "cinder.render.camera.Frustum.cull_spheres",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Frustum",
   "signature": "cull_spheres(self, spheres: List[Vec4]) -> List[Bool]",
   "summary": "Visibility per sphere (xyz centre, w radius); allocates the result list. Use cull_spheres_into in per-frame code to reuse a scratch list.",
   "url": "/docs/api/render/#frustum-cull_spheres",
   "md": "/docs/api/render.md"
  },
  {
   "name": "Camera",
   "qualified": "cinder.render.camera.Camera",
   "kind": "struct",
   "module": "cinder.render.camera",
   "signature": "struct Camera(ImplicitlyCopyable, Movable)",
   "summary": "A perspective camera. near is the only clip distance (infinite far).",
   "url": "/docs/api/render/#struct-camera",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.camera.Camera.__init__",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Camera",
   "signature": "__init__( out self, position: Vec3, rotation: Quat, fov_y: Float32 = 1.0471976, aspect: Float32 = 16.0 / 9.0, near: Float32 = 0.05, )",
   "summary": "",
   "url": "/docs/api/render/#camera-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "look_at",
   "qualified": "cinder.render.camera.Camera.look_at",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Camera",
   "signature": "look_at( eye: Vec3, target: Vec3, up: Vec3 = Vec3.unit_y(), fov_y: Float32 = 1.0471976, aspect: Float32 = 16.0 / 9.0, near: Float32 = 0.05, ) -> Camera",
   "summary": "A camera at eye looking at target, with its rotation taken from Mat4.look_at. up only orients the camera (the stored up() is re-orthogonalised); fov_y is the vertical field of view in radians, near the near clip distance in metres.",
   "url": "/docs/api/render/#camera-look_at",
   "md": "/docs/api/render.md"
  },
  {
   "name": "forward",
   "qualified": "cinder.render.camera.Camera.forward",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Camera",
   "signature": "forward(self) -> Vec3",
   "summary": "World-space view direction: Vec3.forward() (-Z) rotated by rotation, unit length.",
   "url": "/docs/api/render/#camera-forward",
   "md": "/docs/api/render.md"
  },
  {
   "name": "right",
   "qualified": "cinder.render.camera.Camera.right",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Camera",
   "signature": "right(self) -> Vec3",
   "summary": "World-space right axis: +X rotated by rotation.",
   "url": "/docs/api/render/#camera-right",
   "md": "/docs/api/render.md"
  },
  {
   "name": "up",
   "qualified": "cinder.render.camera.Camera.up",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Camera",
   "signature": "up(self) -> Vec3",
   "summary": "World-space up axis: +Y rotated by rotation.",
   "url": "/docs/api/render/#camera-up",
   "md": "/docs/api/render.md"
  },
  {
   "name": "view",
   "qualified": "cinder.render.camera.Camera.view",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Camera",
   "signature": "view(self) -> Mat4",
   "summary": "World-to-view matrix (right-handed, looking down -Z), column-major.",
   "url": "/docs/api/render/#camera-view",
   "md": "/docs/api/render.md"
  },
  {
   "name": "projection",
   "qualified": "cinder.render.camera.Camera.projection",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Camera",
   "signature": "projection(self) -> Mat4",
   "summary": "Reverse-Z perspective with an infinite far plane: depth 1 at near, 0 at infinity.",
   "url": "/docs/api/render/#camera-projection",
   "md": "/docs/api/render.md"
  },
  {
   "name": "view_projection",
   "qualified": "cinder.render.camera.Camera.view_projection",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Camera",
   "signature": "view_projection(self) -> Mat4",
   "summary": "projection() * view(): world space to clip space.",
   "url": "/docs/api/render/#camera-view_projection",
   "md": "/docs/api/render.md"
  },
  {
   "name": "frustum",
   "qualified": "cinder.render.camera.Camera.frustum",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Camera",
   "signature": "frustum(self) -> Frustum",
   "summary": "The five-plane culling frustum of view_projection() (no heap allocation).",
   "url": "/docs/api/render/#camera-frustum",
   "md": "/docs/api/render.md"
  },
  {
   "name": "set_viewport",
   "qualified": "cinder.render.camera.Camera.set_viewport",
   "kind": "method",
   "module": "cinder.render.camera",
   "parent": "Camera",
   "signature": "set_viewport(mut self, width: Int, height: Int)",
   "summary": "Sets aspect to width / height in pixels; ignored when height is not positive.",
   "url": "/docs/api/render/#camera-set_viewport",
   "md": "/docs/api/render.md"
  },
  {
   "name": "frame_graph",
   "qualified": "cinder.render.frame_graph",
   "kind": "module",
   "module": "cinder.render.frame_graph",
   "signature": "",
   "summary": "Frame graph: declared passes, transient textures with lifetimes and aliasing, automatic ordering. The graph is rebuilt every frame (cheap: a few passes). compile orders passes by their read/write dependencies, culls passes that contribute nothing to an exported resource, computes each transient's lifetime as a pass-index interval and assigns physical textures so that transients with compatible…",
   "url": "/docs/api/render/#cinderrenderframe_graph",
   "md": "/docs/api/render.md"
  },
  {
   "name": "TransientDesc",
   "qualified": "cinder.render.frame_graph.TransientDesc",
   "kind": "struct",
   "module": "cinder.render.frame_graph",
   "signature": "struct TransientDesc(Equatable, ImplicitlyCopyable, Movable)",
   "summary": "Size in pixels, format, WGPUTextureUsage bits, sample and mip count of a transient. Transients share one pooled physical texture only when their descriptions are equal.",
   "url": "/docs/api/render/#struct-transientdesc",
   "md": "/docs/api/render.md"
  },
  {
   "name": "FrameGraph",
   "qualified": "cinder.render.frame_graph.FrameGraph",
   "kind": "struct",
   "module": "cinder.render.frame_graph",
   "signature": "struct FrameGraph(Movable)",
   "summary": "One frame's passes and resources, compiled into an execution order and pooled textures. Per frame: reset, declare resources (create, import_view, create_external) and passes (add_pass, read, write), export what must survive, compile, then walk order and look up views with view_of. Physical textures are owned by the graph and freed by release (or when a compile no longer requests them);…",
   "url": "/docs/api/render/#struct-framegraph",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.frame_graph.FrameGraph.__init__",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/render/#framegraph-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "reset",
   "qualified": "cinder.render.frame_graph.FrameGraph.reset",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "reset(mut self)",
   "summary": "Starts a new frame's declaration. Physical textures stay pooled; pass records keep their read/write list capacity for reuse.",
   "url": "/docs/api/render/#framegraph-reset",
   "md": "/docs/api/render.md"
  },
  {
   "name": "create",
   "qualified": "cinder.render.frame_graph.FrameGraph.create",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "create(mut self, name: String, desc: TransientDesc) -> Int",
   "summary": "Declares a transient texture and returns its resource index (valid until reset). The physical texture is assigned by compile, possibly shared with other transients.",
   "url": "/docs/api/render/#framegraph-create",
   "md": "/docs/api/render.md"
  },
  {
   "name": "import_view",
   "qualified": "cinder.render.frame_graph.FrameGraph.import_view",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "import_view( mut self, name: String, view: TextureViewHandle, desc: TransientDesc ) -> Int",
   "summary": "A view the caller keeps alive (swapchain, persistent target). Never aliased.",
   "url": "/docs/api/render/#framegraph-import_view",
   "md": "/docs/api/render.md"
  },
  {
   "name": "create_external",
   "qualified": "cinder.render.frame_graph.FrameGraph.create_external",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "create_external(mut self, name: String) -> Int",
   "summary": "A buffer-backed resource (no texture): passes writing it are ordered before readers and kept alive by them, but no physical texture is allocated.",
   "url": "/docs/api/render/#framegraph-create_external",
   "md": "/docs/api/render.md"
  },
  {
   "name": "export",
   "qualified": "cinder.render.frame_graph.FrameGraph.export",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "export(mut self, resource: Int)",
   "summary": "Marks a resource as needed outside the graph; passes feeding it are kept.",
   "url": "/docs/api/render/#framegraph-export",
   "md": "/docs/api/render.md"
  },
  {
   "name": "add_pass",
   "qualified": "cinder.render.frame_graph.FrameGraph.add_pass",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "add_pass(mut self, name: String) -> Int",
   "summary": "Declares a pass and returns its index; reuses a spare pass record when there is one.",
   "url": "/docs/api/render/#framegraph-add_pass",
   "md": "/docs/api/render.md"
  },
  {
   "name": "read",
   "qualified": "cinder.render.frame_graph.FrameGraph.read",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "read(mut self, pass_: Int, resource: Int)",
   "summary": "Declares that pass_ reads resource (ordered after the resource's producer).",
   "url": "/docs/api/render/#framegraph-read",
   "md": "/docs/api/render.md"
  },
  {
   "name": "write",
   "qualified": "cinder.render.frame_graph.FrameGraph.write",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "write(mut self, pass_: Int, resource: Int)",
   "summary": "Declares that pass_ writes resource; writers of a resource keep declaration order.",
   "url": "/docs/api/render/#framegraph-write",
   "md": "/docs/api/render.md"
  },
  {
   "name": "compile",
   "qualified": "cinder.render.frame_graph.FrameGraph.compile",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "compile(mut self, mut res: Resources) raises",
   "summary": "Orders, culls, computes lifetimes and assigns physical textures.",
   "url": "/docs/api/render/#framegraph-compile",
   "md": "/docs/api/render.md"
  },
  {
   "name": "release",
   "qualified": "cinder.render.frame_graph.FrameGraph.release",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "release(mut self, mut res: Resources) raises",
   "summary": "Destroys every pooled physical texture and its view; raises on a Resources error.",
   "url": "/docs/api/render/#framegraph-release",
   "md": "/docs/api/render.md"
  },
  {
   "name": "view_of",
   "qualified": "cinder.render.frame_graph.FrameGraph.view_of",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "view_of(self, resource: Int) raises -> TextureViewHandle",
   "summary": "View of resource after compile: the imported view or its physical texture's view. Raises for an external (buffer-backed) resource and for one with no physical texture (unused, culled or not compiled).",
   "url": "/docs/api/render/#framegraph-view_of",
   "md": "/docs/api/render.md"
  },
  {
   "name": "texture_of",
   "qualified": "cinder.render.frame_graph.FrameGraph.texture_of",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "texture_of(self, resource: Int) raises -> TextureHandle",
   "summary": "Physical texture behind a transient after compile. Raises for imported and external resources and for transients without a physical texture.",
   "url": "/docs/api/render/#framegraph-texture_of",
   "md": "/docs/api/render.md"
  },
  {
   "name": "find",
   "qualified": "cinder.render.frame_graph.FrameGraph.find",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "find(self, name: String) -> Int",
   "summary": "Index of the resource with this name, or -1.",
   "url": "/docs/api/render/#framegraph-find",
   "md": "/docs/api/render.md"
  },
  {
   "name": "physical_count",
   "qualified": "cinder.render.frame_graph.FrameGraph.physical_count",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "physical_count(self) -> Int",
   "summary": "Pooled physical textures after the last compile (FrameStats.transient_textures).",
   "url": "/docs/api/render/#framegraph-physical_count",
   "md": "/docs/api/render.md"
  },
  {
   "name": "is_culled",
   "qualified": "cinder.render.frame_graph.FrameGraph.is_culled",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "is_culled(self, pass_: Int) -> Bool",
   "summary": "True when the last compile culled the pass (it feeds no exported resource).",
   "url": "/docs/api/render/#framegraph-is_culled",
   "md": "/docs/api/render.md"
  },
  {
   "name": "lifetime",
   "qualified": "cinder.render.frame_graph.FrameGraph.lifetime",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "lifetime(self, resource: Int) -> Tuple[Int, Int]",
   "summary": "(first, last) execution-order indices using the resource; (-1, -1) if no kept pass does.",
   "url": "/docs/api/render/#framegraph-lifetime",
   "md": "/docs/api/render.md"
  },
  {
   "name": "to_graphviz",
   "qualified": "cinder.render.frame_graph.FrameGraph.to_graphviz",
   "kind": "method",
   "module": "cinder.render.frame_graph",
   "parent": "FrameGraph",
   "signature": "to_graphviz(self) -> String",
   "summary": "DOT text: passes as boxes in execution order, resources as ellipses, edges for reads/writes.",
   "url": "/docs/api/render/#framegraph-to_graphviz",
   "md": "/docs/api/render.md"
  },
  {
   "name": "lights",
   "qualified": "cinder.render.lights",
   "kind": "module",
   "module": "cinder.render.lights",
   "signature": "",
   "summary": "Lights and the clustered-culling configuration shared with shaders/common.wgsl.",
   "url": "/docs/api/render/#cinderrenderlights",
   "md": "/docs/api/render.md"
  },
  {
   "name": "LightKind",
   "qualified": "cinder.render.lights.LightKind",
   "kind": "struct",
   "module": "cinder.render.lights",
   "signature": "struct LightKind(Equatable, ImplicitlyCopyable, RegisterPassable)",
   "summary": "Light type tag; values mirror LIGHT_* in common.wgsl (0 directional, 1 point, 2 spot).",
   "url": "/docs/api/render/#struct-lightkind",
   "md": "/docs/api/render.md"
  },
  {
   "name": "directional",
   "qualified": "cinder.render.lights.LightKind.directional",
   "kind": "method",
   "module": "cinder.render.lights",
   "parent": "LightKind",
   "signature": "directional() -> LightKind",
   "summary": "Sun-like light at infinity; only its direction matters.",
   "url": "/docs/api/render/#lightkind-directional",
   "md": "/docs/api/render.md"
  },
  {
   "name": "point",
   "qualified": "cinder.render.lights.LightKind.point",
   "kind": "method",
   "module": "cinder.render.lights",
   "parent": "LightKind",
   "signature": "point() -> LightKind",
   "summary": "Omnidirectional light at a position, attenuated to zero at range.",
   "url": "/docs/api/render/#lightkind-point",
   "md": "/docs/api/render.md"
  },
  {
   "name": "spot",
   "qualified": "cinder.render.lights.LightKind.spot",
   "kind": "method",
   "module": "cinder.render.lights",
   "parent": "LightKind",
   "signature": "spot() -> LightKind",
   "summary": "Cone light at a position along direction, attenuated to zero at range.",
   "url": "/docs/api/render/#lightkind-spot",
   "md": "/docs/api/render.md"
  },
  {
   "name": "Light",
   "qualified": "cinder.render.lights.Light",
   "kind": "struct",
   "module": "cinder.render.lights",
   "signature": "struct Light(ImplicitlyCopyable, Movable)",
   "summary": "A light. Directional: direction (travel direction), color * intensity in lux. Point and spot: position, range (metres), intensity in watts, spot cone angles in radians.",
   "url": "/docs/api/render/#struct-light",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.lights.Light.__init__",
   "kind": "method",
   "module": "cinder.render.lights",
   "parent": "Light",
   "signature": "__init__( out self, kind: LightKind, position: Vec3 = Vec3.zero(), direction: Vec3 = Vec3(0.0, -1.0, 0.0), color: Vec3 = Vec3.one(), intensity: Float32 = 1.0, range: Float32 = 10.0, inner_angle: Float32 = 0.4, outer_angle: Float32 = 0.6, cast_shadows: Bool = False, )",
   "summary": "",
   "url": "/docs/api/render/#light-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "sun",
   "qualified": "cinder.render.lights.Light.sun",
   "kind": "method",
   "module": "cinder.render.lights",
   "parent": "Light",
   "signature": "sun( direction: Vec3, color: Vec3 = Vec3.one(), lux: Float32 = 3.0, cast_shadows: Bool = True, ) -> Light",
   "summary": "Directional light travelling along direction (normalised), with lux illuminance. Position, range and cone angles are zero; shadows default to on (cascaded shadow maps).",
   "url": "/docs/api/render/#light-sun",
   "md": "/docs/api/render.md"
  },
  {
   "name": "point_light",
   "qualified": "cinder.render.lights.Light.point_light",
   "kind": "method",
   "module": "cinder.render.lights",
   "parent": "Light",
   "signature": "point_light( position: Vec3, color: Vec3, watts: Float32, range: Float32, cast_shadows: Bool = False, ) -> Light",
   "summary": "Point light at position (metres) emitting watts, reaching zero at range metres.",
   "url": "/docs/api/render/#light-point_light",
   "md": "/docs/api/render.md"
  },
  {
   "name": "spot_light",
   "qualified": "cinder.render.lights.Light.spot_light",
   "kind": "method",
   "module": "cinder.render.lights",
   "parent": "Light",
   "signature": "spot_light( position: Vec3, direction: Vec3, color: Vec3, watts: Float32, range: Float32, inner: Float32, outer: Float32, cast_shadows: Bool = False, ) -> Light",
   "summary": "Spot light along direction (normalised) emitting watts with a range in metres. inner and outer are cone half-angles in radians from the axis: full intensity inside inner, fading to zero at outer.",
   "url": "/docs/api/render/#light-spot_light",
   "md": "/docs/api/render.md"
  },
  {
   "name": "bounding_sphere",
   "qualified": "cinder.render.lights.Light.bounding_sphere",
   "kind": "method",
   "module": "cinder.render.lights",
   "parent": "Light",
   "signature": "bounding_sphere(self) -> Vec4",
   "summary": "Influence sphere: xyz position, w range in metres (meaningless for directional lights).",
   "url": "/docs/api/render/#light-bounding_sphere",
   "md": "/docs/api/render.md"
  },
  {
   "name": "pack",
   "qualified": "cinder.render.lights.Light.pack",
   "kind": "method",
   "module": "cinder.render.lights",
   "parent": "Light",
   "signature": "pack(self, mut w: ByteWriter, shadow_view: Int)",
   "summary": "64 bytes matching Light in common.wgsl.",
   "url": "/docs/api/render/#light-pack",
   "md": "/docs/api/render.md"
  },
  {
   "name": "pack_lights_into",
   "qualified": "cinder.render.lights.pack_lights_into",
   "kind": "def",
   "module": "cinder.render.lights",
   "signature": "def pack_lights_into( mut w: ByteWriter, lights: List[Light], shadow_views: List[Int] )",
   "summary": "Appends the GPU light array (at least one zeroed entry) to w.",
   "url": "/docs/api/render/#def-pack_lights_into",
   "md": "/docs/api/render.md"
  },
  {
   "name": "pack_lights",
   "qualified": "cinder.render.lights.pack_lights",
   "kind": "def",
   "module": "cinder.render.lights",
   "signature": "def pack_lights(lights: List[Light], shadow_views: List[Int]) -> List[UInt8]",
   "summary": "pack_lights_into into a new byte list (allocates; at least one zeroed 64-byte entry). shadow_views[i] is light i's first shadow-view index (-1 or missing: no shadow).",
   "url": "/docs/api/render/#def-pack_lights",
   "md": "/docs/api/render.md"
  },
  {
   "name": "ClusterParams",
   "qualified": "cinder.render.lights.ClusterParams",
   "kind": "struct",
   "module": "cinder.render.lights",
   "signature": "struct ClusterParams(ImplicitlyCopyable, Movable)",
   "summary": "Logarithmic z slicing: slice = log2(z) * scale + bias between near and far.",
   "url": "/docs/api/render/#struct-clusterparams",
   "md": "/docs/api/render.md"
  },
  {
   "name": "compute",
   "qualified": "cinder.render.lights.ClusterParams.compute",
   "kind": "method",
   "module": "cinder.render.lights",
   "parent": "ClusterParams",
   "signature": "compute(near: Float32, far: Float32) -> ClusterParams",
   "summary": "Slice parameters mapping near to slice 0 and far to CLUSTER_Z (metres).",
   "url": "/docs/api/render/#clusterparams-compute",
   "md": "/docs/api/render.md"
  },
  {
   "name": "slice_of",
   "qualified": "cinder.render.lights.ClusterParams.slice_of",
   "kind": "method",
   "module": "cinder.render.lights",
   "parent": "ClusterParams",
   "signature": "slice_of(self, view_z: Float32) -> Int",
   "summary": "Z slice for a positive view-space distance in metres, clamped to [0, CLUSTER_Z - 1]. Mirrors cluster_z_slice in common.wgsl.",
   "url": "/docs/api/render/#clusterparams-slice_of",
   "md": "/docs/api/render.md"
  },
  {
   "name": "material",
   "qualified": "cinder.render.material",
   "kind": "module",
   "module": "cinder.render.material",
   "signature": "",
   "summary": "glTF 2.0 metallic-roughness materials and their GPU bind groups. Uniform layout (96 bytes, 16-byte aligned fields, mirrored by shaders/material.wgsl): 0  base_color: vec4 16 emissive.rgb, emissive_strength 32 metallic, roughness, normal_scale, occlusion_strength 48 alpha_cutoff, alpha_mode (0 opaque, 1 mask, 2 blend), double_sided, texture_flags 64 uv_scale.xy, uv_offset.xy…",
   "url": "/docs/api/render/#cinderrendermaterial",
   "md": "/docs/api/render.md"
  },
  {
   "name": "AlphaMode",
   "qualified": "cinder.render.material.AlphaMode",
   "kind": "struct",
   "module": "cinder.render.material",
   "signature": "struct AlphaMode(Equatable, ImplicitlyCopyable, RegisterPassable)",
   "summary": "How alpha is used; packed into the material uniform and mirrored in WGSL.",
   "url": "/docs/api/render/#struct-alphamode",
   "md": "/docs/api/render.md"
  },
  {
   "name": "opaque",
   "qualified": "cinder.render.material.AlphaMode.opaque",
   "kind": "method",
   "module": "cinder.render.material",
   "parent": "AlphaMode",
   "signature": "opaque() -> AlphaMode",
   "summary": "Alpha is ignored; the surface is fully opaque.",
   "url": "/docs/api/render/#alphamode-opaque",
   "md": "/docs/api/render.md"
  },
  {
   "name": "mask",
   "qualified": "cinder.render.material.AlphaMode.mask",
   "kind": "method",
   "module": "cinder.render.material",
   "parent": "AlphaMode",
   "signature": "mask() -> AlphaMode",
   "summary": "Alpha-tested: fragments with alpha below alpha_cutoff are discarded.",
   "url": "/docs/api/render/#alphamode-mask",
   "md": "/docs/api/render.md"
  },
  {
   "name": "blend",
   "qualified": "cinder.render.material.AlphaMode.blend",
   "kind": "method",
   "module": "cinder.render.material",
   "parent": "AlphaMode",
   "signature": "blend() -> AlphaMode",
   "summary": "Alpha-blended; drawn after opaque batches, sorted back to front.",
   "url": "/docs/api/render/#alphamode-blend",
   "md": "/docs/api/render.md"
  },
  {
   "name": "Material",
   "qualified": "cinder.render.material.Material",
   "kind": "struct",
   "module": "cinder.render.material",
   "signature": "struct Material(Copyable, Movable)",
   "summary": "CPU description. Texture views are null when a map is absent (defaults are bound instead).",
   "url": "/docs/api/render/#struct-material",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.material.Material.__init__",
   "kind": "method",
   "module": "cinder.render.material",
   "parent": "Material",
   "signature": "__init__(out self, name: String = String(\"material\"))",
   "summary": "",
   "url": "/docs/api/render/#material-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "texture_flags",
   "qualified": "cinder.render.material.Material.texture_flags",
   "kind": "method",
   "module": "cinder.render.material",
   "parent": "Material",
   "signature": "texture_flags(self) -> UInt32",
   "summary": "Bit i set when map slot i (TEX_*) has a texture view.",
   "url": "/docs/api/render/#material-texture_flags",
   "md": "/docs/api/render.md"
  },
  {
   "name": "texcoord_bits",
   "qualified": "cinder.render.material.Material.texcoord_bits",
   "kind": "method",
   "module": "cinder.render.material",
   "parent": "Material",
   "signature": "texcoord_bits(self) -> UInt32",
   "summary": "Texture coordinate set per map, 3 bits per TEX_* slot (the shader takes uv1 for 1).",
   "url": "/docs/api/render/#material-texcoord_bits",
   "md": "/docs/api/render.md"
  },
  {
   "name": "pack_uniform",
   "qualified": "cinder.render.material.Material.pack_uniform",
   "kind": "method",
   "module": "cinder.render.material",
   "parent": "Material",
   "signature": "pack_uniform(self) -> List[UInt8]",
   "summary": "The 96-byte uniform laid out as in the module docstring, in a new list (allocates).",
   "url": "/docs/api/render/#material-pack_uniform",
   "md": "/docs/api/render.md"
  },
  {
   "name": "material_bind_group_layout",
   "qualified": "cinder.render.material.material_bind_group_layout",
   "kind": "def",
   "module": "cinder.render.material",
   "signature": "def material_bind_group_layout( mut res: Resources, ) raises -> BindGroupLayoutHandle",
   "summary": "Creates the group-2 material layout matching shaders/material.wgsl; raises on a GPU error. Binding 0 is the uniform (vertex and fragment), 1 the sampler, 2..6 the maps in TEX_* order.",
   "url": "/docs/api/render/#def-material_bind_group_layout",
   "md": "/docs/api/render.md"
  },
  {
   "name": "GpuMaterial",
   "qualified": "cinder.render.material.GpuMaterial",
   "kind": "struct",
   "module": "cinder.render.material",
   "signature": "struct GpuMaterial(ImplicitlyCopyable, Movable)",
   "summary": "Uniform buffer and bind group of an uploaded material. alpha_mode and double_sided are copied from the Material to select its pipeline.",
   "url": "/docs/api/render/#struct-gpumaterial",
   "md": "/docs/api/render.md"
  },
  {
   "name": "upload_material",
   "qualified": "cinder.render.material.upload_material",
   "kind": "def",
   "module": "cinder.render.material",
   "signature": "def upload_material( mut res: Resources, layout: BindGroupLayoutHandle, defaults: DefaultTextures, material: Material, ) raises -> GpuMaterial",
   "summary": "Creates the material's uniform buffer and group-2 bind group; raises on a GPU error. Absent maps bind the defaults (white base colour, metallic-roughness and occlusion, flat normal, black emissive) and a null sampler binds sampler_linear_repeat. The texture views stay owned by the caller; the returned buffer and bind group are new allocations.",
   "url": "/docs/api/render/#def-upload_material",
   "md": "/docs/api/render.md"
  },
  {
   "name": "update_material",
   "qualified": "cinder.render.material.update_material",
   "kind": "def",
   "module": "cinder.render.material",
   "signature": "def update_material( mut res: Resources, gpu: GpuMaterial, material: Material ) raises",
   "summary": "Re-uploads the parameters (textures are fixed per bind group).",
   "url": "/docs/api/render/#def-update_material",
   "md": "/docs/api/render.md"
  },
  {
   "name": "mesh",
   "qualified": "cinder.render.mesh",
   "kind": "module",
   "module": "cinder.render.mesh",
   "signature": "",
   "summary": "Mesh data on the CPU, GPU meshes, the engine vertex format and procedural primitives. Vertex stream (56 bytes): position f32x3 @0, normal f32x3 @12, tangent f32x4 @24 (w = handedness), uv0 f32x2 @40, uv1 f32x2 @48. Skinning attributes live in a second stream (SkinVertex, 24 bytes): joints u16x4 @0, weights f32x4 @8. Indices are u32.",
   "url": "/docs/api/render/#cinderrendermesh",
   "md": "/docs/api/render.md"
  },
  {
   "name": "vertex_layout",
   "qualified": "cinder.render.mesh.vertex_layout",
   "kind": "def",
   "module": "cinder.render.mesh",
   "signature": "def vertex_layout() -> VertexLayout",
   "summary": "Slot 0: the static vertex stream. Locations 0..4.",
   "url": "/docs/api/render/#def-vertex_layout",
   "md": "/docs/api/render.md"
  },
  {
   "name": "skin_vertex_layout",
   "qualified": "cinder.render.mesh.skin_vertex_layout",
   "kind": "def",
   "module": "cinder.render.mesh",
   "signature": "def skin_vertex_layout() -> VertexLayout",
   "summary": "Slot 1: joints and weights. Locations 5 and 6.",
   "url": "/docs/api/render/#def-skin_vertex_layout",
   "md": "/docs/api/render.md"
  },
  {
   "name": "Bounds",
   "qualified": "cinder.render.mesh.Bounds",
   "kind": "struct",
   "module": "cinder.render.mesh",
   "signature": "struct Bounds(ImplicitlyCopyable, Movable)",
   "summary": "Axis-aligned bounding box in mesh space (metres).",
   "url": "/docs/api/render/#struct-bounds",
   "md": "/docs/api/render.md"
  },
  {
   "name": "centre",
   "qualified": "cinder.render.mesh.Bounds.centre",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "Bounds",
   "signature": "centre(self) -> Vec3",
   "summary": "Midpoint of the box.",
   "url": "/docs/api/render/#bounds-centre",
   "md": "/docs/api/render.md"
  },
  {
   "name": "radius",
   "qualified": "cinder.render.mesh.Bounds.radius",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "Bounds",
   "signature": "radius(self) -> Float32",
   "summary": "Half the box diagonal: the radius of the bounding sphere around centre().",
   "url": "/docs/api/render/#bounds-radius",
   "md": "/docs/api/render.md"
  },
  {
   "name": "sphere",
   "qualified": "cinder.render.mesh.Bounds.sphere",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "Bounds",
   "signature": "sphere(self) -> Vec4",
   "summary": "Bounding sphere: xyz centre, w radius (the input of Frustum.cull_spheres_into).",
   "url": "/docs/api/render/#bounds-sphere",
   "md": "/docs/api/render.md"
  },
  {
   "name": "empty",
   "qualified": "cinder.render.mesh.Bounds.empty",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "Bounds",
   "signature": "empty() -> Bounds",
   "summary": "Inverted box (min +3.4e38, max -3.4e38); the first include collapses it to a point.",
   "url": "/docs/api/render/#bounds-empty",
   "md": "/docs/api/render.md"
  },
  {
   "name": "include",
   "qualified": "cinder.render.mesh.Bounds.include",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "Bounds",
   "signature": "include(mut self, p: Vec3)",
   "summary": "Grows the box to contain p.",
   "url": "/docs/api/render/#bounds-include",
   "md": "/docs/api/render.md"
  },
  {
   "name": "MorphTarget",
   "qualified": "cinder.render.mesh.MorphTarget",
   "kind": "struct",
   "module": "cinder.render.mesh",
   "signature": "struct MorphTarget(Copyable, Movable)",
   "summary": "Per-vertex position and normal deltas of one morph target (normals may be empty).",
   "url": "/docs/api/render/#struct-morphtarget",
   "md": "/docs/api/render.md"
  },
  {
   "name": "MeshLod",
   "qualified": "cinder.render.mesh.MeshLod",
   "kind": "struct",
   "module": "cinder.render.mesh",
   "signature": "struct MeshLod(ImplicitlyCopyable, Movable)",
   "summary": "An index range of the combined index buffer and the simplification error it carries.",
   "url": "/docs/api/render/#struct-meshlod",
   "md": "/docs/api/render.md"
  },
  {
   "name": "MeshData",
   "qualified": "cinder.render.mesh.MeshData",
   "kind": "struct",
   "module": "cinder.render.mesh",
   "signature": "struct MeshData(Copyable, Movable)",
   "summary": "CPU-side triangle mesh. Parallel per-vertex arrays; tangents, uv1, joints and weights may be empty and are filled with defaults at upload.",
   "url": "/docs/api/render/#struct-meshdata",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.mesh.MeshData.__init__",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/render/#meshdata-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "vertex_count",
   "qualified": "cinder.render.mesh.MeshData.vertex_count",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "vertex_count(self) -> Int",
   "summary": "Number of vertices (len(positions)).",
   "url": "/docs/api/render/#meshdata-vertex_count",
   "md": "/docs/api/render.md"
  },
  {
   "name": "triangle_count",
   "qualified": "cinder.render.mesh.MeshData.triangle_count",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "triangle_count(self) -> Int",
   "summary": "Number of triangles (len(indices) // 3).",
   "url": "/docs/api/render/#meshdata-triangle_count",
   "md": "/docs/api/render.md"
  },
  {
   "name": "has_skin",
   "qualified": "cinder.render.mesh.MeshData.has_skin",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "has_skin(self) -> Bool",
   "summary": "True when every vertex has joint indices and weights (joints and weights both match positions, non-empty), which is what pack_skin_vertices reads.",
   "url": "/docs/api/render/#meshdata-has_skin",
   "md": "/docs/api/render.md"
  },
  {
   "name": "bounds",
   "qualified": "cinder.render.mesh.MeshData.bounds",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "bounds(self) -> Bounds",
   "summary": "Bounds of positions; a zero box at the origin when the mesh has no vertices.",
   "url": "/docs/api/render/#meshdata-bounds",
   "md": "/docs/api/render.md"
  },
  {
   "name": "validate",
   "qualified": "cinder.render.mesh.MeshData.validate",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "validate(self) raises",
   "summary": "Raises when the arrays are inconsistent. Checks that normals and uv0 match the vertex count, that tangents and uv1 are empty or match it, that joints and weights are either both empty or both match it (a skin needs one of each per vertex), that the index count is a multiple of 3 and that every index is in range. Morph targets are not checked (missing deltas pack as zero).",
   "url": "/docs/api/render/#meshdata-validate",
   "md": "/docs/api/render.md"
  },
  {
   "name": "compute_normals",
   "qualified": "cinder.render.mesh.MeshData.compute_normals",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "compute_normals(mut self)",
   "summary": "Area-weighted face normals accumulated per vertex.",
   "url": "/docs/api/render/#meshdata-compute_normals",
   "md": "/docs/api/render.md"
  },
  {
   "name": "compute_tangents",
   "qualified": "cinder.render.mesh.MeshData.compute_tangents",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "compute_tangents(mut self, lib: NativePtr) raises",
   "summary": "MikkTSpace tangents through the shim (requires normals and uv0).",
   "url": "/docs/api/render/#meshdata-compute_tangents",
   "md": "/docs/api/render.md"
  },
  {
   "name": "pack_vertices",
   "qualified": "cinder.render.mesh.MeshData.pack_vertices",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "pack_vertices(self) -> List[UInt8]",
   "summary": "The 56-byte-per-vertex static stream as a new byte list (allocates). Missing tangents become (1, 0, 0, 1) and missing uv1 repeats uv0. Expects normals and uv0 for every vertex (see validate).",
   "url": "/docs/api/render/#meshdata-pack_vertices",
   "md": "/docs/api/render.md"
  },
  {
   "name": "pack_skin_vertices",
   "qualified": "cinder.render.mesh.MeshData.pack_skin_vertices",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "pack_skin_vertices(self) -> List[UInt8]",
   "summary": "The 24-byte-per-vertex skin stream: little-endian u16x4 joints, then f32x4 weights. Allocates; expects joints and weights for every vertex.",
   "url": "/docs/api/render/#meshdata-pack_skin_vertices",
   "md": "/docs/api/render.md"
  },
  {
   "name": "pack_indices",
   "qualified": "cinder.render.mesh.MeshData.pack_indices",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "pack_indices(self) -> List[UInt8]",
   "summary": "indices as little-endian u32 bytes in a new list (allocates).",
   "url": "/docs/api/render/#meshdata-pack_indices",
   "md": "/docs/api/render.md"
  },
  {
   "name": "pack_morph_deltas",
   "qualified": "cinder.render.mesh.MeshData.pack_morph_deltas",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "pack_morph_deltas(self) -> List[UInt8]",
   "summary": "Per target, per vertex: position delta (vec4) then normal delta (vec4), as common.wgsl reads.",
   "url": "/docs/api/render/#meshdata-pack_morph_deltas",
   "md": "/docs/api/render.md"
  },
  {
   "name": "build_lods",
   "qualified": "cinder.render.mesh.MeshData.build_lods",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "MeshData",
   "signature": "build_lods( self, lib: NativePtr, levels: Int = 4 ) raises -> List[List[UInt32]]",
   "summary": "LOD index lists (level 0 is the original, vertex-cache optimised) via meshoptimizer. Each level targets half the triangles of the previous one with a relative error bound of 2%; a level that cannot be simplified further ends the chain.",
   "url": "/docs/api/render/#meshdata-build_lods",
   "md": "/docs/api/render.md"
  },
  {
   "name": "GpuMesh",
   "qualified": "cinder.render.mesh.GpuMesh",
   "kind": "struct",
   "module": "cinder.render.mesh",
   "signature": "struct GpuMesh(Copyable, Movable)",
   "summary": "Buffers for one mesh. skin_vertices is null when the mesh is not skinned, morph_buffer when it has no morph targets. lods[0] is the full-detail index range. index_count is the full-detail index count (lods[0].index_count, 0 without LODs), the same for upload_mesh_lods and upload_mesh_bytes; the index buffer holds every LOD range, so its total length is the sum over lods.",
   "url": "/docs/api/render/#struct-gpumesh",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.mesh.GpuMesh.__init__",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "GpuMesh",
   "signature": "__init__( out self, vertices: BufferHandle, skin_vertices: BufferHandle, indices: BufferHandle, index_count: UInt32, vertex_count: UInt32, bounds: Bounds, var lods: List[MeshLod], morph_buffer: BufferHandle, morph_target_count: UInt32, )",
   "summary": "",
   "url": "/docs/api/render/#gpumesh-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "select_lod",
   "qualified": "cinder.render.mesh.GpuMesh.select_lod",
   "kind": "method",
   "module": "cinder.render.mesh",
   "parent": "GpuMesh",
   "signature": "select_lod( self, projected_diameter_px: Float32, screen_height_px: Float32 ) -> Int",
   "summary": "Smaller on screen -> coarser LOD. Level 1 below 1/4 of the screen height, level 2 below 1/8, level 3 below 1/16 (resolution independent).",
   "url": "/docs/api/render/#gpumesh-select_lod",
   "md": "/docs/api/render.md"
  },
  {
   "name": "upload_mesh",
   "qualified": "cinder.render.mesh.upload_mesh",
   "kind": "def",
   "module": "cinder.render.mesh",
   "signature": "def upload_mesh( mut res: Resources, label: String, data: MeshData ) raises -> GpuMesh",
   "summary": "Uploads with a single LOD.",
   "url": "/docs/api/render/#def-upload_mesh",
   "md": "/docs/api/render.md"
  },
  {
   "name": "upload_mesh_lods",
   "qualified": "cinder.render.mesh.upload_mesh_lods",
   "kind": "def",
   "module": "cinder.render.mesh",
   "signature": "def upload_mesh_lods( mut res: Resources, label: String, data: MeshData, lod_indices: List[List[UInt32]], ) raises -> GpuMesh",
   "summary": "Uploads vertex streams plus one combined index buffer holding every LOD range.",
   "url": "/docs/api/render/#def-upload_mesh_lods",
   "md": "/docs/api/render.md"
  },
  {
   "name": "upload_mesh_bytes",
   "qualified": "cinder.render.mesh.upload_mesh_bytes",
   "kind": "def",
   "module": "cinder.render.mesh",
   "signature": "def upload_mesh_bytes( mut res: Resources, label: String, vertex_count: UInt32, vertex_bytes: List[UInt8], skin_bytes: List[UInt8], index_bytes: List[UInt8], var lods: List[MeshLod], bounds: Bounds, morph_target_count: UInt32, morph_bytes: List[UInt8], ) raises -> GpuMesh",
   "summary": "Uploads streams that are already in GPU layout (cooked meshes).",
   "url": "/docs/api/render/#def-upload_mesh_bytes",
   "md": "/docs/api/render.md"
  },
  {
   "name": "destroy_mesh",
   "qualified": "cinder.render.mesh.destroy_mesh",
   "kind": "def",
   "module": "cinder.render.mesh",
   "signature": "def destroy_mesh(mut res: Resources, mesh: GpuMesh) raises",
   "summary": "Destroys the mesh's vertex and index buffers, and its skin and morph buffers when present. The handles in mesh are left as they are; raises on a Resources error.",
   "url": "/docs/api/render/#def-destroy_mesh",
   "md": "/docs/api/render.md"
  },
  {
   "name": "cube",
   "qualified": "cinder.render.mesh.cube",
   "kind": "def",
   "module": "cinder.render.mesh",
   "signature": "def cube(half: Float32 = 0.5) -> MeshData",
   "summary": "24-vertex cube with per-face normals, CCW winding seen from outside.",
   "url": "/docs/api/render/#def-cube",
   "md": "/docs/api/render.md"
  },
  {
   "name": "uv_sphere",
   "qualified": "cinder.render.mesh.uv_sphere",
   "kind": "def",
   "module": "cinder.render.mesh",
   "signature": "def uv_sphere( radius: Float32 = 0.5, rings: Int = 16, segments: Int = 32 ) -> MeshData",
   "summary": "UV sphere centred at the origin, poles on +Y and -Y; radius in metres. (rings + 1) * (segments + 1) vertices (the seam is duplicated), counter-clockwise seen from outside. u runs around the sphere from +X towards +Z, v from the top pole (0) to the bottom (1); tangents point along increasing u.",
   "url": "/docs/api/render/#def-uv_sphere",
   "md": "/docs/api/render.md"
  },
  {
   "name": "plane",
   "qualified": "cinder.render.mesh.plane",
   "kind": "def",
   "module": "cinder.render.mesh",
   "signature": "def plane(half: Float32 = 0.5, subdivisions: Int = 1) -> MeshData",
   "summary": "An XZ plane facing +Y.",
   "url": "/docs/api/render/#def-plane",
   "md": "/docs/api/render.md"
  },
  {
   "name": "renderer",
   "qualified": "cinder.render.renderer",
   "kind": "module",
   "module": "cinder.render.renderer",
   "signature": "",
   "summary": "The forward+ renderer: shadows, depth prepass, GTAO, clustered lights, PBR, sky, bloom, tonemap. Renderer.render(scene, target) builds the frame graph for the current settings, compiles it (ordering, transient aliasing), fills the GPU buffers from the scene and records every pass into one command buffer. CPU work per frame: frustum culling (SIMD), LOD selection, batching by (mesh, material,…",
   "url": "/docs/api/render/#cinderrenderrenderer",
   "md": "/docs/api/render.md"
  },
  {
   "name": "Tonemapper",
   "qualified": "cinder.render.renderer.Tonemapper",
   "kind": "struct",
   "module": "cinder.render.renderer",
   "signature": "struct Tonemapper(Equatable, ImplicitlyCopyable, RegisterPassable)",
   "summary": "Tone curve of the tonemap pass; values mirror post.settings.z in post.wgsl.",
   "url": "/docs/api/render/#struct-tonemapper",
   "md": "/docs/api/render.md"
  },
  {
   "name": "agx",
   "qualified": "cinder.render.renderer.Tonemapper.agx",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Tonemapper",
   "signature": "agx() -> Tonemapper",
   "summary": "AgX (the default).",
   "url": "/docs/api/render/#tonemapper-agx",
   "md": "/docs/api/render.md"
  },
  {
   "name": "aces",
   "qualified": "cinder.render.renderer.Tonemapper.aces",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Tonemapper",
   "signature": "aces() -> Tonemapper",
   "summary": "ACES filmic curve.",
   "url": "/docs/api/render/#tonemapper-aces",
   "md": "/docs/api/render.md"
  },
  {
   "name": "none",
   "qualified": "cinder.render.renderer.Tonemapper.none",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Tonemapper",
   "signature": "none() -> Tonemapper",
   "summary": "No curve: the exposed colour is clamped to [0, 1]; also used for debug views.",
   "url": "/docs/api/render/#tonemapper-none",
   "md": "/docs/api/render.md"
  },
  {
   "name": "DebugMode",
   "qualified": "cinder.render.renderer.DebugMode",
   "kind": "struct",
   "module": "cinder.render.renderer",
   "signature": "struct DebugMode(Equatable, ImplicitlyCopyable, RegisterPassable)",
   "summary": "Mirrors DEBUG_* in common.wgsl.",
   "url": "/docs/api/render/#struct-debugmode",
   "md": "/docs/api/render.md"
  },
  {
   "name": "none",
   "qualified": "cinder.render.renderer.DebugMode.none",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "DebugMode",
   "signature": "none() -> DebugMode",
   "summary": "Normal lit output.",
   "url": "/docs/api/render/#debugmode-none",
   "md": "/docs/api/render.md"
  },
  {
   "name": "normals",
   "qualified": "cinder.render.renderer.DebugMode.normals",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "DebugMode",
   "signature": "normals() -> DebugMode",
   "summary": "World-space normals mapped to colour (n * 0.5 + 0.5).",
   "url": "/docs/api/render/#debugmode-normals",
   "md": "/docs/api/render.md"
  },
  {
   "name": "cascades",
   "qualified": "cinder.render.renderer.DebugMode.cascades",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "DebugMode",
   "signature": "cascades() -> DebugMode",
   "summary": "Colour per sun shadow cascade, shaded by the sun angle.",
   "url": "/docs/api/render/#debugmode-cascades",
   "md": "/docs/api/render.md"
  },
  {
   "name": "clusters",
   "qualified": "cinder.render.renderer.DebugMode.clusters",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "DebugMode",
   "signature": "clusters() -> DebugMode",
   "summary": "Heat map of the light count in each fragment's cluster (full scale at 16 lights).",
   "url": "/docs/api/render/#debugmode-clusters",
   "md": "/docs/api/render.md"
  },
  {
   "name": "overdraw",
   "qualified": "cinder.render.renderer.DebugMode.overdraw",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "DebugMode",
   "signature": "overdraw() -> DebugMode",
   "summary": "Overdraw count: forward pipelines blend additively with the depth test off, so every rasterised fragment (hidden or not, opaque or blended) adds 0.1 grey; brightness is the fragment count / 10 (white at 10 or more) and empty sky is black.",
   "url": "/docs/api/render/#debugmode-overdraw",
   "md": "/docs/api/render.md"
  },
  {
   "name": "lod",
   "qualified": "cinder.render.renderer.DebugMode.lod",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "DebugMode",
   "signature": "lod() -> DebugMode",
   "summary": "Colour per instance from its LOD index (bits 8..15 of the instance flags), skinned and morphed instances included.",
   "url": "/docs/api/render/#debugmode-lod",
   "md": "/docs/api/render.md"
  },
  {
   "name": "albedo",
   "qualified": "cinder.render.renderer.DebugMode.albedo",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "DebugMode",
   "signature": "albedo() -> DebugMode",
   "summary": "Unlit base colour (material factor times the base colour map).",
   "url": "/docs/api/render/#debugmode-albedo",
   "md": "/docs/api/render.md"
  },
  {
   "name": "ao",
   "qualified": "cinder.render.renderer.DebugMode.ao",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "DebugMode",
   "signature": "ao() -> DebugMode",
   "summary": "The ambient occlusion term as greyscale.",
   "url": "/docs/api/render/#debugmode-ao",
   "md": "/docs/api/render.md"
  },
  {
   "name": "RenderSettings",
   "qualified": "cinder.render.renderer.RenderSettings",
   "kind": "struct",
   "module": "cinder.render.renderer",
   "signature": "struct RenderSettings(ImplicitlyCopyable, Movable)",
   "summary": "Quality knobs, read at the start of every render (change them between frames). cascade_resolution, atlas_size and atlas_tile are read at construction only.",
   "url": "/docs/api/render/#struct-rendersettings",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.renderer.RenderSettings.__init__",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "RenderSettings",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/render/#rendersettings-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "Environment",
   "qualified": "cinder.render.renderer.Environment",
   "kind": "struct",
   "module": "cinder.render.renderer",
   "signature": "struct Environment(ImplicitlyCopyable, Movable)",
   "summary": "Procedural sky by default; equirect (an RGBA16F 2D texture view) replaces it when set.",
   "url": "/docs/api/render/#struct-environment",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.renderer.Environment.__init__",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Environment",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/render/#environment-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "RenderInstance",
   "qualified": "cinder.render.renderer.RenderInstance",
   "kind": "struct",
   "module": "cinder.render.renderer",
   "signature": "struct RenderInstance(Copyable, Movable)",
   "summary": "One drawn object: mesh and material indices into the renderer's registries.",
   "url": "/docs/api/render/#struct-renderinstance",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.renderer.RenderInstance.__init__",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "RenderInstance",
   "signature": "__init__( out self, mesh: Int, material: Int, transform: Mat4, joint_offset: Int = -1, cast_shadows: Bool = True, )",
   "summary": "",
   "url": "/docs/api/render/#renderinstance-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "RenderScene",
   "qualified": "cinder.render.renderer.RenderScene",
   "kind": "struct",
   "module": "cinder.render.renderer",
   "signature": "struct RenderScene(Movable)",
   "summary": "Everything one render call draws; owned by the caller and only read by the renderer.",
   "url": "/docs/api/render/#struct-renderscene",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.renderer.RenderScene.__init__",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "RenderScene",
   "signature": "__init__(out self, camera: Camera)",
   "summary": "",
   "url": "/docs/api/render/#renderscene-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "FrameStats",
   "qualified": "cinder.render.renderer.FrameStats",
   "kind": "struct",
   "module": "cinder.render.renderer",
   "signature": "struct FrameStats(ImplicitlyCopyable, Movable)",
   "summary": "Counters of the last render, in Renderer.stats.",
   "url": "/docs/api/render/#struct-framestats",
   "md": "/docs/api/render.md"
  },
  {
   "name": "Renderer",
   "qualified": "cinder.render.renderer.Renderer",
   "kind": "struct",
   "module": "cinder.render.renderer",
   "signature": "struct Renderer(Movable)",
   "summary": "The forward+ renderer; render draws a RenderScene into a target view. Owns the pipelines, persistent GPU buffers and textures, the mesh and material registries, the frame graph, the shader library and per-frame scratch (steady-state frames do not allocate). Holds raw pointers to Gfx and Resources, which must outlive it.",
   "url": "/docs/api/render/#struct-renderer",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.renderer.Renderer.__init__",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "__init__( out self, gfx: Pointer[Gfx, MutUntrackedOrigin], res: Pointer[Resources, MutUntrackedOrigin], lib: NativePtr, settings: RenderSettings, target_format: WGPUTextureFormat, ) raises",
   "summary": "",
   "url": "/docs/api/render/#renderer-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "add_mesh",
   "qualified": "cinder.render.renderer.Renderer.add_mesh",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "add_mesh( mut self, label: String, data: MeshData, lods: Bool = True ) raises -> Int",
   "summary": "Uploads data and returns its index in meshes; raises if validation or upload fails. With lods and more than 64 triangles, up to four LODs are built with meshoptimizer; otherwise the mesh has one. Always appends (removed slots are only reused by add_cooked_mesh).",
   "url": "/docs/api/render/#renderer-add_mesh",
   "md": "/docs/api/render.md"
  },
  {
   "name": "add_cooked_mesh",
   "qualified": "cinder.render.renderer.Renderer.add_cooked_mesh",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "add_cooked_mesh( mut self, label: String, cooked: CookedMesh ) raises -> Int",
   "summary": "Registers a cooked mesh (streams already in GPU layout). Reuses a removed slot if any.",
   "url": "/docs/api/render/#renderer-add_cooked_mesh",
   "md": "/docs/api/render.md"
  },
  {
   "name": "replace_cooked_mesh",
   "qualified": "cinder.render.renderer.Renderer.replace_cooked_mesh",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "replace_cooked_mesh( mut self, index: Int, label: String, cooked: CookedMesh ) raises",
   "summary": "Hot reload: swaps the GPU buffers behind index; instances keep their mesh index.",
   "url": "/docs/api/render/#renderer-replace_cooked_mesh",
   "md": "/docs/api/render.md"
  },
  {
   "name": "remove_mesh",
   "qualified": "cinder.render.renderer.Renderer.remove_mesh",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "remove_mesh(mut self, index: Int) raises",
   "summary": "Frees the GPU buffers; the slot is reused by the next add_cooked_mesh. Instances that still reference it are the caller's error (rendering them raises on the invalid handle).",
   "url": "/docs/api/render/#renderer-remove_mesh",
   "md": "/docs/api/render.md"
  },
  {
   "name": "add_material",
   "qualified": "cinder.render.renderer.Renderer.add_material",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "add_material(mut self, material: Material) raises -> Int",
   "summary": "Uploads material and returns its index in materials; raises on a GPU error. A copy of the parameters is kept in material_params; texture views stay the caller's.",
   "url": "/docs/api/render/#renderer-add_material",
   "md": "/docs/api/render.md"
  },
  {
   "name": "replace_material",
   "qualified": "cinder.render.renderer.Renderer.replace_material",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "replace_material(mut self, index: Int, material: Material) raises",
   "summary": "Hot reload: uploads material into slot index (instances keep their material index) and frees the uniform buffer and bind group of the version it replaces. The new version is uploaded before anything is freed, so a failed upload raises and leaves the slot as it was. Replacing a removed slot makes it live again. material_params[index] becomes a copy of material. Texture views and samplers are the caller's: the old ones are not destroyed (destroy them after this call if nothing else uses them). Raises when index is out of range.",
   "url": "/docs/api/render/#renderer-replace_material",
   "md": "/docs/api/render.md"
  },
  {
   "name": "remove_material",
   "qualified": "cinder.render.renderer.Renderer.remove_material",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "remove_material(mut self, index: Int) raises",
   "summary": "Frees the uniform buffer and bind group of slot index and leaves the slot empty (null handles); removing an empty slot does nothing. Indices stay stable: add_material always appends, so a removed slot is never handed out again (only replace_material on the same index revives it). render raises if a visible instance still uses a removed material. Texture views and samplers are the caller's, and material_params[index] keeps the last parameters. Raises when index is out of range.",
   "url": "/docs/api/render/#renderer-remove_material",
   "md": "/docs/api/render.md"
  },
  {
   "name": "material_is_live",
   "qualified": "cinder.render.renderer.Renderer.material_is_live",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "material_is_live(self, index: Int) -> Bool",
   "summary": "True when slot index exists and has not been removed.",
   "url": "/docs/api/render/#renderer-material_is_live",
   "md": "/docs/api/render.md"
  },
  {
   "name": "mesh_lod_count",
   "qualified": "cinder.render.renderer.Renderer.mesh_lod_count",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "mesh_lod_count(self, mesh: Int) -> Int",
   "summary": "Number of LOD index ranges of mesh mesh; level 0 is full detail.",
   "url": "/docs/api/render/#renderer-mesh_lod_count",
   "md": "/docs/api/render.md"
  },
  {
   "name": "reload_shaders",
   "qualified": "cinder.render.renderer.Renderer.reload_shaders",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "reload_shaders(mut self) raises -> Int",
   "summary": "Hot reload: recompiles changed programs and rebuilds every pipeline on success. Pipelines keep their handles; a failed compile keeps the last good module and pipelines.",
   "url": "/docs/api/render/#renderer-reload_shaders",
   "md": "/docs/api/render.md"
  },
  {
   "name": "render",
   "qualified": "cinder.render.renderer.Renderer.render",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "render( mut self, scene: RenderScene, target: TextureViewHandle, width: Int, height: Int, ) raises",
   "summary": "Renders scene into target (format given at construction). Raises GfxError on device loss.",
   "url": "/docs/api/render/#renderer-render",
   "md": "/docs/api/render.md"
  },
  {
   "name": "graph_dot",
   "qualified": "cinder.render.renderer.Renderer.graph_dot",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "graph_dot(mut self) -> String",
   "summary": "DOT text of the last frame's graph (built on demand: debug UI, docs).",
   "url": "/docs/api/render/#renderer-graph_dot",
   "md": "/docs/api/render.md"
  },
  {
   "name": "release",
   "qualified": "cinder.render.renderer.Renderer.release",
   "kind": "method",
   "module": "cinder.render.renderer",
   "parent": "Renderer",
   "signature": "release(mut self) raises",
   "summary": "Frees the frame graph's pooled textures (everything else dies with Resources).",
   "url": "/docs/api/render/#renderer-release",
   "md": "/docs/api/render.md"
  },
  {
   "name": "shader_library",
   "qualified": "cinder.render.shader_library",
   "kind": "module",
   "module": "cinder.render.shader_library",
   "signature": "",
   "summary": "Shader programs assembled from WGSL files with #include \"file.wgsl\" lines, with hot reload. WGSL has no preprocessor, so includes are resolved here (relative to the shader directory, once per program, in order of first appearance). Error locations reported by naga refer to the assembled text; ShaderLibrary maps them back to the file and line they came from before raising.",
   "url": "/docs/api/render/#cinderrendershader_library",
   "md": "/docs/api/render.md"
  },
  {
   "name": "AssembledShader",
   "qualified": "cinder.render.shader_library.AssembledShader",
   "kind": "struct",
   "module": "cinder.render.shader_library",
   "signature": "struct AssembledShader(Copyable, Movable)",
   "summary": "WGSL text with every include spliced in, mapped back to its source files. chunks locate each assembled line in its file; files lists every file read (directory/name), in order of first inclusion.",
   "url": "/docs/api/render/#struct-assembledshader",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.shader_library.AssembledShader.__init__",
   "kind": "method",
   "module": "cinder.render.shader_library",
   "parent": "AssembledShader",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/render/#assembledshader-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "locate",
   "qualified": "cinder.render.shader_library.AssembledShader.locate",
   "kind": "method",
   "module": "cinder.render.shader_library",
   "parent": "AssembledShader",
   "signature": "locate(self, assembled_line: Int) -> Tuple[String, Int]",
   "summary": "File and file line for a line of the assembled text.",
   "url": "/docs/api/render/#assembledshader-locate",
   "md": "/docs/api/render.md"
  },
  {
   "name": "assemble",
   "qualified": "cinder.render.shader_library.assemble",
   "kind": "def",
   "module": "cinder.render.shader_library",
   "signature": "def assemble(directory: String, entry: String) raises -> AssembledShader",
   "summary": "Reads entry and splices every #include \"x\" (each file at most once) into one text.",
   "url": "/docs/api/render/#def-assemble",
   "md": "/docs/api/render.md"
  },
  {
   "name": "ShaderLibrary",
   "qualified": "cinder.render.shader_library.ShaderLibrary",
   "kind": "struct",
   "module": "cinder.render.shader_library",
   "signature": "struct ShaderLibrary(Movable)",
   "summary": "Loads directory/<entry>.wgsl programs with includes; check_for_changes hot reloads.",
   "url": "/docs/api/render/#struct-shaderlibrary",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.shader_library.ShaderLibrary.__init__",
   "kind": "method",
   "module": "cinder.render.shader_library",
   "parent": "ShaderLibrary",
   "signature": "__init__( out self, gfx: Pointer[Gfx, MutUntrackedOrigin], res: Pointer[Resources, MutUntrackedOrigin], shaders: Pointer[ShaderManager, MutUntrackedOrigin], directory: String, )",
   "summary": "",
   "url": "/docs/api/render/#shaderlibrary-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "compile",
   "qualified": "cinder.render.shader_library.ShaderLibrary.compile",
   "kind": "method",
   "module": "cinder.render.shader_library",
   "parent": "ShaderLibrary",
   "signature": "compile(mut self, entry: String) raises -> WGPUShaderModule",
   "summary": "Assembles and compiles without registering (used for one-off modules and by load).",
   "url": "/docs/api/render/#shaderlibrary-compile",
   "md": "/docs/api/render.md"
  },
  {
   "name": "load",
   "qualified": "cinder.render.shader_library.ShaderLibrary.load",
   "kind": "method",
   "module": "cinder.render.shader_library",
   "parent": "ShaderLibrary",
   "signature": "load(mut self, entry: String) raises -> ShaderHandle",
   "summary": "Assembles, compiles and registers entry (a file in directory) for hot reload. Returns the handle Resources holds the module under. Raises on a missing include or a compile error, with locations mapped to the source files.",
   "url": "/docs/api/render/#shaderlibrary-load",
   "md": "/docs/api/render.md"
  },
  {
   "name": "check_for_changes",
   "qualified": "cinder.render.shader_library.ShaderLibrary.check_for_changes",
   "kind": "method",
   "module": "cinder.render.shader_library",
   "parent": "ShaderLibrary",
   "signature": "check_for_changes(mut self) -> Int",
   "summary": "Recompiles programs whose files changed. Returns how many modules were replaced; failures keep the last good module and add an error diagnostic naming file:line:column.",
   "url": "/docs/api/render/#shaderlibrary-check_for_changes",
   "md": "/docs/api/render.md"
  },
  {
   "name": "take_diagnostics",
   "qualified": "cinder.render.shader_library.ShaderLibrary.take_diagnostics",
   "kind": "method",
   "module": "cinder.render.shader_library",
   "parent": "ShaderLibrary",
   "signature": "take_diagnostics(mut self) -> List[LogRecord]",
   "summary": "Returns and clears the reload records from check_for_changes (info or error).",
   "url": "/docs/api/render/#shaderlibrary-take_diagnostics",
   "md": "/docs/api/render.md"
  },
  {
   "name": "shadows",
   "qualified": "cinder.render.shadows",
   "kind": "module",
   "module": "cinder.render.shadows",
   "signature": "",
   "summary": "Cascaded shadow maps for the sun and an atlas for spot and point lights (CPU-side maths). Cascade fitting: each cascade covers a slice of the camera frustum (practical split scheme, lambda 0.75). The orthographic projection is fitted to the slice's bounding sphere so it has a constant size while the camera rotates, and its origin is snapped to whole shadow texels in light space so edges do not…",
   "url": "/docs/api/render/#cinderrendershadows",
   "md": "/docs/api/render.md"
  },
  {
   "name": "Cascade",
   "qualified": "cinder.render.shadows.Cascade",
   "kind": "struct",
   "module": "cinder.render.shadows",
   "signature": "struct Cascade(ImplicitlyCopyable, Movable)",
   "summary": "One fitted sun cascade: an orthographic reverse-Z light view-projection (world to clip).",
   "url": "/docs/api/render/#struct-cascade",
   "md": "/docs/api/render.md"
  },
  {
   "name": "cascade_splits_into",
   "qualified": "cinder.render.shadows.cascade_splits_into",
   "kind": "def",
   "module": "cinder.render.shadows",
   "signature": "def cascade_splits_into( mut out: Array[Float32, CASCADE_COUNT], near: Float32, shadow_distance: Float32, lambda_: Float32 = 0.75, )",
   "summary": "End distances of the four cascades (practical split: blend of log and uniform) into a stack array (no allocation).",
   "url": "/docs/api/render/#def-cascade_splits_into",
   "md": "/docs/api/render.md"
  },
  {
   "name": "cascade_splits",
   "qualified": "cinder.render.shadows.cascade_splits",
   "kind": "def",
   "module": "cinder.render.shadows",
   "signature": "def cascade_splits( near: Float32, shadow_distance: Float32, lambda_: Float32 = 0.75 ) -> List[Float32]",
   "summary": "End distances of the four cascades (practical split: blend of log and uniform).",
   "url": "/docs/api/render/#def-cascade_splits",
   "md": "/docs/api/render.md"
  },
  {
   "name": "fit_cascade",
   "qualified": "cinder.render.shadows.fit_cascade",
   "kind": "def",
   "module": "cinder.render.shadows",
   "signature": "def fit_cascade( camera: Camera, light_dir: Vec3, z0: Float32, z1: Float32, resolution: Int ) -> Cascade",
   "summary": "Orthographic light view-projection for one slice with texel snapping. light_dir is the direction light travels. Depth range is the sphere diameter plus a generous margin behind the slice so casters outside the camera frustum still cast.",
   "url": "/docs/api/render/#def-fit_cascade",
   "md": "/docs/api/render.md"
  },
  {
   "name": "fit_cascades_into",
   "qualified": "cinder.render.shadows.fit_cascades_into",
   "kind": "def",
   "module": "cinder.render.shadows",
   "signature": "def fit_cascades_into( mut out: List[Cascade], camera: Camera, light_dir: Vec3, shadow_distance: Float32, resolution: Int, )",
   "summary": "fit_cascades into a list supplied by the caller (cleared first, capacity kept).",
   "url": "/docs/api/render/#def-fit_cascades_into",
   "md": "/docs/api/render.md"
  },
  {
   "name": "fit_cascades",
   "qualified": "cinder.render.shadows.fit_cascades",
   "kind": "def",
   "module": "cinder.render.shadows",
   "signature": "def fit_cascades( camera: Camera, light_dir: Vec3, shadow_distance: Float32, resolution: Int ) -> List[Cascade]",
   "summary": "fit_cascades_into into a new list (allocates); per-frame code uses the _into variant.",
   "url": "/docs/api/render/#def-fit_cascades",
   "md": "/docs/api/render.md"
  },
  {
   "name": "ShadowView",
   "qualified": "cinder.render.shadows.ShadowView",
   "kind": "struct",
   "module": "cinder.render.shadows",
   "signature": "struct ShadowView(ImplicitlyCopyable, Movable)",
   "summary": "One atlas tile: a light-space view-projection and its uv rectangle (matches common.wgsl).",
   "url": "/docs/api/render/#struct-shadowview",
   "md": "/docs/api/render.md"
  },
  {
   "name": "pack",
   "qualified": "cinder.render.shadows.ShadowView.pack",
   "kind": "method",
   "module": "cinder.render.shadows",
   "parent": "ShadowView",
   "signature": "pack(self, mut w: ByteWriter)",
   "summary": "Appends the 96-byte GPU form (ShadowView in common.wgsl). view_proj, then the uv rectangle (origin x, origin y, size, size), then the texel size in uv, near, far and a zero pad.",
   "url": "/docs/api/render/#shadowview-pack",
   "md": "/docs/api/render.md"
  },
  {
   "name": "ShadowAtlas",
   "qualified": "cinder.render.shadows.ShadowAtlas",
   "kind": "struct",
   "module": "cinder.render.shadows",
   "signature": "struct ShadowAtlas(Movable)",
   "summary": "Fixed grid of square tiles in one depth texture. Spot lights take one tile, point lights six.",
   "url": "/docs/api/render/#struct-shadowatlas",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.shadows.ShadowAtlas.__init__",
   "kind": "method",
   "module": "cinder.render.shadows",
   "parent": "ShadowAtlas",
   "signature": "__init__(out self, size: Int = 4096, tile_size: Int = 512)",
   "summary": "",
   "url": "/docs/api/render/#shadowatlas-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "capacity",
   "qualified": "cinder.render.shadows.ShadowAtlas.capacity",
   "kind": "method",
   "module": "cinder.render.shadows",
   "parent": "ShadowAtlas",
   "signature": "capacity(self) -> Int",
   "summary": "Number of tiles in the atlas (tiles_per_row squared).",
   "url": "/docs/api/render/#shadowatlas-capacity",
   "md": "/docs/api/render.md"
  },
  {
   "name": "reset",
   "qualified": "cinder.render.shadows.ShadowAtlas.reset",
   "kind": "method",
   "module": "cinder.render.shadows",
   "parent": "ShadowAtlas",
   "signature": "reset(mut self)",
   "summary": "Frees every tile and clears views (capacity kept); called at the start of each frame.",
   "url": "/docs/api/render/#shadowatlas-reset",
   "md": "/docs/api/render.md"
  },
  {
   "name": "tile_pixel_origin",
   "qualified": "cinder.render.shadows.ShadowAtlas.tile_pixel_origin",
   "kind": "method",
   "module": "cinder.render.shadows",
   "parent": "ShadowAtlas",
   "signature": "tile_pixel_origin(self, view_index: Int) -> Tuple[Int, Int]",
   "summary": "Top-left pixel of the tile used by shadow view view_index (views fill tiles in order).",
   "url": "/docs/api/render/#shadowatlas-tile_pixel_origin",
   "md": "/docs/api/render.md"
  },
  {
   "name": "allocate",
   "qualified": "cinder.render.shadows.ShadowAtlas.allocate",
   "kind": "method",
   "module": "cinder.render.shadows",
   "parent": "ShadowAtlas",
   "signature": "allocate(mut self, light: Light) -> Int",
   "summary": "Adds the light's shadow views; returns the first view index or -1 when the atlas is full.",
   "url": "/docs/api/render/#shadowatlas-allocate",
   "md": "/docs/api/render.md"
  },
  {
   "name": "pack_views_into",
   "qualified": "cinder.render.shadows.ShadowAtlas.pack_views_into",
   "kind": "method",
   "module": "cinder.render.shadows",
   "parent": "ShadowAtlas",
   "signature": "pack_views_into(self, mut w: ByteWriter)",
   "summary": "Appends the GPU shadow-view array (at least one zeroed entry) to w.",
   "url": "/docs/api/render/#shadowatlas-pack_views_into",
   "md": "/docs/api/render.md"
  },
  {
   "name": "pack_views",
   "qualified": "cinder.render.shadows.ShadowAtlas.pack_views",
   "kind": "method",
   "module": "cinder.render.shadows",
   "parent": "ShadowAtlas",
   "signature": "pack_views(self) -> List[UInt8]",
   "summary": "pack_views_into into a new byte list (allocates; at least one zeroed entry).",
   "url": "/docs/api/render/#shadowatlas-pack_views",
   "md": "/docs/api/render.md"
  },
  {
   "name": "textures",
   "qualified": "cinder.render.textures",
   "kind": "module",
   "module": "cinder.render.textures",
   "signature": "",
   "summary": "GPU textures from CPU images: CPU box-filter mip chains, sRGB or linear formats, defaults.",
   "url": "/docs/api/render/#cinderrendertextures",
   "md": "/docs/api/render.md"
  },
  {
   "name": "GpuTexture",
   "qualified": "cinder.render.textures.GpuTexture",
   "kind": "struct",
   "module": "cinder.render.textures",
   "signature": "struct GpuTexture(ImplicitlyCopyable, Movable)",
   "summary": "An uploaded 2D texture and a view of all its mips; width and height are mip 0 in pixels. The texture and view are owned by whoever uploaded them and freed through Resources.",
   "url": "/docs/api/render/#struct-gputexture",
   "md": "/docs/api/render.md"
  },
  {
   "name": "mip_count",
   "qualified": "cinder.render.textures.mip_count",
   "kind": "def",
   "module": "cinder.render.textures",
   "signature": "def mip_count(width: Int, height: Int) -> Int",
   "summary": "Levels in a full mip chain down to 1x1 (floor(log2(max(width, height))) + 1).",
   "url": "/docs/api/render/#def-mip_count",
   "md": "/docs/api/render.md"
  },
  {
   "name": "downsample",
   "qualified": "cinder.render.textures.downsample",
   "kind": "def",
   "module": "cinder.render.textures",
   "signature": "def downsample(img: Image) -> Image",
   "summary": "2x2 box filter (edge pixels of odd sizes are clamped), in the image's own encoding.",
   "url": "/docs/api/render/#def-downsample",
   "md": "/docs/api/render.md"
  },
  {
   "name": "upload_image",
   "qualified": "cinder.render.textures.upload_image",
   "kind": "def",
   "module": "cinder.render.textures",
   "signature": "def upload_image( mut res: Resources, label: String, img: Image, srgb: Bool, mips: Bool = True ) raises -> GpuTexture",
   "summary": "Uploads an RGBA8 image as a 2D texture with a CPU box-filtered mip chain. srgb selects RGBA8UnormSrgb (colour data) over RGBA8Unorm (linear data); mips = False uploads level 0 only. The caller owns the result; raises on a GPU error.",
   "url": "/docs/api/render/#def-upload_image",
   "md": "/docs/api/render.md"
  },
  {
   "name": "solid_image",
   "qualified": "cinder.render.textures.solid_image",
   "kind": "def",
   "module": "cinder.render.textures",
   "signature": "def solid_image(r: UInt8, g: UInt8, b: UInt8, a: UInt8) -> Image",
   "summary": "1x1 RGBA8 image of one colour (used for the default textures).",
   "url": "/docs/api/render/#def-solid_image",
   "md": "/docs/api/render.md"
  },
  {
   "name": "DefaultTextures",
   "qualified": "cinder.render.textures.DefaultTextures",
   "kind": "struct",
   "module": "cinder.render.textures",
   "signature": "struct DefaultTextures(ImplicitlyCopyable, Movable)",
   "summary": "1x1 fallbacks: white (base colour, occlusion, metallic-roughness), flat normal, black emissive.",
   "url": "/docs/api/render/#struct-defaulttextures",
   "md": "/docs/api/render.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.render.textures.DefaultTextures.__init__",
   "kind": "method",
   "module": "cinder.render.textures",
   "parent": "DefaultTextures",
   "signature": "__init__(out self, mut res: Resources) raises",
   "summary": "",
   "url": "/docs/api/render/#defaulttextures-__init__",
   "md": "/docs/api/render.md"
  },
  {
   "name": "scene",
   "qualified": "cinder.scene",
   "kind": "module",
   "module": "cinder.scene",
   "signature": "",
   "summary": "Scene files: versioned text and binary formats with migrations, over the ECS world.",
   "url": "/docs/api/scene/#cinderscene-1",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "format",
   "qualified": "cinder.scene.format",
   "kind": "module",
   "module": "cinder.scene.format",
   "signature": "",
   "summary": "Scene serialisation: a human-diffable text format and a binary format, versioned, with migrations. Both formats carry the same intermediate representation (SceneDoc: entities with component records of typed fields), so a document can be read in either format, migrated version by version, and written in either. Component types take part by implementing SceneComponent and being registered in a…",
   "url": "/docs/api/scene/#cindersceneformat",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "Field",
   "qualified": "cinder.scene.format.Field",
   "kind": "struct",
   "module": "cinder.scene.format",
   "signature": "struct Field(Copyable, Movable)",
   "summary": "One named, typed value of a component record. kind is a KIND_* constant and selects which of number, integer, text or floats holds the value; the others keep their zero defaults.",
   "url": "/docs/api/scene/#struct-field",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.scene.format.Field.__init__",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "Field",
   "signature": "__init__(out self, name: String, kind: Int)",
   "summary": "",
   "url": "/docs/api/scene/#field-__init__",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "ComponentRecord",
   "qualified": "cinder.scene.format.ComponentRecord",
   "kind": "struct",
   "module": "cinder.scene.format",
   "signature": "struct ComponentRecord(Copyable, Movable)",
   "summary": "A component as stored in a scene: its scene name and its fields in write order.",
   "url": "/docs/api/scene/#struct-componentrecord",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.scene.format.ComponentRecord.__init__",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "ComponentRecord",
   "signature": "__init__(out self, name: String)",
   "summary": "",
   "url": "/docs/api/scene/#componentrecord-__init__",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "find",
   "qualified": "cinder.scene.format.ComponentRecord.find",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "ComponentRecord",
   "signature": "find(self, name: String) -> Int",
   "summary": "Index of the field called name, or -1.",
   "url": "/docs/api/scene/#componentrecord-find",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "rename_field",
   "qualified": "cinder.scene.format.ComponentRecord.rename_field",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "ComponentRecord",
   "signature": "rename_field(mut self, old: String, new: String) -> Bool",
   "summary": "Renames field old to new (for migrations); returns False when there is no field old. An existing field called new is not checked for.",
   "url": "/docs/api/scene/#componentrecord-rename_field",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "EntityRecord",
   "qualified": "cinder.scene.format.EntityRecord",
   "kind": "struct",
   "module": "cinder.scene.format",
   "signature": "struct EntityRecord(Copyable, Movable)",
   "summary": "One entity of a scene: the records of the components it carries.",
   "url": "/docs/api/scene/#struct-entityrecord",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.scene.format.EntityRecord.__init__",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "EntityRecord",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/scene/#entityrecord-__init__",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "find",
   "qualified": "cinder.scene.format.EntityRecord.find",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "EntityRecord",
   "signature": "find(self, name: String) -> Int",
   "summary": "Index of the component record called name, or -1.",
   "url": "/docs/api/scene/#entityrecord-find",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "SceneDoc",
   "qualified": "cinder.scene.format.SceneDoc",
   "kind": "struct",
   "module": "cinder.scene.format",
   "signature": "struct SceneDoc(Movable)",
   "summary": "The format-independent scene: a version and the entities in file order. Entity fields hold indices into entities. Produced by SceneRegistry.to_doc, read_text and read_binary; consumed by SceneRegistry.migrate, SceneRegistry.instantiate, write_text and write_binary.",
   "url": "/docs/api/scene/#struct-scenedoc",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.scene.format.SceneDoc.__init__",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "SceneDoc",
   "signature": "__init__(out self, version: Int = SCENE_VERSION)",
   "summary": "",
   "url": "/docs/api/scene/#scenedoc-__init__",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "FieldWriter",
   "qualified": "cinder.scene.format.FieldWriter",
   "kind": "struct",
   "module": "cinder.scene.format",
   "signature": "struct FieldWriter(Movable)",
   "summary": "Collects a component's fields. Entities are written as file-local indices.",
   "url": "/docs/api/scene/#struct-fieldwriter",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.scene.format.FieldWriter.__init__",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldWriter",
   "signature": "__init__( out self, name: String, index_of: Pointer[List[Int], MutUntrackedOrigin] )",
   "summary": "",
   "url": "/docs/api/scene/#fieldwriter-__init__",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "float",
   "qualified": "cinder.scene.format.FieldWriter.float",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldWriter",
   "signature": "float(mut self, name: String, v: Float32)",
   "summary": "Appends a KIND_FLOAT field.",
   "url": "/docs/api/scene/#fieldwriter-float",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "int",
   "qualified": "cinder.scene.format.FieldWriter.int",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldWriter",
   "signature": "int(mut self, name: String, v: Int)",
   "summary": "Appends a KIND_INT field.",
   "url": "/docs/api/scene/#fieldwriter-int",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "bool",
   "qualified": "cinder.scene.format.FieldWriter.bool",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldWriter",
   "signature": "bool(mut self, name: String, v: Bool)",
   "summary": "Appends a KIND_BOOL field (stored as 0 or 1).",
   "url": "/docs/api/scene/#fieldwriter-bool",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "string",
   "qualified": "cinder.scene.format.FieldWriter.string",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldWriter",
   "signature": "string(mut self, name: String, v: String)",
   "summary": "Appends a KIND_STRING field.",
   "url": "/docs/api/scene/#fieldwriter-string",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "entity",
   "qualified": "cinder.scene.format.FieldWriter.entity",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldWriter",
   "signature": "entity(mut self, name: String, e: Entity)",
   "summary": "Appends a KIND_ENTITY field with e's file-local index: -1 when e is null, beyond the index table or not part of the snapshot. Only the slot index is looked up; the generation is not checked.",
   "url": "/docs/api/scene/#fieldwriter-entity",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "floats",
   "qualified": "cinder.scene.format.FieldWriter.floats",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldWriter",
   "signature": "floats(mut self, name: String, values: List[Float32])",
   "summary": "Appends a KIND_FLOATS field holding a copy of values.",
   "url": "/docs/api/scene/#fieldwriter-floats",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "vec3",
   "qualified": "cinder.scene.format.FieldWriter.vec3",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldWriter",
   "signature": "vec3(mut self, name: String, v: Vec3)",
   "summary": "Appends v as a three-float KIND_FLOATS field.",
   "url": "/docs/api/scene/#fieldwriter-vec3",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "mat4",
   "qualified": "cinder.scene.format.FieldWriter.mat4",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldWriter",
   "signature": "mat4(mut self, name: String, m: Mat4)",
   "summary": "Appends m as a 16-float KIND_FLOATS field in column-major order.",
   "url": "/docs/api/scene/#fieldwriter-mat4",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "FieldReader",
   "qualified": "cinder.scene.format.FieldReader",
   "kind": "struct",
   "module": "cinder.scene.format",
   "signature": "struct FieldReader(Movable)",
   "summary": "Reads a component's fields by name; missing fields take the given default.",
   "url": "/docs/api/scene/#struct-fieldreader",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.scene.format.FieldReader.__init__",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldReader",
   "signature": "__init__( out self, var record: ComponentRecord, entities: Pointer[List[Entity], MutUntrackedOrigin], )",
   "summary": "",
   "url": "/docs/api/scene/#fieldreader-__init__",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "float",
   "qualified": "cinder.scene.format.FieldReader.float",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldReader",
   "signature": "float(mut self, name: String, default: Float32) -> Float32",
   "summary": "Field name as a float, or default when absent. An integer field is converted; any other kind sets error and returns default.",
   "url": "/docs/api/scene/#fieldreader-float",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "int",
   "qualified": "cinder.scene.format.FieldReader.int",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldReader",
   "signature": "int(mut self, name: String, default: Int) -> Int",
   "summary": "Field name as an integer, or default when absent; another kind sets error and returns default.",
   "url": "/docs/api/scene/#fieldreader-int",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "bool",
   "qualified": "cinder.scene.format.FieldReader.bool",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldReader",
   "signature": "bool(mut self, name: String, default: Bool) -> Bool",
   "summary": "Field name as a boolean, or default when absent; another kind sets error and returns default.",
   "url": "/docs/api/scene/#fieldreader-bool",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "string",
   "qualified": "cinder.scene.format.FieldReader.string",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldReader",
   "signature": "string(mut self, name: String, default: String) -> String",
   "summary": "Field name as a string, or default when absent; another kind sets error and returns default.",
   "url": "/docs/api/scene/#fieldreader-string",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "entity",
   "qualified": "cinder.scene.format.FieldReader.entity",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldReader",
   "signature": "entity(mut self, name: String) -> Entity",
   "summary": "Field name remapped to the spawned entity. Returns the null entity when the field is absent, not an entity field, -1 or out of range; never sets error.",
   "url": "/docs/api/scene/#fieldreader-entity",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "floats",
   "qualified": "cinder.scene.format.FieldReader.floats",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldReader",
   "signature": "floats(mut self, name: String, count: Int) -> List[Float32]",
   "summary": "The count floats of field name. Returns count zeros when the field is absent, and also when it is not a KIND_FLOATS field of exactly count values, in which case error is set.",
   "url": "/docs/api/scene/#fieldreader-floats",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "vec3",
   "qualified": "cinder.scene.format.FieldReader.vec3",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldReader",
   "signature": "vec3(mut self, name: String, default: Vec3) -> Vec3",
   "summary": "Field name as a Vec3, or default when absent; a field of another shape sets error and yields zero.",
   "url": "/docs/api/scene/#fieldreader-vec3",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "mat4",
   "qualified": "cinder.scene.format.FieldReader.mat4",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "FieldReader",
   "signature": "mat4(mut self, name: String) -> Mat4",
   "summary": "Field name as a column-major Mat4, or identity when absent; a field of another shape sets error and yields an all-zero matrix.",
   "url": "/docs/api/scene/#fieldreader-mat4",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "SceneComponent",
   "qualified": "cinder.scene.format.SceneComponent",
   "kind": "trait",
   "module": "cinder.scene.format",
   "signature": "trait SceneComponent(Component)",
   "summary": "A component that can be saved: name, field writer and reader.",
   "url": "/docs/api/scene/#trait-scenecomponent",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "scene_name",
   "qualified": "cinder.scene.format.SceneComponent.scene_name",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "SceneComponent",
   "signature": "scene_name() -> String",
   "summary": "The component's name in scene files, matched against component records on load.",
   "url": "/docs/api/scene/#scenecomponent-scene_name",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "write_scene",
   "qualified": "cinder.scene.format.SceneComponent.write_scene",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "SceneComponent",
   "signature": "write_scene(self, mut w: FieldWriter)",
   "summary": "Writes the component's fields into w.",
   "url": "/docs/api/scene/#scenecomponent-write_scene",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "read_scene",
   "qualified": "cinder.scene.format.SceneComponent.read_scene",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "SceneComponent",
   "signature": "read_scene(mut r: FieldReader) -> Self",
   "summary": "Builds the component from r, with defaults for missing fields. When r.error is set afterwards (the typed getters set it on a kind mismatch) the component is not added and SceneRegistry.instantiate raises.",
   "url": "/docs/api/scene/#scenecomponent-read_scene",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "SceneRegistry",
   "qualified": "cinder.scene.format.SceneRegistry",
   "kind": "struct",
   "module": "cinder.scene.format",
   "signature": "struct SceneRegistry(Movable)",
   "summary": "Known component types and version migrations.",
   "url": "/docs/api/scene/#struct-sceneregistry",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.scene.format.SceneRegistry.__init__",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "SceneRegistry",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/scene/#sceneregistry-__init__",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "register",
   "qualified": "cinder.scene.format.SceneRegistry.register",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "SceneRegistry",
   "signature": "register[T: SceneComponent](mut self)",
   "summary": "Makes T saveable under T.scene_name(). Duplicate names are not rejected; lookups on load use the first registration.",
   "url": "/docs/api/scene/#sceneregistry-register",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "add_migration",
   "qualified": "cinder.scene.format.SceneRegistry.add_migration",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "SceneRegistry",
   "signature": "add_migration(mut self, from_version: Int, migration: MigrationFn)",
   "summary": "Registers migration to upgrade documents at from_version to from_version + 1.",
   "url": "/docs/api/scene/#sceneregistry-add_migration",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "to_doc",
   "qualified": "cinder.scene.format.SceneRegistry.to_doc",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "SceneRegistry",
   "signature": "to_doc(self, mut world: World) raises -> SceneDoc",
   "summary": "Snapshots every live entity (in archetype order) with its registered components.",
   "url": "/docs/api/scene/#sceneregistry-to_doc",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "migrate",
   "qualified": "cinder.scene.format.SceneRegistry.migrate",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "SceneRegistry",
   "signature": "migrate(self, mut doc: SceneDoc) raises",
   "summary": "Applies registered migrations until the document is at SCENE_VERSION.",
   "url": "/docs/api/scene/#sceneregistry-migrate",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "instantiate",
   "qualified": "cinder.scene.format.SceneRegistry.instantiate",
   "kind": "method",
   "module": "cinder.scene.format",
   "parent": "SceneRegistry",
   "signature": "instantiate( self, mut world: World, doc: SceneDoc ) raises -> List[Entity]",
   "summary": "Spawns the document's entities (after migration) and returns them in file order.",
   "url": "/docs/api/scene/#sceneregistry-instantiate",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "format_float",
   "qualified": "cinder.scene.format.format_float",
   "kind": "def",
   "module": "cinder.scene.format",
   "signature": "def format_float(v: Float32) -> String",
   "summary": "Shortest decimal that round-trips, else the IEEE bits as 0x....",
   "url": "/docs/api/scene/#def-format_float",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "parse_float",
   "qualified": "cinder.scene.format.parse_float",
   "kind": "def",
   "module": "cinder.scene.format",
   "signature": "def parse_float(text: String) raises -> Float32",
   "summary": "Parses a float written by format_float: a decimal, or 0x followed by up to 8 hex digits of IEEE bits. Raises on malformed text.",
   "url": "/docs/api/scene/#def-parse_float",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "bitcast_u32_to_f32",
   "qualified": "cinder.scene.format.bitcast_u32_to_f32",
   "kind": "def",
   "module": "cinder.scene.format",
   "signature": "def bitcast_u32_to_f32(bits: UInt32) -> Float32",
   "summary": "Reinterprets IEEE-754 single-precision bits as a Float32.",
   "url": "/docs/api/scene/#def-bitcast_u32_to_f32",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "write_text",
   "qualified": "cinder.scene.format.write_text",
   "kind": "def",
   "module": "cinder.scene.format",
   "signature": "def write_text(doc: SceneDoc) -> String",
   "summary": "Serialises doc in the text format described in the module docstring: a cinder-scene N header, one entity i line per entity and one indented Name key=value ... line per component.",
   "url": "/docs/api/scene/#def-write_text",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "read_text",
   "qualified": "cinder.scene.format.read_text",
   "kind": "def",
   "module": "cinder.scene.format",
   "signature": "def read_text(text: String) raises -> SceneDoc",
   "summary": "Parses the text format into a SceneDoc at the file's version (not migrated). Blank lines and lines starting with # are skipped. Raises on a missing header, entities out of order, a component line before any entity, an unterminated quote or bracket, a token without =, or a value that does not parse.",
   "url": "/docs/api/scene/#def-read_text",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "write_binary",
   "qualified": "cinder.scene.format.write_binary",
   "kind": "def",
   "module": "cinder.scene.format",
   "signature": "def write_binary(doc: SceneDoc) -> List[UInt8]",
   "summary": "Serialises doc in the binary format: MAGIC, then little-endian u32 version and entity count; per entity a component count, per component its name and field count, per field its name, a u8 kind and the value. Strings are a u32 byte length plus bytes; integers, bools and entities are 64-bit (low word first); float lists carry a u32 count.",
   "url": "/docs/api/scene/#def-write_binary",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "read_binary",
   "qualified": "cinder.scene.format.read_binary",
   "kind": "def",
   "module": "cinder.scene.format",
   "signature": "def read_binary(var data: List[UInt8]) raises -> SceneDoc",
   "summary": "Parses the binary format written by write_binary into a SceneDoc at the file's version (not migrated). Raises on a bad magic, truncated data, an unknown field kind, or implausible counts (over 10 million entities, 10 000 components per entity or fields per component, or 1 million floats per field). Trailing bytes are ignored.",
   "url": "/docs/api/scene/#def-read_binary",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "gltf_spawn",
   "qualified": "cinder.scene.gltf_spawn",
   "kind": "module",
   "module": "cinder.scene.gltf_spawn",
   "signature": "",
   "summary": "Spawning a glTF asset into the ECS: one entity per node (transform hierarchy) and one child entity per mesh primitive (MeshRenderer), plus static collision triangles for level geometry.",
   "url": "/docs/api/scene/#cinderscenegltf_spawn",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "SpawnedGltf",
   "qualified": "cinder.scene.gltf_spawn.SpawnedGltf",
   "kind": "struct",
   "module": "cinder.scene.gltf_spawn",
   "signature": "struct SpawnedGltf(Movable)",
   "summary": "Result of spawn_gltf: the root entity, the entity of each glTF node and of each mesh primitive, and the renderer ids of the upload. The entities stay in the world after this value is dropped.",
   "url": "/docs/api/scene/#struct-spawnedgltf",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.scene.gltf_spawn.SpawnedGltf.__init__",
   "kind": "method",
   "module": "cinder.scene.gltf_spawn",
   "parent": "SpawnedGltf",
   "signature": "__init__(out self, root: Entity, var uploaded: UploadedGltf)",
   "summary": "",
   "url": "/docs/api/scene/#spawnedgltf-__init__",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "entity_of_node",
   "qualified": "cinder.scene.gltf_spawn.SpawnedGltf.entity_of_node",
   "kind": "method",
   "module": "cinder.scene.gltf_spawn",
   "parent": "SpawnedGltf",
   "signature": "entity_of_node(self, node: Int) -> Entity",
   "summary": "Entity spawned for glTF node node; the null entity for an out-of-range index or a node outside the scene graph.",
   "url": "/docs/api/scene/#spawnedgltf-entity_of_node",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "spawn_gltf",
   "qualified": "cinder.scene.gltf_spawn.spawn_gltf",
   "kind": "def",
   "module": "cinder.scene.gltf_spawn",
   "signature": "def spawn_gltf( mut renderer: Renderer, mut res: Resources, asset: GltfAsset, mut world: World, root_transform: Mat4 = Mat4.identity(), lods: Bool = True, cast_shadows: Bool = True, skinned_meshes: Bool = True, ) raises -> SpawnedGltf",
   "summary": "Uploads the asset and spawns its node hierarchy. Skinned mesh nodes get a MeshRenderer too (the caller attaches an AnimatorRef so the animation system publishes their palette) unless skinned_meshes is False. Every node is spawned at most once, even when the file reaches it twice (a root that is also a child, a node shared by two parents, or a cycle); a node whose glTF parent has not been…",
   "url": "/docs/api/scene/#def-spawn_gltf",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "collision_triangles",
   "qualified": "cinder.scene.gltf_spawn.collision_triangles",
   "kind": "def",
   "module": "cinder.scene.gltf_spawn",
   "signature": "def collision_triangles( asset: GltfAsset, root_transform: Mat4 = Mat4.identity() ) -> Tuple[List[Vec3], List[UInt32]]",
   "summary": "World-space triangles of every non-skinned mesh node, for a static mesh collider.",
   "url": "/docs/api/scene/#def-collision_triangles",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "render_sync",
   "qualified": "cinder.scene.render_sync",
   "kind": "module",
   "module": "cinder.scene.render_sync",
   "signature": "",
   "summary": "Bridge from the ECS world to a RenderScene: render components and their collection. Components: MeshRenderer (renderer mesh and material indices, shadow flag), LightSource, CameraComponent. build_render_scene reads WorldTransform (propagated beforehand) and fills the renderer's scene lists in one pass; it allocates nothing in steady state because the scene's lists are cleared and refilled in…",
   "url": "/docs/api/scene/#cinderscenerender_sync",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "MeshRenderer",
   "qualified": "cinder.scene.render_sync.MeshRenderer",
   "kind": "struct",
   "module": "cinder.scene.render_sync",
   "signature": "struct MeshRenderer(Component)",
   "summary": "Draws renderer mesh mesh with material material at the entity's WorldTransform; cast_shadows is passed to the render instance.",
   "url": "/docs/api/scene/#struct-meshrenderer",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "component_id",
   "qualified": "cinder.scene.render_sync.MeshRenderer.component_id",
   "kind": "method",
   "module": "cinder.scene.render_sync",
   "parent": "MeshRenderer",
   "signature": "component_id() -> Int",
   "summary": "",
   "url": "/docs/api/scene/#meshrenderer-component_id",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "LightSource",
   "qualified": "cinder.scene.render_sync.LightSource",
   "kind": "struct",
   "module": "cinder.scene.render_sync",
   "signature": "struct LightSource(Component)",
   "summary": "A light positioned by the entity's world transform (direction = transform's -Z).",
   "url": "/docs/api/scene/#struct-lightsource",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "component_id",
   "qualified": "cinder.scene.render_sync.LightSource.component_id",
   "kind": "method",
   "module": "cinder.scene.render_sync",
   "parent": "LightSource",
   "signature": "component_id() -> Int",
   "summary": "",
   "url": "/docs/api/scene/#lightsource-component_id",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "CameraComponent",
   "qualified": "cinder.scene.render_sync.CameraComponent",
   "kind": "struct",
   "module": "cinder.scene.render_sync",
   "signature": "struct CameraComponent(Component)",
   "summary": "A camera at the entity's world transform, looking down its -Z with its +Y up. RenderBridge.build uses the first active one it finds, keeping the scene camera's current aspect ratio.",
   "url": "/docs/api/scene/#struct-cameracomponent",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "component_id",
   "qualified": "cinder.scene.render_sync.CameraComponent.component_id",
   "kind": "method",
   "module": "cinder.scene.render_sync",
   "parent": "CameraComponent",
   "signature": "component_id() -> Int",
   "summary": "",
   "url": "/docs/api/scene/#cameracomponent-component_id",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "JointPalette",
   "qualified": "cinder.scene.render_sync.JointPalette",
   "kind": "struct",
   "module": "cinder.scene.render_sync",
   "signature": "struct JointPalette(Component)",
   "summary": "Skinning matrices and morph weights for an entity's mesh, written by the animation system each frame and consumed by build_render_scene.",
   "url": "/docs/api/scene/#struct-jointpalette",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "component_id",
   "qualified": "cinder.scene.render_sync.JointPalette.component_id",
   "kind": "method",
   "module": "cinder.scene.render_sync",
   "parent": "JointPalette",
   "signature": "component_id() -> Int",
   "summary": "",
   "url": "/docs/api/scene/#jointpalette-component_id",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "RenderBridge",
   "qualified": "cinder.scene.render_sync.RenderBridge",
   "kind": "struct",
   "module": "cinder.scene.render_sync",
   "signature": "struct RenderBridge(Movable)",
   "summary": "ECS -> RenderScene with persistent query specs and chunk scratch (no steady-state allocations). build_render_scene is a convenience wrapper around a temporary instance.",
   "url": "/docs/api/scene/#struct-renderbridge",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.scene.render_sync.RenderBridge.__init__",
   "kind": "method",
   "module": "cinder.scene.render_sync",
   "parent": "RenderBridge",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/scene/#renderbridge-__init__",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "build",
   "qualified": "cinder.scene.render_sync.RenderBridge.build",
   "kind": "method",
   "module": "cinder.scene.render_sync",
   "parent": "RenderBridge",
   "signature": "build(mut self, world: World, mut scene: RenderScene) raises -> Int",
   "summary": "Fills scene.instances, scene.joints and scene.lights from the world and sets the camera from the first active CameraComponent. Returns the number of instances.",
   "url": "/docs/api/scene/#renderbridge-build",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "build_render_scene",
   "qualified": "cinder.scene.render_sync.build_render_scene",
   "kind": "def",
   "module": "cinder.scene.render_sync",
   "signature": "def build_render_scene(world: World, mut scene: RenderScene) raises -> Int",
   "summary": "One-off bridge build (tests); the App keeps a RenderBridge.",
   "url": "/docs/api/scene/#def-build_render_scene",
   "md": "/docs/api/scene.md"
  },
  {
   "name": "tools",
   "qualified": "cinder.tools",
   "kind": "module",
   "module": "cinder.tools",
   "signature": "",
   "summary": "Developer tools: the ImGui debug overlay (frame graph, inspector, assets, render graph, log).",
   "url": "/docs/api/tools/#cindertools-1",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "cstrings",
   "qualified": "cinder.tools.cstrings",
   "kind": "module",
   "module": "cinder.tools.cstrings",
   "signature": "",
   "summary": "Frame-scoped C strings for immediate-mode UI calls. ImGui keeps label pointers only until the frame is rendered, and Mojo Strings move when a list grows (inline small-string storage), so labels are copied into List[UInt8] buffers whose heap data stays put. Call clear once per frame after rendering.",
   "url": "/docs/api/tools/#cindertoolscstrings",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "CStrings",
   "qualified": "cinder.tools.cstrings.CStrings",
   "kind": "struct",
   "module": "cinder.tools.cstrings",
   "signature": "struct CStrings(Movable)",
   "summary": "Owns NUL-terminated byte copies of strings handed to C; pointers from c stay valid until clear.",
   "url": "/docs/api/tools/#struct-cstrings",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.tools.cstrings.CStrings.__init__",
   "kind": "method",
   "module": "cinder.tools.cstrings",
   "parent": "CStrings",
   "signature": "__init__(out self)",
   "summary": "",
   "url": "/docs/api/tools/#cstrings-__init__",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "clear",
   "qualified": "cinder.tools.cstrings.CStrings.clear",
   "kind": "method",
   "module": "cinder.tools.cstrings",
   "parent": "CStrings",
   "signature": "clear(mut self)",
   "summary": "Frees every buffer; pointers returned by c become dangling.",
   "url": "/docs/api/tools/#cstrings-clear",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "__len__",
   "qualified": "cinder.tools.cstrings.CStrings.__len__",
   "kind": "method",
   "module": "cinder.tools.cstrings",
   "parent": "CStrings",
   "signature": "__len__(self) -> Int",
   "summary": "",
   "url": "/docs/api/tools/#cstrings-__len__",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "c",
   "qualified": "cinder.tools.cstrings.CStrings.c",
   "kind": "method",
   "module": "cinder.tools.cstrings",
   "parent": "CStrings",
   "signature": "c( mut self, text: String ) -> Optional[Pointer[c_char, MutUntrackedOrigin]]",
   "summary": "A NUL-terminated copy of text, valid until clear.",
   "url": "/docs/api/tools/#cstrings-c",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "debug_ui",
   "qualified": "cinder.tools.debug_ui",
   "kind": "module",
   "module": "cinder.tools.debug_ui",
   "signature": "",
   "summary": "The ImGui debug overlay: frame-time graph and render stats, entity inspector (view and edit components through the scene registry), asset browser, render graph view and log console. ImGui runs through the shim's SDL3 + WebGPU backends (cn_imgui_*); widgets are the generated dcimgui bindings. The overlay draws into the frame's final render pass after the scene.",
   "url": "/docs/api/tools/#cindertoolsdebug_ui",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "DebugUi",
   "qualified": "cinder.tools.debug_ui.DebugUi",
   "kind": "struct",
   "module": "cinder.tools.debug_ui",
   "signature": "struct DebugUi(Movable)",
   "summary": "The ImGui debug overlay. Construction initialises the shim's ImGui backend for the window and device (raising when that fails); destruction shuts it down. App creates it for windowed apps with debug_ui set and declares it first, so it is destroyed before the window and GPU device. Per frame: begin_frame, draw, then render into the final pass.",
   "url": "/docs/api/tools/#struct-debugui",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "__init__",
   "qualified": "cinder.tools.debug_ui.DebugUi.__init__",
   "kind": "method",
   "module": "cinder.tools.debug_ui",
   "parent": "DebugUi",
   "signature": "__init__( out self, lib: NativePtr, window: Optional[Pointer[SDL_Window, MutUntrackedOrigin]], device: WGPUDevice, format: WGPUTextureFormat, ) raises",
   "summary": "",
   "url": "/docs/api/tools/#debugui-__init__",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "begin_frame",
   "qualified": "cinder.tools.debug_ui.DebugUi.begin_frame",
   "kind": "method",
   "module": "cinder.tools.debug_ui",
   "parent": "DebugUi",
   "signature": "begin_frame(mut self, dt_seconds: Float64)",
   "summary": "Records dt_seconds in the frame-time ring, frees the previous frame's labels and starts a new ImGui frame.",
   "url": "/docs/api/tools/#debugui-begin_frame",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "render",
   "qualified": "cinder.tools.debug_ui.DebugUi.render",
   "kind": "method",
   "module": "cinder.tools.debug_ui",
   "parent": "DebugUi",
   "signature": "render(self, pass_: RenderPass)",
   "summary": "Draws the accumulated ImGui data into an open render pass.",
   "url": "/docs/api/tools/#debugui-render",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "wants_mouse",
   "qualified": "cinder.tools.debug_ui.DebugUi.wants_mouse",
   "kind": "method",
   "module": "cinder.tools.debug_ui",
   "parent": "DebugUi",
   "signature": "wants_mouse(self) -> Bool",
   "summary": "True when ImGui wants the mouse (App then keeps mouse events from the input map); False when ImGui has no IO.",
   "url": "/docs/api/tools/#debugui-wants_mouse",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "wants_keyboard",
   "qualified": "cinder.tools.debug_ui.DebugUi.wants_keyboard",
   "kind": "method",
   "module": "cinder.tools.debug_ui",
   "parent": "DebugUi",
   "signature": "wants_keyboard(self) -> Bool",
   "summary": "True when ImGui wants the keyboard (App then keeps key events from the input map); False when ImGui has no IO.",
   "url": "/docs/api/tools/#debugui-wants_keyboard",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "average_frame_ms",
   "qualified": "cinder.tools.debug_ui.DebugUi.average_frame_ms",
   "kind": "method",
   "module": "cinder.tools.debug_ui",
   "parent": "DebugUi",
   "signature": "average_frame_ms(self) -> Float32",
   "summary": "Mean frame time in ms over the recorded frames (at most HISTORY); 0 before the first frame.",
   "url": "/docs/api/tools/#debugui-average_frame_ms",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "draw",
   "qualified": "cinder.tools.debug_ui.DebugUi.draw",
   "kind": "method",
   "module": "cinder.tools.debug_ui",
   "parent": "DebugUi",
   "signature": "draw( mut self, mut world: World, registry: SceneRegistry, renderer: Renderer, assets: Optional[Pointer[AssetServer, MutUntrackedOrigin]], logs: List[LogRecord], physics_live: Int, audio_live: Int, ) raises",
   "summary": "Builds the overlay for this frame (between begin_frame and render).",
   "url": "/docs/api/tools/#debugui-draw",
   "md": "/docs/api/tools.md"
  },
  {
   "name": "select_tab",
   "qualified": "cinder.tools.debug_ui.DebugUi.select_tab",
   "kind": "method",
   "module": "cinder.tools.debug_ui",
   "parent": "DebugUi",
   "signature": "select_tab(mut self, index: Int)",
   "summary": "Makes tab index the active one on the next draw.",
   "url": "/docs/api/tools/#debugui-select_tab",
   "md": "/docs/api/tools.md"
  }
 ]
}