Scripting with Cog

Vectors, rotations and colors

Positions, directions, turns and colors each have a type: Vec3, Vec2, Rotation and Color. Each is made through its type’s name and reads back through its fields. Every constructor, field and operator is listed in the Cog API reference.

They’re values, like numbers: assigning one copies it.

var a = Vec3(1, 2, 3)
var b = a
b.x = 10            // a is still (1, 2, 3)

== compares exactly, as it does for numbers. To ask whether two positions are close, compare the distance between them: a.distance(b) < 0.1.

Vec3

A point or a direction in 3D. Vec3.up, down, left, right, forward and back are one unit along each axis (forward is -Z, the way a camera looks).

var up = Vec3(0, 1, 0)
var p = self.position + up * 2.0
var to_player = (Scene.find("Player").position - p).normalized
var how_far = p.distance(Scene.find("Player").position)

+ and - work between vectors, * and / with a number, and -v turns one around. Two vectors don’t multiply: use dot or cross, whichever you mean. normalized gives the same direction one unit long, move_toward goes step closer to a target without passing it, and Vec3.lerp(a, b, t) is t of the way from a to b.

Vec2

The same in 2D, without cross or named directions. The mouse reads as one: Input.mouse_delta().x.

Rotation

A way to face. Make one from whatever you know about it:

var face_right = Rotation.from_euler(0, 90, 0)            // degrees
var tilted = Rotation.from_axis_angle(Vec3.right, 30)     // 30 degrees about X
var at_target = Rotation.look_toward(Vec3(1, 0, 1))       // face a direction
var level = Rotation.identity                             // no turn at all

from_euler takes angles in degrees, applied Y, then X, then Z: the numbers the Inspector shows. And read it back the same ways: r.euler_angles, r.forward, r.right, r.up, r.axis and r.angle.

r * other turns by r, then by other; r * v turns the vector v.

Color

Channels from 0 to 1, as a color picker shows them.

var gold = Color.from_hex("#ffcc00")
var faded = Color.from_rgba(1, 1, 1, 0.5)
var dim = gold * 0.5
self.set_property("PointLightComponent", "color", gold)

Make one from channels (from_rgb, from_rgba), bytes from 0 to 255 (from_bytes), a hex string (from_hex) or hue, saturation and value (from_hsv), and read it back any of those ways (c.bytes, c.hex, c.hue). + and - work between colors, * with a color (a tint) or a number, and / with a number.

Where they come from

Positions, directions and angles come from objects (self.position, self.euler_angles, self.velocity) and the camera (Camera.forward); the mouse is a Vec2; a component’s color property is a Color. The reference’s table of where the types come from has them all.

An @export can be any of the four: @export var tint: Color = Color.white shows a color picker in the Inspector.