Skip to main content

Asset registry (assets.yaml)

The asset registry gives your game's resources names: images, sounds, fonts, materials, sprite animations, actors and data files. Your code and other data files refer to assets by these names instead of by file path, and ctgame uses the registry to know which files to ship.

By default the game loads data/assets.yaml. Set paths.asset_registry in game.json to use another file.

Example​

images:
- name: ship
path: images/ship.png
- name: ship_normal
path: images/ship-normal.png
srgb: false
mipmaps: true

sounds:
- name: laser
path: audio/laser.ogg

fonts:
- name: body
package: data/fonts/body.ctfont
- name: hud
atlas: images/fonts/hud-msdf.png
metrics: data/fonts/hud-msdf.json

materials:
- name: hull
system: pbr
mipmaps: true
textures:
- name: albedo
image: ship
- name: normal
image: ship_normal
- name: roughness
color: [0.6, 0.6, 0.6]
parameters:
- name: normal_strength
value: 1

animations:
- name: ship_flight
image: ship
clips:
- origin: [0, 0]
frame_size: [100, 100]
count: 3
duration: 0.06
loop: once

actors:
- name: PlayerShip
path: data/actors/PlayerShip.yaml

files:
- name: scene
path: data/scene.yaml
- name: tuning
path: data/tuning.yaml
- name: muzzle_flash
path: data/effects/muzzle_flash.effect

Paths are relative to the folder containing game.json, not to the registry file. Write the folder as part of each path. Absolute paths work when you run the game locally but can't be exported.

Top-level fields​

FieldTypeDescription
formatmapOptional file format version; see File format versions.
imageslistPNG textures.
soundslistSound effects and music.
fontslistFonts for text.
shaderslistNames for shaders built into the game.
materialslistHow meshes and sprites are shaded.
animationslistSprite-sheet animations.
actorslistActor definitions.
fileslistAny other data file: scenes, tuning, effects, your own YAML or JSON.

Every section is optional. Names must be unique within a section (an image and a sound may share a name). Names are case-sensitive. Unknown keys are ignored.

images​

FieldTypeDefaultDescription
namestring—Required. Asset name.
pathstring—Required. PNG file.
srgbbooltruetrue for color art. Set false for data textures: normal maps, masks, distance fields, lookup tables.
premultiplyboolfalsePremultiply color by alpha when loading.
mipmapsboolsee belowGenerate smaller versions of the image (mipmaps) so it looks smooth when drawn small.
mipmap_levelsinteger 0–160Most mip levels to generate, including the full-size image. 0 means as many as possible; 1 means none.
mipmap_filterauto, color, data or normalautoHow smaller levels are averaged. auto picks normal for images used as a material's normal input, color for sRGB images and data otherwise.

Booleans accept true/yes/1 and false/no/0.

Mipmap policy​

You rarely need to set mipmaps on an image:

  • An image used by a material with mipmaps: true gets mipmaps, using the material's mipmap_levels.
  • An image used by an animation gets mipmaps. Each frame is shrunk on its own, so frames never bleed into each other, and frames never shrink below 4 pixels.
  • Any other image has no mipmaps.

Setting mipmaps or mipmap_levels on the image overrides these defaults. The color filter needs srgb: true; normal needs srgb: false and premultiply: false.

sounds​

FieldTypeDefaultDescription
namestring—Required. Asset name.
pathstring—Required. .wav, .flac or .ogg (Vorbis) file.

fonts​

Give each font either a package, or an atlas and metrics together.

FieldTypeDefaultDescription
namestring—Required. Asset name.
packagestring—A .ctfont file made from TrueType fonts with ctfont-pack. Sharp at any size.
atlasstring—Multi-channel signed distance field (MSDF) atlas PNG. Needs metrics.
metricsstring—The atlas's metrics JSON. Needs atlas.

shaders​

Shaders are compiled into the game. A shaders entry gives one a name that materials and effects can use.

FieldTypeDefaultDescription
namestring—Required. Asset name.
providerstring—Required. Shader to use. Built in: sprite, sprite_gpu_anim, vfx, sprite_pbr, armor, armor_shadow. Games with C code can register their own.

materials​

A material says how a mesh or sprite is shaded: which images or colors it uses and its settings.

FieldTypeDefaultDescription
namestring—Required. Asset name.
systemstring—Required. Render system that draws it, for example pbr or mesh_lit.
shaderstringsystem defaultShader asset name.
cast_shadowsbooltrueObjects with this material cast shadows.
receive_shadowsbooltrueShadows fall on objects with this material.
mipmapsboolfalseGive this material's images mipmaps (unless an image says otherwise).
mipmap_levelsinteger 0–160Default mipmap_levels for this material's images.
textureslistemptyImage inputs; see below.
parameterslistemptyNumeric settings; see below.

textures​

Each texture needs a name and either image or color.

FieldTypeDescription
namestringInput name, defined by the render system: for example albedo, normal, height, metallic, roughness.
imagestringImage asset name.
color[r, g, b] or [r, g, b, a]A flat color instead of an image. Each value 0–1; alpha defaults to 1.

Inputs the render system requires must be present.

parameters​

FieldTypeDescription
namestringSetting name, defined by the render system.
valuenumber or listOne number, or a list of 2–4 numbers, matching the setting. Mesh systems also accept a whole number or 16 numbers (a 4×4 matrix).

animations​

A sprite animation plays frames from a sprite-sheet image.

FieldTypeDefaultDescription
namestring—Required. Asset name.
imagestring—Required. Image asset name (not a path).
clipslist—Required. At least one clip. Code selects clips by position in this list, starting at 0.

clips​

FieldTypeDefaultDescription
origin[x, y][0, 0]Pixel position of the first frame in the image.
frame_size[w, h]—Required. Frame size in pixels.
countinteger—Required. Number of frames.
frames_per_rowintegercountFrames before wrapping to the next row (or column).
horizontalboolfalsetrue: frames run left to right, then wrap down. false: frames run top to bottom, then wrap right.
durationnumber—Required. Seconds per frame.
looploop, once or pingpongloopRepeat, play once and stop, or play back and forth.

All the animations of one image can have at most 100,000 frames in total.

actors​

FieldTypeDescription
namestringRequired. Actor name. Must match the name inside the actor file.
pathstringRequired. The actor file.

Actor files are checked when the game starts, so a broken actor stops the game with an error.

files​

Any other file your game reads. The registry only checks that the file exists; your code decides what's in it.

FieldTypeDescription
namestringRequired. Asset name.
pathstringRequired. The file.

Some names have a meaning to cTurtle:

NameContents
sceneYour main scene. paths.scene in game.json overrides it.
modelsYour procedural models, used by Studio.

Other common entries are effects, motion clips and rigs and tuning data.

Tuning and other data files​

Keep gameplay numbers (speeds, health, HUD spacing) in your own YAML file instead of in code. Register it under files, then decode the part each system needs into a BT object that holds its defaults:

# data/assets.yaml
files:
- name: tuning
path: data/tuning.yaml
# data/tuning.yaml
hud:
bottom_padding: 14
include "cturtle/yaml";

object HudSettings { float bottom_padding; }
object HudTuning { HudSettings hud; }

fn load_hud_tuning() -> HudTuning {
HudTuning tuning = HudTuning { hud: HudSettings { bottom_padding: 10.0 } };
yaml_decode_asset("tuning", tuning)?;
return tuning;
}

Keys missing from the file keep the defaults you set. Each system can decode its own part of the same file. Edits take effect the next time the file is decoded, normally on the next launch. Registered files are exported automatically.

Per-actor values (an enemy's weapons or health) belong in its actor file instead.

Reading assets from BT​

To getCall
An imagerenderImageGet("ship")
A soundaudioSound("laser")
A file or actor file, decoded into an objectyaml_decode_asset(name, target), yaml_decode_asset_defaults(name, target, defaults), json_decode_asset(name, target)
A file or actor file, as a YAML documentyaml_parse_asset(name)

See cturtle/yaml, cturtle/render and cturtle/audio. A data file can be at most 64 MiB.

YAML rules​

The registry, scenes and actor files support common YAML, with these limits:

  • Use indentation for maps and - item for lists. Lists of numbers can be written inline: [1, 2, 3]. Inline maps ({ a: 1 }) aren't supported.
  • Every value fits on one line. No multi-line strings, anchors, aliases, tags or multiple documents in one file.
  • # starts a comment.
  • A line or value can be at most 255 characters. A key can be at most 63 characters, and keys can nest at most 16 levels deep.

Exported builds​

ctgame ships the registry and every file it names. It also converts each image to a .ktx2 file, with its mipmaps, which loads faster than a PNG. See Packaging.

Errors​

Errors stop the game at startup and look like asset registry '<path>': <message>.

MessageWhat to do
assets.yaml: `version: 1` is no longer usedDelete the version line (an older file).
assets.yaml uses format version X; this cTurtle reads format …The file was written for a newer cTurtle; see File format versions.
image N requires non-empty name and path (also sound, file, actor)Entry number N is missing a field.
duplicate image asset 'X' (also other types)Two entries share a name, possibly one in game.json assets.
font N requires exactly package or atlas plus metricsUse either package, or atlas and metrics.
'images.N' mipmap_levels must be 0..16Fix the level count.
'materials.N' uses mipmap_filter on a material; set it on each imageMove mipmap_filter to the images.
image 'X' color mipmap_filter requires srgb / normal mipmap_filter requires srgb: falseThe filter doesn't match the image's srgb.
image 'X' is used as both normal and non-normal map; set mipmap_filter explicitlySet mipmap_filter on that image.
image 'X' has conflicting material mipmap_levelsTwo materials want different levels; set mipmap_levels on the image.
material 'X' texture N requires a name and exactly one of image or colorFix the texture entry.
material 'X' texture 'Y' color must be normalizedColor values must be 0–1.
animation 'X' requires at least one clip, clip N requires positive frame_size (or count, duration)Fix the clip.
animation 'X' clip N has unknown loop mode 'Y'Use loop, once or pingpong.
material asset 'X' references unavailable mesh system 'Y'Unknown system.
material asset 'X' has unknown texture input 'Y' for system 'Z' (or unknown parameter, invalid value for parameter)The render system has no such input, or the value has the wrong number of components.
material asset 'X' is missing required texture input 'Y'Add the input.
material asset 'X' references unknown image 'Y' (also animation asset)Register the image first.
could not prepare image asset 'X' from 'P'The PNG is missing or unreadable.
could not register file asset 'X' from 'P'The file doesn't exist.
actor asset 'X' contains actor named 'Y'Make the registry name match the actor file's name.
UI-only asset registries may contain images, sounds, files, actors, and fonts, ...UI-only apps (such as those run with bt-ui) can't use shaders, materials or animations.

See also​