BGE
Static Methods
sphereOverlap(
centerA: BGE.Math.Vector,
radiusA: float,
centerB: BGE.Math.Vector,
radiusB: float,
): BGE.Sphere3dCollisionResult
True 3D sphere-sphere overlap test - the narrow-phase check after the two-plane broad-phase gate, since two spheres can pass both plane checks while never actually touching in 3D (a diagonal near-miss - see the design doc's spike findings).
Parameters
centerA(BGE.Math.Vector)radiusA(float)centerB(BGE.Math.Vector)radiusB(float)
Returns
aabbOverlap(
minA: BGE.Math.Vector,
maxA: BGE.Math.Vector,
minB: BGE.Math.Vector,
maxB: BGE.Math.Vector,
): BGE.Box3dCollisionResult
True 3D AABB-vs-AABB overlap test. Unlike sphereOverlap(), the two-plane broad-phase gate has no false-positive case for boxes (AABB overlap decomposes exactly per axis) - this only computes the penetration/normal result.
Parameters
minA(BGE.Math.Vector)maxA(BGE.Math.Vector)minB(BGE.Math.Vector)maxB(BGE.Math.Vector)
Returns
sphereBoxOverlap(
sphereCenter: BGE.Math.Vector,
radius: float,
boxMin: BGE.Math.Vector,
boxMax: BGE.Math.Vector,
): BGE.Sphere3dCollisionResult
True 3D sphere-vs-AABB overlap test - the only cross-shape pair this engine's 3D collision system supports.
Parameters
sphereCenter(BGE.Math.Vector)radius(float)boxMin(BGE.Math.Vector)boxMax(BGE.Math.Vector)
Returns
BGE.Sphere3dCollisionResult— normal points away from the box, toward the sphere
intersectRaySphere(
origin: BGE.Math.Vector,
direction: BGE.Math.Vector,
maxDistance: float,
center: BGE.Math.Vector,
radius: float,
): BGE.RaycastHit
Ray-vs-sphere intersection (the true 3D case; intersectRayCircle() is the 2D specialization below). Returns the nearest intersection point along the ray within [0, maxDistance], or invalid if the ray misses, points away from the sphere, or the sphere is entirely beyond maxDistance. direction must already be a unit vector - the returned distance is only meaningful in the same units as direction's magnitude. If origin is already inside the sphere, returns a hit at distance: 0/point: origin (an arbitrary normal, since there's no entry face) rather than invalid or the far exit point - same convention as intersectRayAabb3d().
Parameters
origin(BGE.Math.Vector)direction(BGE.Math.Vector) — must be a unit vectormaxDistance(float)center(BGE.Math.Vector)radius(float)
Returns
intersectRayCircle(
origin: BGE.Math.Vector,
direction: BGE.Math.Vector,
maxDistance: float,
center: BGE.Math.Vector,
radius: float,
): BGE.RaycastHit
Ray-vs-circle intersection in the XY plane - z is ignored entirely on both the ray and the circle, by flattening both to z=0 and delegating to intersectRaySphere().
intersectRaySphere()'s math assumes a unit-length direction. Simply zeroing out z (as this used to do) leaves the flattened direction shorter than 1 whenever the original direction had a nonzero z component, silently breaking that assumption. So this renormalizes the flattened direction and rescales maxDistance/distance to compensate: letting len = the flattened direction's own length, a step of t along the original unit direction covers t * len of flat (XY-only) distance, so the flat search runs out to maxDistance * len and the flat hit's distance is converted back with / len.
Parameters
origin(BGE.Math.Vector)direction(BGE.Math.Vector) — must be a unit vectormaxDistance(float)center(BGE.Math.Vector)radius(float)
Returns
intersectRayAabb3d(
origin: BGE.Math.Vector,
direction: BGE.Math.Vector,
maxDistance: float,
minPoint: BGE.Math.Vector,
maxPoint: BGE.Math.Vector,
): BGE.RaycastHit
Ray-vs-axis-aligned-box intersection via the classic slab method (Kay/Kajiya): each axis narrows [tMin, tMax] to the interval where the ray is within that axis' [lo, hi] slab; if the interval ever becomes empty, the ray misses. The entry face's outward normal is tracked as whichever axis last raised tMin.
Parameters
origin(BGE.Math.Vector)direction(BGE.Math.Vector) — must be a unit vectormaxDistance(float)minPoint(BGE.Math.Vector)maxPoint(BGE.Math.Vector)
Returns
intersectRayAabb2d(
origin: BGE.Math.Vector,
direction: BGE.Math.Vector,
maxDistance: float,
minPoint: BGE.Math.Vector,
maxPoint: BGE.Math.Vector,
): BGE.RaycastHit
Ray-vs-axis-aligned-rectangle intersection in the XY plane - z is ignored entirely, by flattening the ray to z=0 and widening the box's z-range so the z-axis slab test in intersectRayAabb3d() never constrains the result.
See intersectRayCircle()'s doc comment for why the flattened direction must be renormalized (and maxDistance/distance rescaled to compensate) rather than just zeroing z - the same reasoning applies here.
Parameters
origin(BGE.Math.Vector)direction(BGE.Math.Vector) — must be a unit vectormaxDistance(float)minPoint(BGE.Math.Vector)maxPoint(BGE.Math.Vector)
Returns
resolveAabbTileCollision(
positionBefore: BGE.Math.Vector,
currentPosition: BGE.Math.Vector,
width: float,
height: float,
velocity: BGE.Math.Vector,
tileCollider: BGE.RectangleCollider,
isOneWay?: boolean,
tolerancePx?: float,
): BGE.TileCollisionResult
Resolves an entity's axis-aligned hitbox against one static rectangular tile collider, using the entity's pre-move position to determine which side it approached from - the generic "solid tile world" resolution algorithm (landing on top, one-way-platform pass-through, head bumps, side pushes) needed by a tile-based platformer or top-down game's GameEntity.onCollision(). It does not replace BGE.Collider/CheckMultipleCollisions() for entity-vs-entity collision - use it only for collisions against static tile geometry.
A resolved position leaves the entity exactly flush against the tile, touching but not overlapping it, so onCollision() won't fire for that tile again next frame unless the entity moves back into it (e.g. under gravity). See GameEntity.onCollision().
The entity's own hitbox is assumed feet-anchored, matching GameEntity.addRectangleCollider()'s own convention: positionBefore is the bottom- center point (x = horizontal center, y = bottom edge), so the hitbox spans positionBefore.x -+ width/2 horizontally and positionBefore.y to positionBefore.y + height vertically.
Precondition: only call this when the entity's current (post-move) position is already known to overlap this tile - e.g. from inside onCollision(), which only fires on a genuine overlap. This function has no independent way to verify an overlap actually exists (it trusts positionBefore/currentPosition/velocity at face value); called with values that were never actually approaching/touching, its returned side is not meaningful (this mirrors the exact same precondition the hand-rolled onCollision() logic it replaces already had, implicitly, by virtue of only ever running inside onCollision()).
Parameters
positionBefore(BGE.Math.Vector) — the entity's position as of the start of this frame, before this frame's own movement was applied (capture it at the top of onUpdate(), before integrating velocity) - used to tell which side of the tile the entity approached from.currentPosition(BGE.Math.Vector) — the entity's actual position right now (at the moment onCollision() fires) - this is what gets returned unchanged on the axis that isn't resolved this call, and as the base every resolved axis's correction is applied on top of. Do NOT pass positionBefore here - by the time onCollision() runs, the engine has already integrated this frame's velocity into the entity's position (see Game.bs's processEntitiesPreDraw -> processEntitiesCollisions ordering), so currentPosition and positionBefore are genuinely different values whenever the entity moved at all this frame.width(float) — the entity's hitbox width (matching the width passed to addRectangleCollider())height(float) — the entity's hitbox heightvelocity(BGE.Math.Vector) — the entity's current velocity (only .y's sign matters for landing/head-bump detection)tileCollider(BGE.RectangleCollider) — the tile's own collider (the otherCollider passed to onCollision()), whose offset is the tile's top-left corner in world space, e.g. addRectangleCollider(tileName, TileSize, TileSize, leftX, topY)isOneWay(boolean, optional, default: false) — true if this tile only blocks a from-above landing and passes through from below/the sides (e.g. a one-way platform)tolerancePx(float, optional, default: "1.0") — how many pixels of overlap/gap still count as "touching" a side, absorbing floating-point/frame-step slack
Returns
newFullHeightParallaxLayer(
owner: BGE.GameEntity,
region: roRegion,
canvasWidth: float,
canvasHeight: float,
factor: float,
targetX?: float,
targetY?: float,
zOffset?: float,
): BGE.DrawableParallaxLayer
Builds a DrawableParallaxLayer scaled to fill the canvas vertically edge-to-edge and tiled to cover it on both axes, with its tile-repeat seam anchored at a chosen canvas position (targetX, targetY) rather than wherever computeEffectiveWorldPosition()'s own reference-position capture would otherwise put it - see that method's own derivation comment, and examples/platformer's MainScene for a worked application (including staggering several stacked layers' seams via different targetX values so they don't all reinforce into one obvious seam).
This assumes owner sits at world (0,0,0) and the camera's target on the axis orthogonal to factor's own drift direction stays fixed for the object's lifetime (e.g. a side-scroller with a Y-locked camera) - it is not a general-purpose "anchor anywhere under any camera motion" solution. See examples/parallax's own hand-rolled newLayer() for a different derivation (owner co-located with a moving camera target, non-uniform per-axis factor) that this helper does not cover.
Note: this function deliberately lives in its own file, separate from DrawableParallaxLayer.bs - a namespace-level free function whose return type self-references a class defined in the SAME file triggers a real BrighterScript compiler bug (confirmed via bisection: a trivial return invalid body with the same signature still fails, and changing only the return type to as object "fixes" it - the trigger is the self-referential return type, not this function's body). Keeping it in a separate file (importing DrawableParallaxLayer.bs) avoids the bug entirely while keeping full type fidelity on the return type.
Parameters
owner(BGE.GameEntity) — the entity this layer attaches to; must sit at world (0,0,0)region(roRegion) — the bitmap tile to scroll/repeatcanvasWidth(float)canvasHeight(float)factor(float) — parallaxFactor applied uniformly to both axes - must be nonzero; a fully camera-pinned layer (factor = 0) is not supported by this helper's offset math (it would divide by zero).targetX(float, optional, default: "0.0") — on-canvas X the tile seam lands at while the camera sits at canvasWidth/2 (its assumed rest position on this axis)targetY(float, optional, default: "0.0") — on-canvas Y the tile seam lands at, given the camera's fixed Y target (canvasHeight/2 is the common "camera always centers vertically" case)zOffset(float, optional, default: "0.0") — Z offset for this layer, useful for stacking several layers' draw order via BGE.DrawableParallaxLayer's normal Z-based sort
Returns
getRenderQualityModelPrefix(model: string): string
The model-code prefix used to look a device up: everything up to the first "X" after the leading 3-4 characters (e.g. "3941X2" -> "3941", "C000GB" -> "C000", "K8PXX" -> "K8P"), or the first four characters when there is no "X".
Parameters
model(string) —roDeviceInfo.GetModel()
Returns
string
seedRenderQualityLevel(
model: string,
graphicsPlatform: string,
uiResolutionName: string,
isSimulator: boolean,
): RenderQualityLevel
Starting quality level for a device. Pure - seedRenderQualityLevelForDevice() calls this with the real device's values.
Parameters
model(string) —roDeviceInfo.GetModel(), e.g. "4850X"graphicsPlatform(string) —roDeviceInfo.GetGraphicsPlatform(), "opengl" or "directfb"uiResolutionName(string) —roDeviceInfo.GetUIResolution().name: "SD", "HD" or "FHD"isSimulator(boolean) — whether this is the BrightScript simulator
Returns
RenderQualityLevel— aBGE.RenderQualityLevelvalue
seedRenderQualityLevelForDevice(): RenderQualityLevel
Reads this device's model, graphics platform and resolution and returns its starting quality level. Game calls this for you.
Returns
RenderQualityLevel— aBGE.RenderQualityLevelvalue
getRenderQualityModelTable(): roAssociativeArray
Known model prefixes -> level, from developer.roku.com/dev/docs/hardware ("Current" and "Updatable" models). Add or correct entries as real benchmark data comes in.
Returns
roAssociativeArray
lookUpRenderQualityModel(prefix: string): integer
Table lookup with inference for unknown codes; -1 when nothing fits.
Parameters
prefix(string)
Returns
integer
isRenderQualityNumericCode(code: string): boolean
"4850", "3941": four digits
Parameters
code(string)
Returns
boolean
isRenderQualityTvCode(code: string): boolean
"M000", "K8P": a letter followed by a digit
Parameters
code(string)
Returns
boolean
getRenderQualityLevelName(level: integer): string
Display name for a quality level, e.g. "High".
Parameters
level(integer) — aBGE.RenderQualityLevelvalue
Returns
string
clampRenderQualityLevel(level: integer): RenderQualityLevel
Clamps any integer into the valid BGE.RenderQualityLevel range.
Parameters
level(integer)
Returns
getRenderQualityPreset(level: integer): RenderQualitySettings
The engine's built-in settings for a quality level, as a new copy each call.
Parameters
level(integer) — aBGE.RenderQualityLevelvalue (clamped)
Returns
mergeRenderQualitySettings(
base: BGE.RenderQualitySettings,
overrides: BGE.RenderQualitySettingsOverrides,
): RenderQualitySettings
Copies base, replacing each field named in overrides. Keys that aren't quality settings are ignored.
Parameters
base(BGE.RenderQualitySettings)overrides(BGE.RenderQualitySettingsOverrides) — e.g. {planeSliceCount: 80}
Returns
getNewMemoryScratchRegion(
width: float,
height: float,
): ScratchRegion
Parameters
width(float)height(float)
Returns
isBackFaceDrawMode(drawMode: SceneObjectDrawMode): boolean
Parameters
drawMode(SceneObjectDrawMode)
Returns
boolean
isDirectDrawMode(drawMode: SceneObjectDrawMode): boolean
Parameters
drawMode(SceneObjectDrawMode)
Returns
boolean
isOrientedDrawMode(drawMode: SceneObjectDrawMode): boolean
Parameters
drawMode(SceneObjectDrawMode)
Returns
boolean
isScreenAlignedDrawMode(drawMode: SceneObjectDrawMode): boolean
The draw modes that keep an object square to the screen rather than turning it in 3D - the billboard modes. directScaled belongs here even though isOrientedDrawMode groups it with the oriented modes: it faces the camera like directToCamera and only differs in taking its size from how far away it is (a Doom-style sprite).
Parameters
drawMode(SceneObjectDrawMode)
Returns
boolean
isWireFrameDrawMode(drawMode: SceneObjectDrawMode): boolean
Parameters
drawMode(SceneObjectDrawMode)
Returns
boolean
isSolidDrawMode(drawMode: SceneObjectDrawMode): boolean
Parameters
drawMode(SceneObjectDrawMode)
Returns
boolean
isFullDrawMode(drawMode: SceneObjectDrawMode): boolean
Parameters
drawMode(SceneObjectDrawMode)
Returns
boolean
getDrawModeName(drawMode: SceneObjectDrawMode): string
The name of a draw mode, as written in the SceneObjectDrawMode enum - handy for debug overlays and for examples that let you cycle through the draw modes.
Parameters
drawMode(SceneObjectDrawMode)
Returns
string— the mode's name, or "unknown" for a value outside the enum
getDrawModeBooleanLookupArray(
defaultValue?: boolean,
): Array.<boolean>
Parameters
defaultValue(boolean, optional, default: false)
Returns
Array.<boolean>
getDotProductFromSurfaceToCamera(
rendererObj: BGE.Renderer,
facePoint: BGE.Math.Vector,
faceNormal: BGE.Math.Vector,
): float
Parameters
rendererObj(BGE.Renderer)facePoint(BGE.Math.Vector)faceNormal(BGE.Math.Vector)
Returns
float
isNormalFacingCamera(
rendererObj: BGE.Renderer,
facePoint: BGE.Math.Vector,
faceNormal: BGE.Math.Vector,
): boolean
Parameters
rendererObj(BGE.Renderer)facePoint(BGE.Math.Vector)faceNormal(BGE.Math.Vector)
Returns
boolean
HSVtoRGBA(
hPercent: float,
sPercent: float,
vPercent: float,
a?: integer,
): integer
Parameters
hPercent(float)sPercent(float)vPercent(float)a(integer, optional, default: -1)
Returns
integer
RGBAtoRGBA(
red: integer,
green: integer,
blue: integer,
alpha?: float,
): integer
Parameters
red(integer)green(integer)blue(integer)alpha(float, optional, default: 1)
Returns
integer
unpackRGB(rgb: integer): roAssociativeArray
Unpacks a packed RGB color (0xRRGGBB) into its R/G/B channels.
Parameters
rgb(integer)
Returns
roAssociativeArray— {r, g, b}, each 0-255
unpackRGBA(rgba: integer): roAssociativeArray
Unpacks a packed RGBA color (0xRRGGBBAA) into its R/G/B/A channels.
Parameters
rgba(integer)
Returns
roAssociativeArray— {r, g, b, a}, each 0-255
GetColor(name: string): integer
Looks up a BGE.Colors value by name (case-insensitive). Falls back to White for a name that isn't a known color.
Parameters
name(string)
Returns
integer
GetColorRGB(name: string): integer
Looks up a BGE.ColorsRGB value by name (case-insensitive). Falls back to White for a name that isn't a known color.
Parameters
name(string)
Returns
integer
getRandomColorRGB(
r?: integer,
g?: integer,
b?: integer,
): integer
A random color as a packed RGB integer (0xRRGGBB, no alpha byte) - the format Drawable.color/Drawable.outlineRGBA expect. Use getRandomColorRGBA for the packed-RGBA format the Renderer.draw* calls take.
Parameters
r(integer, optional, default: 255) — exclusive upper bound for the red channelg(integer, optional, default: 255) — exclusive upper bound for the green channelb(integer, optional, default: 255) — exclusive upper bound for the blue channel
Returns
integer— packed RGB color
getRandomColorRGBA(
r?: integer,
g?: integer,
b?: integer,
a?: integer,
): integer
Parameters
r(integer, optional, default: 255)g(integer, optional, default: 255)b(integer, optional, default: 255)a(integer, optional, default: 255)
Returns
integer
colorBrightness(rgba: integer, brightness: float): integer
Parameters
rgba(integer)brightness(float)
Returns
integer
colorOpacity(rgba: integer, opacity: float): integer
Parameters
rgba(integer)opacity(float)
Returns
integer
lerpColorRGB(
colorA: integer,
colorB: integer,
t: float,
): integer
Linearly interpolates between two packed RGB colors (0xRRGGBB), channel-wise.
Parameters
colorA(integer) — start color, packed RGB (returned at t=0)colorB(integer) — end color, packed RGB (returned at t=1)t(float) — interpolation factor, clamped to 0-1
Returns
integer— the interpolated packed RGB color
getControlEventKind(
controlCode: integer,
charCode: integer,
): BGE.ControlEventKind
Tells a remote button event apart from a character typed on a keyboard (e.g. the Roku mobile app's keyboard). A typed character arrives as its own press and release events, and its code can collide with a button code ("d" is 100, the same as a Back release), so check this before treating an event as a button.
Parameters
controlCode(integer) — the event's GetInt()charCode(integer) — the event's GetChar()
Returns
getDeviceRenderTier(): DeviceRenderTier
Determines this device's render tier via roDeviceInfo.
Not cached internally - CreateObject("roDeviceInfo") plus one or two native calls is cheap enough for the common case (called once, e.g. from a constructor), and this can't change at runtime. A call site that needs to avoid repeating the check across many calls (e.g. once per frame) should cache the returned value itself, the same way Camera3d.getMaxDrawDistanceDeviceCap() already caches its derived cap in an instance field.
Returns
registryWrite(
registry_section: string,
key: string,
value: dynamic,
): void
Parameters
registry_section(string)key(string)value(dynamic)
Returns
void
registryRead(
registry_section: string,
key: string,
default_value?: dynamic,
): dynamic
Parameters
registry_section(string)key(string)default_value(dynamic, optional, default: "invalid")
Returns
dynamic
getNumberOfLinesInAString(text: string): integer
Gets the number of lines in a string by counting the newlines
Parameters
text(string)
Returns
integer
lastInStr(text: string, substring: string): integer
Finds the index of the last time a substring appears in a string
Parameters
text(string)substring(string)
Returns
integer
numberToFixed(num: float, precision: integer): string
Given a float number, returns the number with a fixed numbers of decimals as a string
Parameters
num(float)precision(integer)
Returns
string
arrayToStr(things: Array.<dynamic>): string
Parameters
things(Array.<dynamic>)
Returns
string
stringToFloat(input: string): float
Parameters
input(string)
Returns
float
TexturePacker_GetRegions(
atlas: dynamic,
bitmap: ifDraw2d,
): roAssociativeArray
TODO: figure this out... is useful for sprites with different size frames
Parameters
atlas(dynamic)bitmap(ifDraw2d)
Returns
roAssociativeArray
sliceGridRegions(
bitmap: ifDraw2d,
cellWidth: integer,
cellHeight: integer,
): Array.<roRegion>
Slices a bitmap into a row-major grid of cellWidth x cellHeight roRegions.
Parameters
bitmap(ifDraw2d)cellWidth(integer)cellHeight(integer)
Returns
Array.<roRegion>
ArrayInsert(
array: Array.<dynamic>,
index: integer,
value: dynamic,
): Array.<dynamic>
Parameters
array(Array.<dynamic>)index(integer)value(dynamic)
Returns
Array.<dynamic>
DrawCircleOutline(
draw2d: ifDraw2d,
line_count: integer,
x: float,
y: float,
radius: float,
rgba: integer,
): void
Parameters
draw2d(ifDraw2d)line_count(integer)x(float)y(float)radius(float)rgba(integer)
Returns
void
DrawRectangleOutline(
draw2d: ifDraw2d,
x: float,
y: float,
width: float,
height: float,
rgba: integer,
): void
Parameters
draw2d(ifDraw2d)x(float)y(float)width(float)height(float)rgba(integer)
Returns
void
isValidEntity(entity: EntityWithId): boolean
Parameters
entity(EntityWithId)
Returns
boolean
buttonNameFromCode(buttonCode: integer): string
Parameters
buttonCode(integer)
Returns
string
buttonAliasToName(buttonName: string): string
Resolves a button name or common alias to the (lowercased) BGE canonical button name, e.g. for use with GameInput.isButton(). Unrecognized names are returned lowercased, unchanged, so a caller checking a name BGE doesn't know about still gets consistent case-insensitive behavior. A gamepad's "a"/"b" face buttons alias to "ok"/"back" here too (A = confirm, B = cancel) - isButton() resolves both sides of its comparison through this table, so an "ok"/"back" check matches a gamepad's A/B press with no extra binding needed.
Parameters
buttonName(string) — a button name or alias (case insensitive)
Returns
string
cloneArray(original?: Array.<dynamic>): Array.<dynamic>
Clone an array (shallow)
Parameters
original(Array.<dynamic>, optional, default: "[]") — the original array to be clones
Returns
Array.<dynamic>— A shallow copy of the original array
pointArraysEqual(
a?: Array.<PositionXY>,
b?: Array.<PositionXY>,
): boolean
Check if two arrays of points are teh same - that is, if each point, in order has same x and y values
Parameters
a(Array.<PositionXY>, optional, default: "[]") — the first arrayb(Array.<PositionXY>, optional, default: "[]") — the second array
Returns
boolean— true if both arrays have same number of points and x and y values are the same for each point
isTrue(value: dynamic): boolean
Parameters
value(dynamic)
Returns
boolean
bytesToInteger(
bytes: Array.<integer> | roByteArray,
offset?: integer,
isLittleEndian?: boolean,
): integer
Parameters
bytes(Array.<integer> | roByteArray)offset(integer, optional, default: 0)isLittleEndian(boolean, optional, default: true)
Returns
integer
bytesToFloat(
bytes: Array.<integer> | roByteArray,
offset?: integer,
isLittleEndian?: boolean,
): float
Parameters
bytes(Array.<integer> | roByteArray)offset(integer, optional, default: 0)isLittleEndian(boolean, optional, default: true)
Returns
float
hexStringToByteArray(hex: string): roByteArray
Decodes a hex-encoded string (e.g. from roEVPDigest.Process()) into its raw bytes. Processes hex characters in pairs; an odd-length input's trailing character is decoded as a single nibble (left-padded with implicit zero).
Parameters
hex(string)
Returns
roByteArray
subArray(
array: ifArray,
startIndex: integer,
length: integer,
): roArray
Parameters
array(ifArray)startIndex(integer)length(integer)
Returns
roArray
decToHex(dec: integer): string
Parameters
dec(integer)
Returns
string
Enums
.TweenApplyMode
How a managed tween writes its interpolated value onto its target - internal, not part of the public API. "fields" is what to()/addManagedTween() uses for plain named-field targets; the color variants repack channels back into a single packed int instead.
Properties
fields(default: "fields")colorRGB(default: "colorRGB")colorRGBA(default: "colorRGBA")
.TileCollisionSide
Which side of the tile (if any) resolveAabbTileCollision() resolved a collision against. "none" means the tile didn't block the entity at all this frame (e.g. rising through a one-way platform, or no overlap).
Properties
none(default: "none")top(default: "top")bottom(default: "bottom")left(default: "left")right(default: "right")
.ParticleShape
The shape drawn for every particle spawned by a DrawableParticles emitter.
Properties
Line(default: "line")Rectangle(default: "rectangle")Image(default: "image")
.PlaneFillMode
Which of the three composable ways a DrawablePlane fills its surface:
- color: a flat fill using the drawable's own
color/alphafields, no texture at all. Never "runs out" - the natural base/backdrop layer under the other two. - tiledImage:
regionis treated as a single repeating tile, seamlessly covering the world-space footprint bounded by the camera'smaxDrawDistance. - staticImage:
regionis a one-off finite decal anchored at the plane's own world position (today's only historical behavior) - correct for e.g. a map texture, wrong for anything meant to repeat.
Multiple DrawablePlanes (in any mix of modes) can be layered on the same entity or scene via separate addDrawable() calls - draw order for planes at the same depth follows insertion order (SceneObject's existing depth-sort tie-break), so add the base layer (e.g. a color plane) first.
Properties
color(default: "color")tiledImage(default: "tiledImage")staticImage(default: "staticImage")
.SpritePlayMode
Properties
Loop(default: "loop")Forward(default: "forward")Reverse(default: "reverse")PingPong(default: "pingpong")
.RenderQualityLevel
Render quality levels, from cheapest to best-looking. See Game.renderQuality, Game.setQualityLevel() and Game.enableAdaptiveQuality().
Properties
basic(default: 0)low(default: 1)medium(default: 2)high(default: 3)ultra(default: 4)
.CameraFrustumSide
Properties
top(default: "top")bottom(default: "bottom")left(default: "left")right(default: "right")near(default: "near")
.SceneObjectType
Properties
Line(default: "Line")Rectangle(default: "Rectangle")Text(default: "Text")Bitmap(default: "Bitmap")Polygon(default: "Polygon")Billboard(default: "Billboard")Model(default: "Model")Plane(default: "Plane")ParallaxLayer(default: "ParallaxLayer")Circle(default: "Circle")Particle(default: "Particle")Skybox(default: "Skybox")
.SceneObjectDrawMode
Properties
matchCamera(default: 0) — Rotations are ignoreddirectToCamera(default: 1) — Do not orient in 3d spacedirectScaled(default: 2) — Do not orient in 3d space, but scale in relation to distance from cameraoriented(default: 3) — Orient in 3d spaceorientedDrawBackFace(default: 4) — Orient the object, and draw any back faceswireFrame(default: 5) — Just draw a wire framewireFrameDrawBackFace(default: 6) — Just draw a wire frame, including back facessolid(default: 7) — Draw a solid polygonsolidDrawBackFace(default: 8) — Draw a solid polygon, including back faces
.Colors
Named colors as packed RGBA integers (0xRRGGBBAA), fully opaque. Values match RGBAtoRGBA(r, g, b) for the same named color.
Properties
Black(default: 255)White(default: 4294967295)Red(default: 4278190335)Lime(default: 16711935)Blue(default: 65535)Yellow(default: 4294902015)Cyan(default: 16777215)Aqua(default: 16777215)Magenta(default: 4278255615)Pink(default: 4278255615)Fuchsia(default: 4278255615)Silver(default: 3233857791)Gray(default: 2155905279)Grey(default: 2155905279)Maroon(default: 2147483903)Olive(default: 2155872511)Green(default: 8388863)Purple(default: 2147516671)Teal(default: 8421631)Navy(default: 33023)
.ColorsRGB
Named colors as packed RGB integers (0xRRGGBB, no alpha byte) - the same values as BGE.Colors, right-shifted by 8.
Properties
Black(default: 0)White(default: 16777215)Red(default: 16711680)Lime(default: 65280)Blue(default: 255)Yellow(default: 16776960)Cyan(default: 65535)Aqua(default: 65535)Magenta(default: 16711935)Pink(default: 16711935)Fuchsia(default: 16711935)Silver(default: 12632256)Gray(default: 8421504)Grey(default: 8421504)Maroon(default: 8388608)Olive(default: 8421376)Green(default: 32768)Purple(default: 8388736)Teal(default: 32896)Navy(default: 128)
.ControlEventKind
What a roUniversalControlEvent represents - see getControlEventKind().
Properties
button(default: "button")charPress(default: "charPress")charRelease(default: "charRelease")
.DeviceRenderTier
Roku hardware performance tier, derived from roDeviceInfo. Every device-tiered branch in the engine (scratch bitmap sizing, low-end draw-quality checks, texture size caps, far-clip distance caps) should switch on this instead of independently re-deriving it from HasFeature("simulation_engine")/GetUIResolution().name.
Properties
simulator(default: "simulator")sd(default: "SD")hd(default: "HD")fhd(default: "FHD")
Other
Canvas
Contains a roku roBitmap which all game objects get drawn to.
Parameters
gameEngine(Game)canvasWidth(integer) — width of canvascanvasHeight(integer) — height of canvasoptions(RendererOptions, optional, default: "{useBitmapPooling: true}")
Properties
bitmap(ifDraw2D) — bitmap GameEntity images get drawn tooffset(BGE.Math.Vector) — Position offset from screen coordinates (z value ignored)scale(BGE.Math.Vector) — Scale (z value ignored)renderer(Renderer) — Renderer for this canvasrendererOptions(RendererOptions)
Returns
Game
Main Game Engine class which runs everything The main game loop is as follows:
- Update - For each GameEntity:
- Process Input from roku remote
- Process Audio Events (https://developer.roku.com/en-ca/docs/references/brightscript/events/roaudioplayerevent.md)
- Process ECP input (https://developer.roku.com/en-ca/docs/developer-program/debugging/external-control-api.md)
- Process URL events (https://developer.roku.com/en-ca/docs/references/brightscript/events/rourlevent.md)
- Runs the Entity's onUpdate() function
- Moves Entity based on velocity
- Collisions - For each GameEntity:
- Run Entity's onPreCollision() function
- For any collisions, runs Entity's onCollision() function
- Runs entity's onPostCollision() function (At any time, the Entity in question may Delete() itself. Before every entity interaction, the entity is checked to make sure it is still valid in case it was deleted in the last interaction)
- Draw - For each GameEntity, sorted by zIndex
- Runs the Entity onDrawBegin() function
- For each drawable in the Entity, run the draw() function
- Run the Entity onDrawEnd() function
-
Draw all debug items in game space (e.g. colliders, screen safe zones, etc).
-
UI - For the tree of widgets in the UI Container
- Run onUpdate()
- Run draw()
- Debug UI - Draw all debug windows in the tree of the Debug UI
Parameters
canvasWidth(integer) — Width of the canvas the game is drawn tocanvasHeight(integer) — Height of the canvas the game is drawn touiWidth(integer, optional, default: 0) — Width of the UI canvas - if 0, will be same as screenuiHeight(integer, optional, default: 0) — Height of the UI canvas - if 0, will be same as screen
Properties
sortedEntities(Array.<GameEntity>)compositor(roCompositor)screen(roScreen)canvas(BGE.Canvas)uiCanvas(BGE.Canvas)dummyScreen(roScreen)renderQuality(BGE.RenderQualityManager) — The game's render quality level and presets - seesetQualityLevel(),currentScene(GameScene) — The scene currently in playcurrentSceneArgs(object) — The args passed to changeScene() for the current sceneEntities(object) — All of the GameEntities by name => => GameEntityStatics(object) — All static variables for a given object typeScenes(object) — The scene definitions by name (see defineScene())Interfaces(object) — The interface definitions by nameBitmaps(object) — The loaded bitmaps by nameSounds(object) — The loaded sounds by nameFonts(object) — The loaded fonts by nameModels(object) — The loaded Models by nametweenManager(BGE.TweenManager) — Ticks every live tween once per frame and writes interpolated values onto arbitraryscreenFade(BGE.ScreenFade) — Full-screen overlay used by changeSceneWithFade() - see BGE.ScreenFade.gameUi(BGE.UI.UiContainer) — Container for all UIdebugUi(BGE.UI.UiContainer) — Container for Debug UIfocusManager(BGE.UI.FocusManager) — The single, global focused-widget/cursor state shared by gameUi and anydefaultTheme(BGE.UI.Theme) — Default theme for all UI widgets, set in new()uiFocusSoundKey(string) — Default Game.loadSound() keys played by every BGE.UI.Button on focus/click (seeuiClickSoundKey(string)controls(BGE.Controller.ControlMap) — Unified remote+controller input mapping - see enableControllerInput()
Returns
GameEntity
Every thing (character, player, object, etc) in the game should extend this class. This class has a number of empty methods that are designed to be overridden in subclasses. For example, override onInput() to handle input event, and onUpdate() to handle updating each frame
Parameters
game(Game) — The game engine that this entity is going to be assigned togameEngine(Game)args(roAssociativeArray, optional, default: "{}") — Any extra properties to be added to this entity
Properties
name(string) — Constant - name of this Entityid(string | dynamic) — Constant - Unique Idgame(Game)enabled(boolean) — Is this GameEntity enabledpersistent(boolean) — Does this entity persist across scene changes?pauseable(boolean) — When the game is paused, does this entity pause too?isStatic(boolean) — Marks this entity's drawables as static geometry (walls, props) that never movesposition(dynamic) — position of where this entity is in game worldvelocity(dynamic) — Speed of this entity, in units/second (not units/frame) - added to position each frame scaled by elapsed timerotation(dynamic) — Rotation of entity - applies to all imagesscale(dynamic) — Scale of entity - applies to all imagescolliders(roAssociativeArray) — The colliders for this entity by namedrawables(Array.<Drawable>) — The array of drawables to draw for this entitydrawablesByName(roAssociativeArray) — Associative array of drawables by nametagsList(dynamic) — Game Entities can be tagged with any number of tags so they can be easily identified (e.g. "enemy", "wall", etc.)transformationMatrix(dynamic) — The Current Transformation MatrixmotionChecker(MotionChecker)isDying(boolean) — True once invalidateAfter() has been called - lets game code (collisiondyingTimer(GameTimer) — Timer/delay backing invalidateAfter()'s grace period. Public (rather thandyingDelayMs(integer)
Returns
CONTROLLER_BUTTON_CODE_PRESS_BASE
Numeric bands for controller-originated buttonCodes (see BGE.Controller. ControllerRegistry/Game.drainControllerInput, which construct these) - deliberately far above the remote's own 0-99 (press) / 100-999 (release) / 1000+ (held) ranges (see the button-code table below) so a controller event's code can never be misclassified as a remote one. A controller button's identity is a name, not a code (see explicitButtonName below) - these bands exist only to classify press/release/held, so every controller-originated GameInput uses the band's base value as-is.
Default: 100000
CONTROLLER_BUTTON_CODE_RELEASE_BASE
Default: 200000
CONTROLLER_BUTTON_CODE_HELD_BASE
Default: 300000
GameInput
Class that contains all information about the current input during a given frame from the remote
Parameters
buttonCode(integer) — button to use for the dataheldTimeMs(integer) — how long was this button held forplayerIndex(integer, optional, default: -1) — the assigned player index for this input's source (remote, simulator gamepad, or browser controller); -1 only if none was resolvedexplicitButtonName(string, optional, default: "invalid") — overrides buttonNameFromCode, used for controller buttons
Properties
button(string) — The name of the button associated with the current inputbuttonCode(integer) — The code for the inputpress(boolean) — Was the button pressed since the last frameheld(boolean) — Was the button held down since last framerelease(boolean) — Was the button released this frameheldTimeMs(integer) — How many milliseconds was the current input held forplayerIndex(integer) — Which remote/gamepad/controller this input came from. Every physicalconsumed(boolean) — Set by a UiWidget/UiContainer that acted on this event - once set, thex(float) — Current horizontal directional input: left -> -1, right -> 1y(float) — Current vertical directional input, in world space (+y is up, matching
Returns
Example
' -------Button Code Reference--------
' Button Pressed Released Held
' ------------------------------
' Back 0 100 1000
' Up 2 102 1002
' Down 3 103 1003
' Left 4 104 1004
' Right 5 105 1005
' OK 6 106 1006
' Replay 7 107 1007
' Rewind 8 108 1008
' FastForward 9 109 1009
' Options 10 110 1010
' Play 13 113 1013GameScene
Extends: GameEntity
A GameScene is a GameEntity that represents one distinct state of your game - a title screen, a menu, a level. Register scenes with Game.defineScene() and switch between them with Game.changeScene(). Only one GameScene is current at a time, and it gets the same per-frame hooks (onUpdate, onInput, ...) as any other entity.
Every scene change destroys all non-persistent entities, including "changing" to the current scene again with Game.resetScene(). When changing to a different scene, the outgoing scene's own drawables (anything added with addDrawable()/addImage()/etc. directly on the scene) are removed too, by this class's default onChangeScene(). On a resetScene() the scene's own drawables are left in place, since onCreate() runs again immediately and typically re-adds everything.
To keep some or all of a scene's own drawables across a change:
- set
persistDrawablesAcrossSceneChange = trueto keep all of them, or - override
onChangeScene()with your own cleanup. An override replaces the default cleanup unless it callssuper.onChangeScene(newScene).
Parameters
gameEngine(Game)args(roAssociativeArray, optional, default: "{}")
Properties
persistDrawablesAcrossSceneChange(boolean) — Whether this scene's own directly-added drawables survive a change to a different
Returns
GameTimer
Wrapper for Roku's roTimeSpan that allows time adjustment
Returns
ScreenFade
A full-screen colour overlay drawn on top of the game and its UI, faded in or out over time. Game owns one (game.screenFade) and drives it for Game.changeSceneWithFade(); you can also call fadeTo() on it directly, e.g. to dim the screen behind a pause menu.
Properties
color(integer) — Overlay colour, packed RGB (0xRRGGBB)opacity(float) — 0 = invisible, 1 = fully covers the screen
MAX_FADE_STEP_SECONDS
Longest dt a single ScreenFade.tick() counts (one frame at 30fps) A literal, not 1.0 / 30.0 - the docs plugin can only emit literal const values.
Default: 0.0333333
ManagedTween
One tween TweenManager is tracking - internal bookkeeping, not part of the public API a consumer touches directly (that's to()/toColorRGB()/toColorRGBA()/cancel()).
Properties
tweenObj(BGE.Tweens.TweenObject)target(object) — The object setAnchor()-style consumers pass to to()/toColorRGB()/toColorRGBA() -applyMode(TweenApplyMode)fieldName(string) — Only set (to the field on target holding the packed color) when applyMode isowner(BGE.GameEntity) — The GameEntity to validate every tick via isValidEntity(), or invalid for a tweenonComplete(function) — Called once, with this tween's own target, when it retires - see to()'s doc for whyloopMode(BGE.Tweens.TweenLoopMode)delayMs(integer)delayTimer(BGE.GameTimer) — Only non-invalid while a nonzero delay hasn't elapsed yet.originalStart(roAssociativeArray) — The tween's original start/dest fields, before any pingPong ChangeTweenDest() callsoriginalDest(roAssociativeArray)pingPongForwardNext(boolean)
TweenManager
Ticks every live tween once per frame (see Game.tweenManager) and writes interpolated values straight onto arbitrary target object fields - no manual per-frame HandleTween() bookkeeping required. Wraps BGE.Tweens.CreateTweenObject()/HandleTween() per managed tween rather than reimplementing interpolation.
BoxCollider3d
Extends: Collider
A collider with the shape of an axis-aligned box CENTERED at (offset.x, offset.y, offset.z), with given width (x), height (y), depth (z). Note this offset convention is center-based, not RectangleCollider's own corner-based convention (see RectangleCollider's class doc) - deliberately simpler, since BoxCollider3d's own 3D math (aabbOverlap()) has no reason to inherit RectangleCollider's screen-space corner convention.
Internally, this owns two ordinary RectangleColliders for broad-phase - one tracking the entity's real (x, y) plane, one tracking a synthetic (y, z) "YZ plane", flagged with COLLIDER_3D_YZ_PLANE_FLAG the same way SphereCollider3d's internal colliders are (see that class's doc comment for why). Unlike SphereCollider3d, this two-plane broad phase has NO false-positive case for boxes - AABB overlap decomposes exactly per axis, so a pair that passes both plane checks is always a genuine 3D overlap. confirmCollision() still runs aabbOverlap(), but only to compute the penetration/normal result for physics response, not to reject anything. See specs/2026-09-18-3d-collision-detection-design.md.
Parameters
colliderName(string) — name of this colliderargs(roAssociativeArray, optional, default: "{}") — additional properties (e.g {width: 10, height: 20, depth: 10})
Properties
width(float) — Full extent of the box along each axis (this is a full width/height/depth, not a half-extent)height(float)depth(float)lastCollisionResult(Box3dCollisionResult) — The most recent confirmCollision() result, readable from onCollision() to compute a
Returns
CircleCollider
Extends: Collider
Collider with the shape of a circle centered at (offset.x, offset.y), with given radius
Parameters
colliderName(string) — name of this colliderargs(roAssociativeArray, optional, default: "{}") — additional properties (e.g {radius: 10})
Properties
radius(integer) — Radius of the collider
Returns
Collider
Colliders are attached to GameEntities and when two colliders intersect, it triggers the onCollision() method in the GameEntity
Parameters
colliderName(string) — the name this collider will be identified byargs(roAssociativeArray, optional, default: "{}") — additional properties to be added to this collider
Properties
colliderType(string) — The type of this collider - should be defined in sub classes (eg. "circle", "rectangle")name(string) — Name this collider will be identified byenabled(boolean) — Does this collider trigger onCollision() ?offset(BGE.Math.Vector) — Offset from the GameEntity it is attached tomemberFlags(integer) — Bitflag for collision detection: this collider is in this group - https://developer.roku.com/en-ca/docs/references/brightscript/interfaces/ifsprite.md#setmemberflagsflags-as-integer-as-voidcollidableFlags(integer) — Bitflag for collision detection: this collider will only collider with colliders in this group - https://developer.roku.com/en-ca/docs/references/brightscript/interfaces/ifsprite.md#setcollidableflagsflags-as-integer-as-voidcompositorObject(roSprite) — Used internal to Game - should not be modified manuallycontacts(roAssociativeArray) — Used internal to Game - should not be modified manually. Colliders overlapped last frame,tagsList(dynamic) — Colliders can be tagged with any number of tags so they can be easily identified (e.g. "enemy", "wall", etc.)
Returns
COLLIDER_3D_YZ_PLANE_FLAG
Reserved member/collidable flag bit for SphereCollider3d/BoxCollider3d's internal YZ-plane colliders, which share a roCompositor with ordinary 2D colliders - without this, a YZ-plane collider (positioned at entity.y/z, not a real screen position) could spuriously match a 2D collider whose (x, y) happens to coincide numerically. Avoid this bit when choosing custom memberFlags/collidableFlags. See specs/2026-09-18-3d-collision-detection-design.md.
Default: 1073741824
Sphere3dCollisionResult
The result of sphereOverlap(): whether two spheres truly overlap in 3D, and if so, the contact normal (points away from centerB, toward centerA) and how far they're currently penetrating along that normal.
Parameters
overlapping(boolean)normal(BGE.Math.Vector)penetrationDepth(float)
Properties
overlapping(boolean)normal(BGE.Math.Vector)penetrationDepth(float)
Returns
Box3dCollisionResult
The result of aabbOverlap(): whether two axis-aligned boxes truly overlap, and if so, the contact normal (along whichever axis has the least overlap, away from box B and toward box A) and the penetration depth along that axis.
Parameters
overlapping(boolean)normal(BGE.Math.Vector)penetrationDepth(float)
Properties
overlapping(boolean)normal(BGE.Math.Vector)penetrationDepth(float)
Returns
RAY_EPSILON
Below this magnitude, a ray's direction component along an axis is treated as exactly zero (parallel to that axis' slab) rather than risking a division by a near-zero value in intersectRayAabb3d()'s slab test.
Default: 0.000001
RaycastHit
The result of a raycast hitting a collider - see Game.raycast()/raycastAll(). Pure data, so it's an interface rather than a class (no instantiation cost).
Properties
entity(GameEntity)collider(Collider)point(BGE.Math.Vector)distance(float)normal(BGE.Math.Vector)
RectangleCollider
Extends: Collider
Collider with the shape of a rectangle, width x height, whose top-left corner is at (offset.x, offset.y) from the entity's position. World +y is up, so the rectangle spans offset.x to offset.x + width, and offset.y - height to offset.y.
Parameters
colliderName(string) — name of this colliderargs(roAssociativeArray, optional, default: "{}") — additional properties (e.g {width: 10, height: 20})
Properties
width(float)height(float)
Returns
SlideOptions
Extends: roAssociativeArray
Options for BGE.SolidWorld.moveAndSlide().
Properties
cornerNudge(float) — How far (px) a box moving along one axis may clip a corner and still be eased around it.maxStep(float) — Longest single sub-step (px), so a fast move can't skip over a thin solid. Default 4.
SlideResult
Result of BGE.SolidWorld.moveAndSlide().
Properties
x(float) — New bottom-left x of the moving boxy(float) — New bottom-left y of the moving boxblockedX(boolean) — True if a solid stopped movement along xblockedY(boolean) — True if a solid stopped movement along y
SolidWorldSolid
One solid rectangle in a BGE.SolidWorld.
Properties
x(float) — Bottom-left xy(float) — Bottom-left yw(float)h(float)id(string) — Unique within its SolidWorld
SolidWorld
A set of static, axis-aligned solid rectangles for top-down movement (walls, water, prop bases), and moveAndSlide() to move a box through them: it stops flush against solids, slides along walls, and eases around corners it only just clips.
Every rectangle is {x, y, w, h} - (x, y) is the bottom-left corner, world +y up. This is plain rectangle maths, separate from colliders: colliders report overlaps, while a SolidWorld keeps a mover out of them. For platformer tiles (including one-way platforms) see BGE.resolveAabbTileCollision() instead.
Parameters
bucketSize(integer, optional, default: 128) — solids are grouped in square cells this size (px), so a move only tests nearby solids. Roughly the size of a typical solid works well. 0 or less uses the default.
Returns
Example
world = new BGE.SolidWorld()
world.addBounds(0, 0, mapWidth, mapHeight)
world.addSolid(64, 64, 32, 32)
' Each frame, move the player's feet box:
result = world.moveAndSlide({x: feetX, y: feetY, w: 20, h: 12}, dx, dy)
feetX = result.x
feetY = result.ySphereCollider3d
Extends: Collider
A collider with the shape of a sphere centered at (offset.x, offset.y, offset.z) with given radius, that detects a true 3D overlap - not just an XY-space projection.
Internally, this owns two ordinary CircleColliders for broad-phase: one tracking the entity's real (x, y) - the same XY plane every other 2D Collider uses - and one tracking a synthetic (y, z) "YZ plane", flagged with COLLIDER_3D_YZ_PLANE_FLAG so it can only ever match another YZ-plane collider (both register against the same roCompositor as ordinary 2D colliders, so without this flag a YZ-plane collider could spuriously match an unrelated 2D collider at the same numeric (x, y) position). A pair only becomes a broad-phase candidate when it overlaps on BOTH planes - and even then, confirmCollision() runs a true sphere-sphere distance check before accepting it, because two spheres can pass both plane checks while never actually touching in 3D (a diagonal near-miss). See specs/2026-09-18-3d-collision-detection-design.md.
Parameters
colliderName(string) — name of this colliderargs(roAssociativeArray, optional, default: "{}") — additional properties (e.g {radius: 10})
Properties
radius(float) — Radius of the spherelastCollisionResult(Sphere3dCollisionResult) — The most recent confirmCollision() result, readable from onCollision() to compute a
Returns
TileCollisionResult
The result of resolveAabbTileCollision(): the corrected position/velocity to apply this frame, and which side of the tile (if any) was resolved. When side = none, both position and velocity are returned exactly as the currentPosition/velocity inputs were - nothing to apply, safe to write back unconditionally either way.
Parameters
position(BGE.Math.Vector)velocity(BGE.Math.Vector)side(BGE.TileCollisionSide)
Properties
position(BGE.Math.Vector)velocity(BGE.Math.Vector)side(BGE.TileCollisionSide)
Returns
FreeFlyCameraController
A reusable free-fly camera control scheme: yaw/pitch relative to the camera's current (roll-adjusted) orientation, strafe/drive, roll, and a ground-plane clamp so driving forward can't cross the ground. Not a GameEntity - a GameScene (or any owner) constructs one and forwards its own onInput/onUpdate calls to it. Extracted from examples/terrain's original FreeFlyCameraController (issue #148); that example now layers its own scene-switching/debug-toggle/hint-text glue on top of this.
Movement/look are read each frame from a BGE.Controller.ControlMap's move/look axes (see update()), not from onInput() - a connected dual-stick controller drives full strafe+drive / yaw+pitch, and with no real second stick, both axes fall back to the same remote/simulator source, so the single physical d-pad turns and drives exactly as it always has (see update()'s regime check).
Parameters
camera(BGE.Camera3d) — the camera to drivegroundPlane(BGE.Math.Plane) — the plane clampAboveGround() keeps the camera abovecontrols(BGE.Controller.ControlMap) — read each update() for the move/look axesmoveAxis(string, optional, default: "\"move\"") — axis name bound (via controls.bindAxis()) to the left/drive sticklookAxis(string, optional, default: "\"look\"") — axis name bound (via controls.bindAxis()) to the right/look stick
Properties
camera(BGE.Camera3d)groundPlane(BGE.Math.Plane)turnSpeed(float)driveSpeed(integer) — radians/secrollSpeed(integer) — units/secpitchSpeed(float) — degrees/secmaxDownwardTilt(float) — radians/secminHeightAboveGround(float) — radians (~69 degrees)lastInput(BGE.GameInput) — 1 = pitching up, 1 = pitching down, 0 = not pitching
Returns
AnimatedImage
Extends: Image
Parameters
owner(GameEntity)regions(Array.<roRegion>)args(roAssociativeArray, optional, default: "{}")
Properties
index(integer) — The current index of image - this would not normally be changed manually, but if you wanted to stop on a specific image in the spritesheet this could be set.animationDurationMs(float) — The time in milliseconds for a single cycle through the animation to play.animationTween(string) — The name of the tween to use for choosing the next imageregions(Array.<roRegion>) — ------------Never To Be Manually Changed-----------------animationTimer(dynamic)tweensReference(dynamic)
Returns
Drawable
Abstract drawable class - all drawables extend from this
Parameters
owner(GameEntity)args(roAssociativeArray, optional, default: "{}")
Properties
name(string) — -------------Values That Can Be Changed------------offset(dynamic) — The offset of the image from the owner's positionscale(dynamic) — The image scalerotation(dynamic) — Rotation of the imagebanksWithCameraRoll(boolean) — directScaled only (see SceneObjectBillboard.updateCanvasPointsForCameraFacingQuad()):color(integer) — This can be used to tint the image with the provided color if desired. White makes no change to the original image.outlineRGBA(integer) — RGB color for the outline stroke. Leaveinvalidfor no outline at all.outlineWidth(integer) — Thickness of the outline stroke, in pixels. Only used whenoutlineRGBAis set.alpha(float) — Change the image alpha (transparency).enabled(boolean) — Whether or not the image will be drawn.transformationMatrix(dynamic)motionChecker(MotionChecker)shouldRedraw(boolean)geometryVersion(integer) — Bumped every time this drawable's geometry changes in a way theanchor(dynamic) — Normalized anchor point (0-1 on each axis) this drawable pivots around, where (0,0) isanchorIsSet(boolean) — Whether setAnchor() has ever been called. Image consults this to decide whether to keepowner(GameEntity) — The GameEntity this drawable is attached to. May beinvalidfor a drawable usedwidth(float)height(float)sceneObjects(object)noOwnerTransformationMatrix(Array.<Array.<float>>) — Lazily-created identity matrix returned by getOwnerTransformationMatrix() when there's no owner.drawMode(SceneObjectDrawMode)isShaded(boolean)ambientBrightness(float) — The darkest anisShadedsurface is ever allowed to get, as a 0-1 fraction of its
Returns
DrawableCircle
Extends: Drawable
Draws a filled circle via the renderer's shared circle texture (see Renderer.getCircleResource()), with an optional outline stroked as a regular polygon inscribed in the circle's own quad - see SceneObjectCircle.
Like DrawableRectangle, the circle's top left (of its bounding square) sits at the drawable's own world position, extending radius * 2 right and down - so it anchors and composes with the rest of the engine the same way every other drawable does. In the oriented/solid/wireFrame 3D draw modes it foreshortens into an ellipse when viewed at an angle, the same as any other billboard (see DrawableSphere for a circle that never does this).
Parameters
owner(GameEntity)radius(float)args(roAssociativeArray, optional, default: "{}")
Properties
radius(float)outlineSegments(integer) — Regular-polygon segment count used only for the outline - the fill is a texture
Returns
DrawableLine
Extends: Drawable
Parameters
owner(GameEntity)startPos(BGE.Math.Vector)endPos(BGE.Math.Vector)args(roAssociativeArray, optional, default: "{}")
Properties
startPosition(BGE.Math.Vector)endPosition(BGE.Math.Vector)
Returns
OrientedSpriteBucket
One resolved angle/elevation bucket: its own registered Sprite animation name.
Properties
animationName(string)
DrawableOrientedSprite
Extends: Sprite
A Sprite that swaps which named animation is active based on the angle between the camera and this entity - the classic Doom/Duke3D "billboard sprite" technique for faking full 3D orientation with pre-rendered 2D views. See docs/drawables-and-scene-objects.md for a full walkthrough and specs/2026-09-22-oriented-sprite-billboards-design.md for the design.
Parameters
owner(GameEntity)spriteSheet(ifDraw2d)cellWidth(integer)cellHeight(integer)numAngles(integer, optional, default: 8)numElevationBands(integer, optional, default: 1)args(roAssociativeArray, optional, default: "{}")
Properties
numAngles(integer) — Number of horizontal (azimuth) view buckets around the entity. Bucket 0 is thenumElevationBands(integer) — Number of vertical (elevation) view bands, from the camera looking up at the
Returns
DrawableParallaxLayer
Extends: Drawable
Scrolls a tiled/non-tiled bitmap layer at a configurable per-axis fraction of the camera's movement (parallax). {1,1} is the default and behaves exactly like an ordinary drawable; {0,0} pins the layer to the camera; 0 < factor < 1 is a background layer that drifts slower than the world; factor > 1 is a foreground layer that scrolls faster. See SceneObjectParallaxLayer for the actual per-frame math.
Combines with the owning entity's position/offset exactly like every other Drawable - there is no special "independent of owner" positioning mode. Attach this to a dedicated static entity if you want a fixed background anchor.
This is also the right tool for a 2D sky-like background (issue #145): BGE.Skybox is a yaw/pitch-driven cylindrical panorama, Camera3d-only. For a Camera2d scene, a wide region with a small parallaxFactor (e.g. {x: 0.1, y: 0.1}) gives the same "shifts slowly with the camera" feel without needing any dedicated skybox-for-2D mechanism.
Parameters
owner(BGE.GameEntity)region(roRegion)args(roAssociativeArray, optional, default: "{}")
Properties
region(roRegion) — The bitmap tile to scroll/repeat.parallaxFactor(BGE.Math.Vector) — Per-axis fraction of camera movement this layer scrolls at. See the class doc forrepeatX(boolean) — Whether this layer tiles to cover the canvas along each axis. repeatX defaults truerepeatY(boolean)
Returns
ParticleRecord
One live particle spawned by a DrawableParticles emitter.
Properties
position(BGE.Math.Vector)velocity(BGE.Math.Vector)age(float)lifetime(float)startColor(integer)endColor(integer)startAlpha(float)endAlpha(float)startSize(float)endSize(float)rotation(float)
DrawableParticles
Extends: Drawable
Emits and simulates lightweight particles (lines, rectangles, or images) with randomized velocity, constant acceleration, and lifetime-driven fade/color/size interpolation. Draws through a single SceneObjectParticle per emitter rather than one SceneObject per particle, so spawning/expiring particles never touches Renderer.addSceneObject/removeSceneObject - see specs/2026-08-18-particle-system-design.md for why that matters for depth-sort performance.
Parameters
owner(GameEntity)shape(ParticleShape)args(roAssociativeArray, optional, default: "{}")
Properties
shape(ParticleShape) — Shape drawn for every particle. See BGE.ParticleShape.image(dynamic) — Bitmap or region drawn for each particle when shape = BGE.ParticleShape.Image.cellWidth(integer) — Width/height (pixels) of one animation cell ifimageis a sprite sheet, thecellHeight(integer)regions(Array.<roRegion>)spawnRate(float) — Particles spawned per second while emitting (see start()/stop()).lifetime(float) — Base lifetime in seconds each particle survives, randomized by +/- lifetimeSpread.lifetimeSpread(float)velocity(BGE.Math.Vector) — Base emission velocity (world units/second) shared by every particle beforevelocitySpreadAngleDegrees(float) — Randomizes each particle's velocity direction by +/- this many degrees aroundvelocitySpreadMagnitude(float) — Randomizes each particle's velocity magnitude by +/- this amount. Ifvelocityacceleration(BGE.Math.Vector) — Constant acceleration (world units/second^2) applied to every particle everystartColor(integer) — Packed RGB (0xRRGGBB) color interpolated over each particle's lifetime.endColor(integer)startAlpha(float) — Alpha (0-255) interpolated over each particle's lifetime.endAlpha(float)startSize(float) — Size interpolated over each particle's lifetime - a line's length, a rectangle'sendSize(float)rotationSpeed(float) — Degrees/second of rotation applied to each particle. Only used whenmaxParticles(integer) — Hard cap on live particles. Once reached, further spawns (continuous emission orparticles(Array.<BGE.ParticleRecord>) — Live particle records. See BGE.ParticleRecord.emitting(boolean)spawnAccumulator(float)timer(dynamic)
Returns
DrawablePlane
Extends: BGE.Image
Used to draw a "infinite" plane in 3d space Ideally used for a ground or floor
Parameters
owner(BGE.GameEntity)region(roRegion) — the texture tile to use fortiledImage/staticImagefillMode - passinvalidforcolorfillMode, which ignores it entirely. Aninvalidregion with any other fillMode logs an error and falls back tocolorrather than crashing later inside the renderer.plane(BGE.Math.Plane)args(object, optional, default: "{}") — passfillModehere to select a mode other than the defaultstaticImage- e.g.{fillMode: BGE.PlaneFillMode.color}.
Properties
plane(BGE.Math.Plane)fillMode(PlaneFillMode)
Returns
DrawablePolygon
Extends: Drawable
Parameters
owner(GameEntity)points(Array.<BGE.Math.Vector>, optional, default: "[]")args(roAssociativeArray, optional, default: "{}")
Properties
points(Array.<BGE.Math.Vector>) — the set of points defining a convex polygon
Returns
DrawableRectangle
Extends: Drawable
Draws a rectangle, filled and/or outlined.
The rectangle's top left corner sits at the drawable's own world position (its offset transformed by the owning entity), extending width to the right and height downwards on screen - the same anchoring an Image uses, so the two are interchangeable.
In the direct (billboard) draw modes - which is what a 2D game gets, since a Camera2d resolves matchCamera to directToCamera - this is a plain axis-aligned rectangle. In the oriented/solid/wireFrame draw modes it becomes a quad that rotates and foreshortens in 3D like any other billboard (see examples/3d's RectanglesScene).
Set color for the fill and outlineRGBA for the outline (both packed RGB, no alpha byte - alpha is separate). Leaving outlineRGBA unset means no outline at all; set filled = false for an outline-only rectangle.
Parameters
owner(GameEntity)width(float)height(float)args(roAssociativeArray, optional, default: "{}")
Properties
filled(boolean) — Whether the rectangle's interior is filled withcolor. Set false for an outline-only
Returns
DrawableSkybox
Extends: BGE.Image
Draws a cylindrical panorama that tracks the camera's yaw/pitch (and, via a render-then-rotate composite, roll), giving a Camera3d scene a sky/horizon background instead of a flat fill. See SceneObjectSkybox for the draw algorithm.
Parameters
owner(BGE.GameEntity)region(roRegion) — a cylindrical panorama textureargs(object, optional, default: "{}") — passdegreesPerFullWidth/verticalDegreesCoveredhere to override the defaults
Properties
degreesPerFullWidth(float) — How many degrees of camera yaw the texture's full width covers. Default wraps averticalDegreesCovered(float) — How many degrees of camera pitch the texture's full height covers, centered on
Returns
DrawableSphere
Extends: DrawableCircle
A circle that always looks the same from any camera angle, because a sphere looks the same from every direction. Everything about the fill/outline is identical to DrawableCircle (which this extends unchanged, including addToRenderer) - the only difference is forcing drawMode to directScaled in the constructor, which billboards (never rotates/foreshortens) while still scaling with camera distance in 3D. See SceneObject.getActualDrawMode(): it only resolves the matchCamera default through the camera, so any other explicit drawMode - this one included - is used as-is.
Deliberately does NOT re-append args after forcing drawMode (DrawableCircle's own constructor already applied them once) - a caller passing {drawMode: ...} here should not be able to silently defeat a DrawableSphere's entire reason for existing. A caller who genuinely wants a different draw mode can still assign sphere.drawMode = ... directly after construction.
Parameters
owner(GameEntity)radius(float)args(roAssociativeArray, optional, default: "{}")
Returns
MIN_TEXT_REGION_SIZE
Default: 256
DrawableText
Extends: Drawable
Class to draw text
Parameters
owner(GameEntity)text(string, optional, default: "\"\"")font(roFont, optional, default: "invalid")args(roAssociativeArray, optional, default: "{}")
Properties
text(string) — The text to write on the screenfont(roFont) — The Font object to use ( get this from the font registry)alignment(BGE.UI.HorizAlignment) — The Horizontal alignment for the texttextColor(integer) — The color the text is drawn inlastTextValue(string)lastTextColor(integer)tempCanvas(roBitmap)tempRegion(roRegion)lastAlignment(BGE.UI.HorizAlignment)
Returns
Image
Extends: BGE.Drawable
Used to draw a bitmap image to the screen
Parameters
owner(BGE.GameEntity)region(roRegion)args(roAssociativeArray, optional, default: "{}")
Properties
regionId(string) — An optional unique name for the region, used for caching image data. If not provided, the name of the drawable will be used as the region name.region(roRegion) — ------------Never To Be Manually Changed-----------------
Returns
Model3dTexture
Parameters
srcRegionWithId(BGE.RendererHelpers.RegionWithId)points(Array.<BGE.Math.Vector>)
Properties
srcRegionWithId(BGE.RendererHelpers.RegionWithId)points(Array.<BGE.Math.Vector>)
Returns
Model3dLoadOptions
The options accepted by Game.load3dModel() for an .obj model's texture.
Properties
texturePath(string)
Model3dFace
Properties
vertices(Array.<BGE.Math.Vector>)normal(BGE.Math.Vector)Texture(Model3dTexture)brightness(float)priority(float)color(integer)faceIndex(integer) — This face's position in the model's own, never-reordered face list - set on the
Model3d
Parameters
faces(Array.<Model3dFace>)
Properties
faces(Array.<Model3dFace>)name(string)texturePath(string)
Returns
DrawableModel
Extends: Drawable
Parameters
owner(BGE.GameEntity)model(Model3d)args(roAssociativeArray, optional, default: "{}")
Properties
model(Model3d)maxStaleFrames(integer) — How many consecutive frames a face may reuse its own last-rendered rastermaxFaceDriftDistance(float) — How far (in canvas pixels, Manhattan distance - same measure the engine's other
Returns
AnimationFrameDescription
Properties
startFrame(integer)frameCount(integer)
SpriteAnimation
CReate a new SpriteAnimation
Parameters
name(string) — Name of the animationframeList(Array.<integer> | AnimationFrameDescription) — Wither an array of cell indexes, or an object {startFrame, frameCount}frameRate(integer) — Frames per second the animation should play atplayMode(SpritePlayMode, optional, default: "SpritePlayMode.Loop") — Play mode for the sprite: loop, forward, reverse, pingpong
Properties
name(string) — Name of the animationframeRate(integer) — Frames per second the animation should play atframeList(Array.<integer>) — Array of the regions of the each cell of this animationplayMode(SpritePlayMode) — Play mode for the sprite: loop, forward, reverse, pingpong
Returns
Sprite
Extends: AnimatedImage
Parameters
owner(GameEntity)spriteSheet(ifDraw2d)cellWidth(integer)cellHeight(integer)args(roAssociativeArray, optional, default: "{}")
Properties
spriteSheet(ifDraw2d) — roBitmap to pick cells fromcellWidth(integer) — Width of each animation cell in the sprite image in pixelscellHeight(integer) — Height of each animation cell in the sprite image in pixelsanimations(roAssociativeArray) — Lookup map of animation name -> SpriteAnimation objectactiveAnimation(SpriteAnimation) — The current animation being played
Returns
SceneChangeInfo
Properties
scene(GameScene)args(roAssociativeArray)
GarbageCollectionInfo
Properties
count(integer)orphaned(integer)root(integer)
DebugColors
Properties
colliders(integer)safe_action_zone(integer)safe_title_zone(integer)
EntityWithId
Properties
id(dynamic)
PositionXY
Properties
x(float)y(float)
SizeWH
Properties
width(float)height(float)
AdaptiveQualityOptions
Extends: roAssociativeArray
Options for Game.enableAdaptiveQuality(). Every field is optional.
Properties
targetFps(float) — Frame rate to hold (default 20)minLevel(integer) — Lowest level the controller may choose (default basic)maxLevel(integer) — Highest level the controller may choose (default ultra)windowSeconds(float) — Seconds of frames averaged (default 1.0)outlierFrameSeconds(float) — Frames longer than this are ignored, e.g. garbage collection (default 0.25)settleSeconds(float) — Seconds ignored after a level or scene change (default 0.25)stepDownBelowFraction(float) — Step down when average fps < targetFps * this (default 0.9)stepUpHeadroomFraction(float) — Step up when average fps >= targetFps * this... (default 1.25)stepUpSustainSeconds(float) — ...for this many seconds (default 0.5)maxMeasurableFps(float) — Display refresh ceiling for the step-up threshold (default 60)stepDownCooldownSeconds(float) — Minimum seconds between two downward steps (default 0.75)probeFailWindowSeconds(float) — A step down this soon after a step up marks that level as failed (default 1.5)probeBackoffSeconds(float) — Seconds a failed level isn't retried; doubles on each repeat failure (default 10)stepUpJumpFraction(float) — Step up two levels at once when average fps >= targetFps * this; 0 disables (default 2.0)
QualityController
Chooses a render quality level from measured frame times. Game runs one for you after enableAdaptiveQuality(); you don't normally create one yourself.
Parameters
options(BGE.AdaptiveQualityOptions, optional, default: "{}") — any subset of the options
Properties
targetFps(float)minLevel(integer)maxLevel(integer)windowSeconds(float)outlierFrameSeconds(float)settleSeconds(float)stepDownBelowFraction(float)stepUpHeadroomFraction(float)stepUpSustainSeconds(float)maxMeasurableFps(float)stepDownCooldownSeconds(float)probeFailWindowSeconds(float)probeBackoffSeconds(float)stepUpJumpFraction(float)
Returns
RenderQualityManager
Owns the game's current render quality level. Reach it through game.renderQuality; most games only need Game.setQualityLevel() or Game.enableAdaptiveQuality().
Parameters
renderer(BGE.Renderer) — the renderer to apply settings to (the game canvas)initialLevel(integer) — aBGE.RenderQualityLevelvalue
Returns
RenderQualitySettings
Extends: roAssociativeArray
Every draw-quality value a BGE.Renderer uses. Each BGE.RenderQualityLevel has a preset (see BGE.getRenderQualityPreset()); override individual fields per level with game.renderQuality.overridePreset().
Adding a new quality setting: add the field here, give it a value at every level in RenderQualityPresets.bs, and read it via renderer.qualitySettings.
Properties
drawDistanceScale(float) — Multiplier onCamera3d.maxDrawDistancedrawDistanceOverride(float) — Absolute draw distance for this level; 0 or less means "use drawDistanceScale"planeSliceCount(integer) — Horizontal slices used to draw aDrawablePlanein perspectivetriangleSkipSize(float) — Triangles smaller than this many pixels on both axes are skippedtriangleQuickDrawThreshold(float) — Triangles smaller than this on either axis are drawn with the cheaper line-filltriangleQuickDrawStep(integer) — Pixel step between lines in the cheap line-fill (1 = solid)fastDrawParallelogramTolerance(float) — How far from a true parallelogram a billboard's quad may be and still use thefastDrawPerpendicularityTolerance(float) — How far from perpendicular a billboard's quad edges may be and still use the
RenderQualitySettingsOverrides
Extends: roAssociativeArray
Any subset of BGE.RenderQualitySettings, for game.renderQuality.overridePreset().
Properties
drawDistanceScale(float)drawDistanceOverride(float)planeSliceCount(integer)triangleSkipSize(float)triangleQuickDrawThreshold(float)triangleQuickDrawStep(integer)fastDrawParallelogramTolerance(float)fastDrawPerpendicularityTolerance(float)
RendererResourceSize
Default: 400
DEPTH_TIE_EPSILON
Default: 0.5
TriangleQuickDrawParams
The triangle line-fill values a Renderer is using - see getTriangleQuickDrawParams().
Properties
skipSize(float) — Triangles smaller than this many pixels on both axes are skippedthreshold(float) — Triangles smaller than this on either axis use the cheap line-fillstep(integer) — Pixel step between lines in the line-fill
LevelOfDetailOptions
Properties
levelOffset(integer)levelOfDetail(integer)
RendererOptions
Properties
useBitmapPooling(boolean)
Renderer
Wrapper for Draw2D calls, so that we can keep track of how much is being drawn per frame
Parameters
draw2d(ifDraw2d)mainGame(BGE.Game, optional, default: "invalid")cam(BGE.Camera, optional, default: "invalid")options(RendererOptions, optional, default: "{useBitmapPooling: true}")
Properties
nextSceneObjectId(integer)minimumFrameRateTarget(integer) — Frame rate target - the game will reduce quality if this target is not metonlyDrawWhenInFrame(boolean)drawDebugCells(boolean)drawDebugTrianglePoints(boolean)computeOverlapClusters(boolean) — Whether render() computes overlap clusters (BGE.DepthSort.groupIntoClusters)camera(Camera)triangleCache(dynamic)frameCount(integer)bmpPool(BGE.ScratchBitmapPool)qualitySettings(BGE.RenderQualitySettings) — The draw-quality values this renderer uses.Gamesets these from the currentqualityVersion(integer) — Bumped by every setQualitySettings() call, so scene objects know to redraw theirgame(BGE.Game)name(string)statsString(string)resourcesdummyScreen(roScreen)
Returns
DrawPinnedCornersOptions
Properties
splitIntoFour(boolean)alwaysUseTLtoBR(boolean)
ScratchBitmap
Parameters
id(string)w(integer)h(integer)
Properties
bitmap(roBitmap)id(string)
Returns
ScratchRegion
Parameters
region(roRegion)scratchBmp(ScratchBitmap)
Properties
region(roRegion)scratchBmp(ScratchBitmap)scale(dynamic)
Returns
ScratchBitmapPool
Parameters
doPooling(boolean, optional, default: true)initialCount(integer, optional, default: 10)forcePoolingRegardlessOfDevice(boolean, optional, default: false)
Returns
TriangleCacheEntry
Parameters
triangle(BGE.RendererHelpers.TriangleBitmap)
Properties
triangle(BGE.RendererHelpers.TriangleBitmap)timeLastUsed(integer)
Returns
TriangleCache
Parameters
cacheKeepSeconds(integer, optional, default: 60)
Returns
Camera
Properties
orientation(dynamic) — A vector pointed in the direction of the cameraposition(BGE.Math.Vector)motionChecker(MotionChecker)frameSize(BGE.Math.Vector)projectionVersion(integer) — Bumped whenever something about the camera's projection - as opposed to itszoom(float)drawDistanceScale(float) — Multiplier on a 3D camera's maxDrawDistance, set from the renderer's qualitydrawDistanceOverride(float) — Absolute draw distance from the renderer's quality settings; 0 or less meansworldToCamera(Array.<Array.<float>>)name(string)
Returns
Camera2d
Extends: Camera
Properties
top(float)bottom(float)right(float)left(float)near(float)far(float)name(string)
CameraFrustumNormals
Properties
top(BGE.Math.Vector)bottom(BGE.Math.Vector)left(BGE.Math.Vector)right(BGE.Math.Vector)near(BGE.Math.Vector)
CameraFrustumRays
Properties
topLeft(BGE.Math.Ray)topRight(BGE.Math.Ray)bottomLeft(BGE.Math.Ray)bottomRight(BGE.Math.Ray)
Camera3d
Extends: Camera
Properties
fieldOfViewDegrees(float)rollDegrees(float) — Rotation about the camera's own forward/view axis, in degrees. Positive = rightmaxDrawDistance(float) — How far (world units) in front of the camera your game wants to draw. ThefrustumNormals(CameraFrustumNormals)frustrumConvergence(BGE.Math.Vector)frustumRays(CameraFrustumRays)name(string)
MAX_DRAW_MODE
Default: 8
SceneObject
Parameters
name(string)drawableObj(Drawable)objType(SceneObjectType)
Properties
name(string)id(string) — Unique IdclusterMemberCount(integer) — How many members are in this object's overlap cluster this frame (seedrawable(Drawable)type(SceneObjectType)negDistanceFromCamera(float) — The negative distance from the camera, used for depth sorting. Measured fromworldPosition(dynamic)depthPosition(dynamic) — This object's position as used for depth classification (BGE.BSP's dynamic-itemtransformationMatrix(dynamic) — The Current Transformation MatrixlastFrameWasCulled(boolean) — Whether the last frame's draw was skipped because the frustum rejected this object,lastFrameDidDraw(boolean) — Whether the last frame's draw actually happened. Distinct from lastFrameWasCulledhasValidWorldPosition(boolean)hasValidCanvasPosition(boolean)wasEnabledLastFrame(boolean)isFirstFrameSinceEnabled(boolean)isLowEndDevice(boolean)lastGeometryVersion(integer) — The drawable'sgeometryVersionas of the last completed draw - see geometryChanged()lastQualityVersion(integer) — The renderer'squalityVersionas of the last drawqualityChangedThisDraw(boolean) — True during a draw whose renderer quality settings changed since this object'slastDrawMode(integer) — The draw mode this object last drew in - see drawModeChanged()lastProjectionVersion(integer) — The camera'sprojectionVersionas of the last draw - see projectionChanged()depthChangedThisFrame(boolean) — True for exactly the frame this object's negDistanceFromCamera was recomputed -stableSortKey(float) — What Renderer actually sorts by - negDistanceFromCamera quantized intoisStatic(boolean) — Set by Renderer when this object's owning entity is marked GameEntity.isStatic andstaticGeometryMovedThisFrame(boolean) — True for exactly the frame Renderer.updateSceneObjects() should mark the staticstaticCheckArmed(boolean) — Whether update() has completed at least one prior frame for this object - guardsstaticWarningLogged(boolean) — Whether the one-time misuse warning has already been logged for this object -staticDrawModeWarningLogged(boolean) — Whether the one-time "static but not in an oriented draw mode" warning haswasStaticEnabledState(boolean) — This object's isEnabled() as of the last checkStaticEnabledStateChanged() call -
Returns
TransformTempBitmapDetails
Properties
origin(BGE.Math.Vector)rotation(float)scaleX(float)scaleY(float)
TempBitmapDrawResult
Properties
worked(boolean)didFastDraw(boolean)
SceneObjectBillboard
Extends: SceneObject
Parameters
name(string)drawableObj(Drawable)objType(SceneObjectType)
Properties
worldPoints(BGE.Math.CornerPoints)canvasPoints(BGE.Math.CornerPoints)canvasPosition(BGE.Math.Vector)useTempBitmapMap(Array.<boolean>)usedTransformedFastDrawLastFrame(boolean) — Whether the most recent oriented/solid draw took the cheap rotate+scale fast path
Returns
SceneObjectCircle
Extends: SceneObjectBillboard
Draws a DrawableCircle. The fill is inherited, unmodified SceneObjectBillboard machinery (pinned-corners texture warp, tinting, temp-bitmap caching) blitting the renderer's shared circle resource (Renderer.getCircleResource(), built lazily on first use) - exactly like SceneObjectImage, just with a fixed texture instead of one supplied by the drawable. Only the outline differs from a plain Image: it's stroked as an N-gon inscribed in this object's own already-transformed canvasPoints quad (via the generic getOutlineCanvasPoints() hook), which is far cheaper than rasterizing the fill itself as a many-sided polygon and needs no new Renderer draw method.
Parameters
name(string)drawableObj(DrawableCircle)
Properties
drawable(DrawableCircle)
Returns
SceneObjectImage
Extends: SceneObjectBillboard
Parameters
name(string)drawableObj(Image)
Properties
drawable(Image)frameNumber(integer)
Returns
SceneObjectLine
Extends: SceneObject
Parameters
name(string)drawableObj(DrawableLine)
Properties
drawable(DrawableLine)
Returns
SceneObjectModel
Extends: SceneObjectBillboard
Parameters
name(string)drawableObj(DrawableModel)
Properties
drawable(DrawableModel)
Returns
SceneObjectParallaxLayer
Extends: SceneObject
Parameters
name(string)drawableObj(DrawableParallaxLayer)
Properties
drawable(DrawableParallaxLayer)
Returns
SceneObjectParticle
Extends: SceneObject
Draws an entire DrawableParticles emitter's live particles with a single SceneObject
- not one SceneObject per particle. See specs/2026-08-18-particle-system-design.md ("Why one SceneObjectParticle per emitter, not per particle") for why: per-particle SceneObjects would call Renderer.addSceneObject/removeSceneObject every frame during continuous emission, permanently defeating the depth-sort skip-optimization for the whole renderer.
Parameters
name(string)drawableObj(DrawableParticles)
Properties
drawable(DrawableParticles)
Returns
PerspectiveCalculationResult
Properties
actual(BGE.Math.CornerPoints)mapped(BGE.Math.CornerPoints)
PerspectiveSlice
Properties
srcWidth(float)srcHeight(float)srcTopLeft(BGE.PositionXY)scaleX(float)
SCENE_OBJECT_PLANE_NEAR_DISTANCE
Default: 0
SCENE_OBJECT_PLANE_TILES_PER_AXIS_WARNING_THRESHOLD
Above this, the supertexture build's tilesPerAxis^2 blit count is worth a runtime warning (63x63 = ~4k blits) - see buildSuperTextureIfNeeded().
Default: 63
SceneObjectPlane
Extends: SceneObject
Parameters
name(string)drawableObj(DrawablePlane)
Properties
drawable(DrawablePlane)
Returns
SceneObjectPolygon
Extends: SceneObjectBillboard
Parameters
name(string)drawableObj(DrawablePolygon)
Properties
drawable(DrawablePolygon)
Returns
SceneObjectRectangle
Extends: SceneObjectBillboard
Draws a DrawableRectangle. Extends SceneObjectBillboard, so a rectangle orients and foreshortens in 3D in the oriented draw modes and stays screen-aligned in the direct ones, exactly like an image does.
Unlike an image, though, a rectangle has no texture to sample: it's a single flat color. So it never needs the inherited pinned-corners path - filling the projected quad produces identical pixels for far less work, and DrawableRectangle never has to hold a bitmap of its own. This is how SceneObjectPolygon draws, for the same reason.
It does still cache that fill into a temp bitmap in the oriented draw modes, exactly like a polygon: filling a rotated quad means rasterizing two triangles through scratch bitmaps, which is far too expensive to repeat every frame for an object that hasn't moved. In the direct (billboard) draw modes there's nothing worth caching - the draw is already a single DrawRect - so those skip the temp bitmap entirely.
Parameters
name(string)drawableObj(DrawableRectangle)
Properties
drawable(DrawableRectangle)
Returns
SceneObjectSkybox
Extends: SceneObject
Parameters
name(string)drawableObj(DrawableSkybox)
Properties
drawable(DrawableSkybox)
Returns
SceneObjectText
Extends: SceneObjectBillboard
Parameters
name(string)drawableObj(DrawableText)
Properties
drawable(DrawableText)
Returns
CountdownTimer
A simple dt-driven countdown: start it with a duration, tick() it once per frame (typically from GameEntity.onUpdate()'s own dt), and check isActive() to see if time remains. Replaces a hand-rolled "duration constant + live timer field + manual decrement-and-clamp block" pattern - the same shape used for coyote time, jump/input buffering, invulnerability windows, hit-flash timers, cooldowns, etc.
This is not the same as BGE.GameTimer, which wraps a wall-clock roTimespan (mark()/totalMilliseconds()) for measuring real elapsed time - CountdownTimer is purely dt-driven and has no idea what real time it is.
Returns
MotionChecker
Properties
previousTransform(dynamic)movedLastFrame(boolean)
SomeConst
Default: 23
TagList
Returns