Reference
Cog API
Everything the engine gives a script, in one place. The guides explain how to use it: the language, hooks and events, working with objects and vectors, rotations and colors.
Hooks
The functions the engine calls on a script, each optional. How they fit together: Hooks and events.
| Hook | Called |
|---|---|
on_ready() | Once, when play starts. The place to find other objects and components. The script’s top-level vars were set before this. |
on_update(delta) | Every frame while playing. delta is how long the frame took, in seconds. |
on_destroy() | When the object is destroyed, or play stops. |
on_collision(other, normal) | This object starts touching another with a solid contact. normal points the way this object would have to move to get out. other is a handle to the other object. |
on_collision_exit(other) | They stop touching. |
on_trigger_enter(other) | Something enters this object’s sensor collider. |
on_trigger_exit(other) | It leaves. |
on_ui_click(path) | A button in this object’s Canvas is clicked. |
on_ui_change(path, value) | A slider moves or a text input changes in this object’s Canvas; value is the new value or text. |
on_ui_submit(path, text) | Enter is pressed in a text input in this object’s Canvas. |
Annotations
@component(Name) | What the Inspector and Add Component call the script. |
@category(Name) | Where Add Component lists it. |
@export var name: type = value | A variable shown in the Inspector, set per object: int, float, bool, string, Vec2, Vec3, Color or Rotation. |
@deprecated("note") | Above a function or class: every use is warned about, with the note. |
Objects
self, and the handles from Scene.find, Scene.find_all,
Scene.with_tag, Scene.objects_within, Scene.spawn and a hook’s other.
How to use them: Working with objects.
name, id | The object’s name and its unique number. |
tags, has_tag(tag) | The object’s tags. |
position, rotation, euler_angles | In the world: a Vec3, a Rotation, and its angles in degrees applied Y, then X, then Z. Assign to set: self.position = v. |
local_position, local_rotation, local_euler_angles | Relative to the parent: the numbers the Transform holds and the Inspector shows. Assign to set. For an object with no parent they are the same as the world ones. |
set_position(v), set_rotation(r) | The same as assigning position and rotation. |
velocity, angular_velocity | How fast it is moving and turning, as Vec3s, from its Rigid Body or Character Controller. |
grounded | Whether a Character Controller is standing on something. |
get_component(name) | The component’s properties and actions. An error when the object has none. |
try_get_component(name) | The same, or null. |
set_property(type, property, value) | Sets any component property, by the component’s type name and the property’s script name. See Components. |
send(handler, args...) | Calls a function on the object’s scripts. A name nothing there has is a warning in the Console, once. |
after(seconds, callback, args...) | Calls callback (a function, or a handler’s name) once, later. Gives back an id. |
every(seconds, callback) | Calls callback repeatedly. Gives back an id. |
cancel(id) | Stops a timer. Timers fire before on_update, in the order they were set. |
Components are named without spaces: "RigidBody", "CharacterController",
"Collider", "Renderer", "Animator", "Camera", "Script",
"ParticleEmitter".
Changes are applied at the end of the frame, all together, so reading a value
straight after setting it in the same frame still gives the old one. For the
same reason one part of a transform property can’t be set on its own yet:
self.position.x = 5 is an error that says to set the whole value.
Component actions
What get_component(name) gives you can do. The actions are the component’s,
not self’s: an object without a Rigid Body has nothing to push.
| Component | Action | Does |
|---|---|---|
"RigidBody" | set_velocity(v), set_angular_velocity(v) | Sets the speed outright. |
"RigidBody" | apply_force(v), apply_torque(v) | Pushes for the next physics step only: call every frame for a steady push. |
"RigidBody" | apply_impulse(v), apply_torque_impulse(v) | A kick: changes the velocity at once. |
"RigidBody" | set_gravity(scale) | Scales gravity for this body. |
"CharacterController" | set_velocity(v) | Sets its velocity; call every frame. |
"CharacterController" | set_gravity(scale) | Scales gravity for this character. |
"Animator" | play(state) | Plays the named state. |
"ParticleEmitter" | emit(count) | Throws out count particles now, playing or not. |
"ParticleEmitter" | play() | Starts emitting. On a non-looping emitter, starts its duration and burst over. |
"ParticleEmitter" | stop() | Stops emitting; what is alive finishes. |
"ParticleEmitter" | clear() | Removes every live particle at once. |
Like every change a script makes, these take effect on the next frame.
Scene
Scene.find(name) | The first object with that name, or null. |
Scene.find_all(name) | Every object with that name. |
Scene.with_tag(tag) | Every object with the tag. |
Scene.objects_within(position, radius) | Every other object within reach. |
Scene.raycast(from, direction, max_distance) | { point, distance, object, id } for the nearest collider hit, or null. point is a Vec3. |
Scene.spawn(prefab, position) | Places a prefab, by address. Gives back its handle. |
Scene.destroy() | Removes this object, at the end of the frame. |
Scene.canvas(name) | The Canvas on the object with that name, below. |
Scene.restart() | Starts this scene over, after this frame. |
Scene.load(scene) | Changes to another scene, by address. |
Canvas
From Scene.canvas(name). Elements are named by path: "menu/start".
set_text(path, text) | Sets a label’s or button’s text. |
set_visible(path, visible) | Shows or hides an element. |
set_enabled(path, enabled) | Enables or disables an element. |
set(path, property, value) | Sets any property of an element. |
get(path, property) | What an element shows now. |
Input
Input.axis(action) | -1 to 1, from an axis action. |
Input.held(name) | Down this frame. |
Input.pressed(name) | Went down this frame. |
Input.released(name) | Came up this frame. |
Input.mouse_position() | The pointer, in pixels from the top left of the game, as a Vec2. |
Input.mouse_delta() | How far the mouse moved this frame, as a Vec2. Use it for a mouse-look camera. |
name is an action, a key ("Space", "R") or a mouse button
("MouseLeft"). See Input.
Camera, Time and Engine
Camera.forward, Camera.right | The active camera’s directions, as Vec3s. |
Time.delta | This frame’s length, in seconds. |
Time.elapsed | Seconds since play started. |
Time.frame | Frames since play started. |
Engine.quit() | Ends the game. In the editor, stops play. |
Engine.max_fps, Engine.set_max_fps(n) | The frame-rate cap; 0 is none. |
Save
Progress, in slots. How to use it: Saving data.
Save.write(slot, value) | Keeps any value (object, list, number, text, true/false, null, Vec2, Vec3, Rotation, Color) in a slot, replacing what was there. Gives nothing back; a failed write is an error naming the file and the reason. |
Save.read(slot) | The value as it was written (a Vec3 is a Vec3, a whole number stays whole), or null when the slot is empty. |
Save.exists(slot) | Whether the slot has a save. |
Save.delete(slot) | Removes the slot and its backup. A slot that is not there is already gone. |
Save.list() | [{ name, saved_at }], newest first; saved_at is seconds since 1970. |
A slot name is plain text such as "slot1": not empty, with no slashes, no dots
and none of the characters : * ? " < > |. Anything else is an error that says
so. A slot is the file user://saves/<slot>.json. A value that cannot be saved
(a function, an object in the world, a number that is not a number) is an error
naming where in the value it is, such as the value at .items[1].f.
Save.set, get, has, remove, load, and Save.write without a value
are the old store’s calls. They still work and warn; see
Moving from the old Save.
Settings
What the player prefers, kept apart from saves. How to use it: Saving data.
Settings.set(key, value) | Keeps any value Save can hold. Written to disk by the end of the frame, and when the game ends. Setting what is already there writes nothing. |
Settings.get(key, default) | The value, or default (null when it is left out) when none is set. A list or object is a copy. |
Settings.has(key) | Whether a value is set. |
Settings.remove(key) | Forgets it. A key that is not there is already forgotten. |
The settings are the file user://settings.json. The key cannot be empty.
File
Files of your own, by address. How to use it: Files.
A path outside the two places below is an error that says what is allowed, and
a failed write or a refused path is thrown, so try and catch can take it.
| Address | |
|---|---|
user://... | This game’s folder: read and write. |
assets://... | The game’s own files: read only. |
File.read_all_text(path) | The file’s text, or null when there is no file. A file that is not text is an error. |
File.write_all_text(path, text) | Writes the text, making folders as needed. user:// only. |
File.read_json(path) | The value in a JSON file (a whole number is an int), or null when there is no file. A user file that does not parse is read from its backup. |
File.write_json(path, value) | Writes the value as JSON. user:// only. |
File.exists(path) | Whether there is a file. A folder is not one. |
File.delete(path) | Deletes a file and the backup beside it. A file that is not there is already gone; a folder is an error. user:// only. |
File.list(folder) | The names in a folder, sorted; a folder’s ends in /. A folder that is not there is empty. On assets:// the names come from the project’s asset list, the same in the editor and the built game. |
A path is user:// or assets:// and then names separated by /. These are
refused: an empty part (//), . and .., backslashes, #, a name ending in
a dot or a space, a character that cannot be in a file name on every computer
(: * ? " < > | or a control character), and the names Windows reserves for
devices (CON, NUL, COM1 and the like).
File.write_json writes plain JSON. A Vec3 is {"x", "y", "z"}, a Vec2
{"x", "y"}, a Color {"r", "g", "b", "a"} (0 to 1) and a Rotation its
quaternion {"x", "y", "z", "w"}. None reads back as its type; Save is for
that.
log
log.info(...), log.warn(...), log.error(...) write to the Console.
math
math.pi | |
sqrt, abs, floor, ceil, round, pow, exp, sign | |
log(x), log(x, base) | |
min(...), max(...) | Of any number of numbers. |
clamp(x, lo, hi) | |
lerp(a, b, t) | Numbers. |
sin, cos, tan, asin, acos, atan2 | Radians. |
random(), random(lo, hi) | |
length(v), distance(a, b), normalize(v), dot(a, b), cross(a, b) | Deprecated: a vector does these itself, v.length, a.distance(b), v.normalized, a.dot(b), a.cross(b). |
Every built-in function says what it takes when given the wrong number of
arguments: math.sqrt takes 1 argument, got 2.
Values
int(x), float(x), str(x) | Conversions. |
range(n), range(a, b), range(a, b, step) | Numbers for a for loop. |
Vec3 and Vec2
How to use them: Vectors, rotations and colors. All four types are values: assigning one copies it.
Vec3(x, y, z), Vec2(x, y) | Makes one. |
v.x, v.y, v.z | Its numbers; v.x = 3 changes v. |
Vec3.up, down, left, right, forward, back | One unit along each axis. forward is -Z, the way a camera looks. Vec2 has none. |
Vec3.zero, Vec3.one, Vec2.zero, Vec2.one | |
v.length | How long it is. |
v.normalized | The same direction, one unit long. Zero stays zero. |
v.dot(w) | |
v.cross(w) | Vec3 only. |
v.distance(w) | How far apart two points are. |
v.move_toward(target, step) | step closer to target, never past it. |
Vec3.lerp(a, b, t), Vec2.lerp(a, b, t) | t of the way from a to b. |
+, -, * n, / n, -v, == | Between vectors, and with a number. Two vectors don’t multiply: use dot or cross. == is exact: to ask whether two points are close, compare a.distance(b) with a distance. |
vec3(x, y, z) | Deprecated: Vec3(x, y, z). |
Rotation
Rotation.from_euler(x, y, z), Rotation.from_euler(v) | From angles in degrees, applied Y, then X, then Z: the numbers the Inspector shows. |
Rotation.from_axis_angle(axis, degrees) | A turn about an axis. |
Rotation.look_toward(forward, up) | Facing forward, with its top toward up (Vec3.up when left out). |
Rotation.from_to(a, b) | The turn that takes direction a to direction b. |
Rotation.from_quaternion(x, y, z, w) | From a quaternion’s four numbers. There is no bare Rotation(...): four numbers that look like angles aren’t a rotation, and the error says which constructor to use. |
Rotation.identity | No turn. |
r.euler_angles | Its angles in degrees, as a Vec3. |
r.axis, r.angle | The axis it turns about, and how far, in degrees. |
r.forward, r.right, r.up | Which way its front, right and top point. |
r.x, r.y, r.z, r.w | Its quaternion. |
r.inverse | The turn back. |
r.slerp(other, t) | t of the way to other. |
r * other, r * v, == | r * other turns by r, then by other; r * v turns the vector v. == is exact, and a quaternion equals its negation. |
Color
Channels run from 0 to 1, as a color picker shows them.
Color.from_rgb(r, g, b), Color.from_rgba(r, g, b, a) | Channels from 0 to 1. |
Color.from_bytes(r, g, b), Color.from_bytes(r, g, b, a) | Channels from 0 to 255. |
Color.from_hex(text) | "#rrggbb", "#rrggbbaa" or "#rgb". |
Color.from_hsv(hue, saturation, value), with an optional alpha | Hue in degrees, the others 0 to 1. |
Color.white, Color.black, Color.clear | clear is fully transparent. There is no bare Color(...). |
c.r, c.g, c.b, c.a | Its channels; c.a = 0.5 changes c. |
c.bytes, c.hex, c.hue, c.saturation, c.value | The same color the other ways. |
Color.lerp(a, b, t) | t of the way from a to b. |
+, -, *, / n, == | * takes a color (a tint) or a number. |
Where the types come from
self.position, self.local_position | Vec3 |
self.rotation, self.local_rotation | Rotation |
self.euler_angles, self.local_euler_angles | Vec3, degrees |
self.velocity, self.angular_velocity | Vec3 |
Camera.forward, Camera.right | Vec3 |
Input.mouse_position(), Input.mouse_delta() | Vec2 |
A raycast’s point | Vec3 |
| A component’s color property | Color |
An @export can be any of the four: @export var tint: Color = Color.white
shows a color picker in the Inspector.
Text
s.len(), s.length, s.upper(), s.lower(), s.trim(),
s.contains(part), s.starts_with(part), s.ends_with(part),
s.replace(from, to), s.split(sep), s.substring(start, end). Each is
also string.name(s, ...): string.len(s).
Arrays
a.length, a.push(x), a.pop(), a.contains(x), a.index_of(x) (-1 when
it isn’t there), a.remove(x), a.map(f), a.filter(f), a.copy().
Objects
o.keys(), o.values() (in key order), o.has(key), o.copy().