the x position of the element, in screen pixels
the y position of the element, in screen pixels
Optionalw: number
the width of the element, in pixels
Optionalh: number
the height of the element, in pixels
Define the renderable opacity
Set to zero if you do not wish an object to be drawn
Opacity cascades: it is multiplied with the alpha already on the
renderer, so fading a Container fades everything inside it,
and a child at alpha 0.5 inside a parent at 0.5 draws at 0.25.
Each renderable keeps its own value — the composition happens at
draw time, and is undone when the renderable is done.
That is different from Container#setChildsProperty, which
assigns a value onto the children themselves. Use alpha to fade a
subtree, and setChildsProperty to change what the children are.
Whether the renderable object will always update, even when outside of the viewport
a reference to the parent object that contains this renderable
The anchor point is used for attachment behavior, and/or when applying transformations.
The coordinate system places the origin at the top left corner of the frame (0, 0) and (1, 1) means the bottom-right corner

a Renderable's anchor point defaults to (0.5,0.5), which corresponds to the center position.
Note: Object created through Tiled will have their anchorPoint set to (0, 0) to match Tiled Level editor implementation.
To specify a value through Tiled, use a json expression like json:{"x":0.5,"y":0.5}, or (since 19.9) a plain string preset such as bottom.
At construction time, settings.anchorPoint also accepts the named presets
"center", "top", "bottom", "left", "right", "top-left", "top-right",
"bottom-left", "bottom-right" on every renderable that consumes it
(Sprite, Entity, Collectable, ImageLayer, Text, BitmapText, Sprite3d and subclasses).
Note: a body's collision shapes are measured from the same frame this
places the renderable in, so a shape of Rect(0, 0, width, height) covers the
renderable whatever the anchor is (since 20.7; before that shapes were measured
from pos regardless, and a non-corner anchor collided where it was not drawn).
A shape's own pos still offsets it inside that frame. A renderable that has
cleared Renderable#applyAnchorTransform takes no offset at all, on the
drawing or on its shapes. Note also that the adapters read the anchor when the
body is created, so changing it afterwards moves the drawing but not an
already-built body.
Whether Renderable#preDraw applies the Renderable#anchorPoint offset to the renderer transform.
When true (the default), the renderable is shifted by
-anchorPoint × (width, height) so its anchor — not its top-left
corner — aligns with its position. Correct for sprites and other 2D
renderables.
Set to false for a renderable that emits its own final world
coordinates and takes its origin from geometry rather than a bounds
box — e.g. a Mesh on the Camera3d world-space path (a 3D
mesh is positioned by its transform and has no anchor). The WebGL mesh
batcher reuses this same renderer transform as its view matrix,
so applying the normalized anchor there would shift every mesh by
half its OWN bounds box; because scene meshes size that box per node,
props and the platforms they rest on would drift apart and overlap.
Specify if the children z index should automatically be managed by the parent container
Whether the container keeps its children sorted by itself.
"x" or "y" sort, it also keeps its children in order every
frame, as they move: at the end of each update, after physics and
the children's own updates, it checks the order and re-sorts when
anything is out of place. A character walking around a y-sorted
scene passes in front of and behind things with no sort() call.
A frame where nothing moved costs one pass over the children, and
nothing is redrawn because of it."z" sort, changing a child's depth after adding it does
NOT re-sort: call Container#sort, or use
Container#moveToTop and the other move methods, which
reorder the children themselves. "depth" is re-sorted every frame
by its Camera3d.Turn it off to keep the children in the order you put them.
When enabled, an object container will automatically apply any defined transformation before calling the child draw method.
// enable "automatic" transformation when the object is activated
onActivateEvent: function () {
// reset the transformation matrix
this.currentTransform.identity();
// ensure the anchor point is the renderable center
this.anchorPoint.set(0.5, 0.5);
// enable auto transform
this.autoTransform = true;
....
}
define a background color for this container
the blend mode to be applied to this renderable — any of the modes listed on CanvasRenderer#setBlendMode, honoured identically by every renderer
the renderable physics body — the handle returned by the
active PhysicsAdapter's addBody (or constructed
imperatively via new Body(...)). Typed as the portable
PhysicsBody interface; cast to the adapter-specific
concrete type (MatterAdapter.Body, BuiltinAdapter.Body, or
the legacy Body class) to reach native fields.
// define a new Player Class
class PlayerEntity extends me.Sprite {
// constructor
constructor(x, y, settings) {
// call the parent constructor
super(x, y , settings);
// define a basic walking animation
this.addAnimation("walk", [...]);
// define a standing animation (using the first frame)
this.addAnimation("stand", [...]);
// set the standing animation as default
this.setCurrentAnimation("stand");
// add a physic body
this.body = new me.Body(this);
// add a default collision shape
this.body.addShape(new me.Rect(0, 0, this.width, this.height));
// configure max speed, friction, and initial force to be applied
this.body.setMaxVelocity(3, 15);
this.body.setFriction(0.4, 0);
this.body.force.set(3, 0);
this.isKinematic = false;
// set the display to follow our position on both axis
app.viewport.follow(this, app.viewport.AXIS.BOTH);
}
...
}
Declarative body definition consumed by the active
PhysicsAdapter when this renderable is added to a
container. Adapter API only — leave undefined if you
build a body imperatively via this.body = new Body(...).
When set, the parent container forwards it to
world.adapter.addBody(this, this.bodyDef), which constructs
the underlying physics body (matter, builtin SAT, …) and
assigns the engine-portable wrapper to this.body. This is
the engine-portable path: the same bodyDef produces an
equivalent body under any adapter.
Typical fields: type ("static"/"dynamic"/"kinematic"),
shapes, collisionType, collisionMask, restitution,
frictionAir, density, gravityScale, isSensor,
maxVelocity, fixedRotation. See BodyDefinitionInit.
shapes is normally a list of collision shapes, but it can also
name a collision shape file preloaded as JSON, paired with id
naming the body to read out of it. The file is resolved before any
adapter sees the definition, so the same one works unchanged on
every backend.
// a shape authored in code
this.bodyDef = {
type: "dynamic",
shapes: [new me.Rect(0, 0, this.width, this.height)],
};
// shapes drawn in a physics-shape editor, preloaded as JSON with
// { name: "shapes", type: "json", src: "data/physics/shapes.json" }
this.bodyDef = { type: "dynamic", shapes: "shapes", id: "hotdog" };
// the density, friction and bounce the shapes were authored with
// come with them, unless the definition states otherwise (each is
// honoured by whichever backends support it):
this.bodyDef = {
type: "dynamic",
shapes: "shapes",
id: "hotdog",
restitution: 0.9, // wins over whatever the file carries
};
Specify if the container draw operation should clip its children to its own bounds
OptionalcollisionOptionalcollisionOptional per-shape collision settings, honoured by Body#addShape
and defaulted there. Declared rather than initialized: the body writes
them when the shape joins it, so a class field here would emit an
undefined own property on every shape ever built. See addShape for
the table of defaults and what each one does.
the renderable transformation matrix (4x4).
For standard 2D use, only the 2D components are used (rotate around Z, scale X/Y, translate X/Y).
For 3D use (e.g. Mesh), the full 4x4 matrix supports rotation around any axis,
3D translation, and perspective projection.
Use the rotate(), scale(), and translate() methods rather than modifying this directly.
The edges here are the direction of the nth edge of the polygon, relative to
the nth point. If you want to draw a given edge from the edge value, you must
first translate to the position of the starting point.
Re-measure this container's bounds from its children, so they follow the children as they move: on every update (after the children have been updated), whenever a child is added or removed, and, while the container is culled, before each visibility check, so a group whose members come back into view is drawn again. Expensive — every update walks the whole child list — and off by default, because a parent almost never needs it.
Enable it for a group whose extent genuinely IS its members' union and moves as they do: a flock of birds, a squad of enemies. A container whose size is known (or fixed) should be given that size with Renderable#resize instead, which costs nothing per frame — that is what GLTFModel does, from the glTF scene's own bounding box.
Note that a container with neither — no dimensions of its own and
this left off — reports an EMPTY bounds (min +Infinity, max
-Infinity), since Container#updateBounds then has nothing
to measure. Anything reading it is wrong about where the container
is, and the physics broadphase, which files every item by
getBounds(), cannot place it at all.
UI elements use screen coordinates by default, so they stay put when
the camera moves. Children added to a UIBaseElement should keep their
own floating at false.
Whether this element can take the keyboard and gamepad focus: see UIBaseElement#focus. The built-in buttons, checkboxes and sliders set it; set it on a widget of your own to make it reachable. A disabled or hidden element is skipped.
While dragged: where the element was grabbed, relative to its
position. undefined otherwise.
(G)ame (U)nique (Id)entifier"
a GUID will be allocated for any renderable object added
to an object container (including the app.world container)
How long a press must be held before UIBaseElement#onHold
runs, in milliseconds. Needs isHoldable.
true while the pointer is over the element. A tap on a touch screen
does not set it. Cleared when the element is removed, so one added back
later is not drawn lit until the pointer comes over it again.
The scale the widget is drawn at under the pointer, or while it shows
the focus ring: a little bounce, such as 1.05. 1 turns it off.
Only the drawing scales, about the widget's centre. Its hit area and its place in a layout stay the same, so the widgets around it do not move. The scale eases there and back by itself (about 0.2 s). A disabled widget does not grow.
a list of indices for all vertices composing this polygon, filled in by Polygon#getIndices and invalidated by Polygon#recalc.
A subclass may repurpose this name for geometry of its own: a
Mesh holds a GPU index buffer here, a typed array rather than a
plain one. recalc therefore only clears the slot when it owns it —
anything else reading it should check what it got.
Optionalisfalse takes this shape out of collision without removing it
Whether the pointer can press the element. The low-level flag under
UIBaseElement#enabled: prefer enabled, which also calls off a
press in progress, blocks the keys and the pad, and draws a built-in
widget disabled.
when true the renderable will be redrawn during the next update cycle
Whether the element follows the pointer while held. onClick runs on
the pick-up, UIBaseElement#onMove on each move and onRelease
on the drop.
Whether a press held for holdThreshold ms calls
UIBaseElement#onHold.
If true then physic collision and input events will not impact this renderable
make the renderable object persistent over level changes
Optionalistrue reports contacts but skips the position correction
Whether a drag that starts on this element belongs to it.
When false, a drag that starts on the element inside a scrolling
UIPanel scrolls the panel and calls off the press. Set it on a
widget that handles its own drags, such as a knob or a colour picker,
as UISlider does. An isDraggable element keeps its drags
anyway.
A mask limits rendering elements to the shape and position of the given mask object. So, if the renderable is larger than the mask, only the intersecting part of the renderable will be visible.
The name of the renderable
a callback to be extended, triggered after a child has been added or removed
an event handler that is called when the renderable leave or enter a camera viewport
Array of points defining the Polygon
Note: If you manually change points, you must call recalcafterwards so that the changes get applied correctly.
origin point of the Polygon
whether a single post effect on this renderable needs an offscreen capture instead of the renderer's shader-swap fast path.
One effect is normally applied by drawing the renderable with the
effect's own program rather than capturing and post-processing it,
which costs no render target. That is only equivalent when everything
the renderable draws is a textured quad. fillRect and the shape
dispatch go through a batcher that never looks at that shader, so a
single effect on a renderable that draws with primitives silently
does nothing. Set this and the capture is used instead, at the cost
of a render target while the effect is active.
Two or more effects always capture, so this only ever changes the single-effect case.
the list of post-processing shader effects applied to this renderable (GPU backends — WebGL and WebGPU). Effects are applied in order. Use addPostEffect, getPostEffect, and removePostEffect to manage effects, or assign directly. On the Canvas renderer effects stay inert (the scene keeps rendering un-effected).
The scale the widget is drawn at while held down, such as 0.92.
1 turns it off. Drawing only, as UIBaseElement#hoverScale.
false while the element is held down (by the pointer, or by Enter /
A with the focus), true otherwise. Removing a held element calls the
press off (see UIBaseElement#cancelPress), so it is true again
once out of the scene.
whether the container is the root of the scene
The shape type (used internally).
Whether to update this object when the game is paused.
On a container it covers everything under it: a child steps through a pause on its own opt-in or on one from any container above it, so a pause menu flags itself once and its nested labels follow.
The layers this renderable belongs to, as bits (1, 2, 4, 8... up to
32 of them). A camera draws it only if it shares a bit with the
camera's Camera2d#cullMask: by default every renderable is on
layer 1 and every camera draws every layer, so it shows in all of
them. Put something on a layer a camera leaves out to keep it off that
camera only, such as the particles off a minimap. A container left
out is left out with everything inside it (the world included), and
a renderable on no layer, 0, is drawn by no camera.
It decides what a camera draws, and nothing else: the renderable
still updates, collides and receives pointer events. A
Light2d a camera leaves out, itself or a container it is in,
neither glows, nor cuts its hole in the darkness, nor lights
normal-mapped sprites in that camera (a Light3d lights the meshes
of every camera). A
floating renderable must also pass the camera's floating rule (see
Renderable#visibleInAllCameras). On an object of a Tiled map
it can be set as an int custom property of the object.
If true, this floating renderable will be rendered by all cameras (e.g. background image layers). If false (default), floating elements are only rendered by the default camera (e.g. UI/HUD elements), zoomed or not. Only applies to floating renderables in multi-camera setups.
StaticfocusThe colour of the ring drawn around the element with the focus, for every element. Any CSS colour.
bottom coordinate of the Rectangle
absolute center of this rectangle on the horizontal axis
absolute center of this rectangle on the vertical axis
the depth of this renderable on the z axis
Whether the widget answers input: the switch to turn a widget off.
Turning it off clears isClickable, calls off a press in progress
(see UIBaseElement#cancelPress), and skips it in keyboard and
gamepad navigation. The built-in widgets draw themselves disabled:
their disabled skin region, or at half opacity. A widget of your own
reads enabled in its draw.
isClickable is the low-level flag underneath; setting it alone does
not change enabled or the look.
true while this element has the keyboard and gamepad focus
height of the Rectangle
The left coordinate of the Rectangle.
returns the parent application (or game) to which this renderable is attached to
the parent application or undefined if not attached to any container/app
right coordinate of the Rectangle
since 19.2.0 — use addPostEffect / getPostEffect / removePostEffect instead
An offset, in pixels, added to this renderable's position when its
parent container sorts its children on "y" (or "x"), and used for
nothing else. It never moves the renderable and never changes where
or how it is drawn: it only decides whether it is drawn before or after
its siblings, and so which one is on top, and which one a pointer hits.
A container sorted on "y" draws its children from the smallest
pos.y to the largest, the last one on top. A child with a
sortOffset is lined up as if it stood that many pixels lower
(positive) or higher (negative), while staying where it is. Use it when
pos is not the point a renderable should be sorted by: the top of a
Tiled tile object's image, the top left corner of a container, or the
top of a particle emitter's spawn area.
autoSort, the default) picks a
change up at its next update; with autoSort off, call its sort()."z" or "depth" ignore it, and on "x" and
"y" a different pos.z still decides first.1 settles such a tie on
purpose.0.The property of the child object that should be used to sort on this container.
"x" / "y" — 2D scroll-order, descending on both axes
(higher pos.z first; tied z, higher pos.x or pos.y first).
Suited to side-scrollers and top-down games. Each child is compared
at pos.x / pos.y plus its Renderable#sortOffset, which
changes the order and never the position. With
Container#autoSort on (the default), the children are kept in
that order every frame as they move."z" — descending pos.z (higher z draws on top). Default for
Camera2d — matches the painter's-algorithm 2D layering model
where pos.z is "layer index"."depth" — Camera3d-only. Ascending squared distance from
the active camera (closest first in the array → far drawn first
→ close drawn on top under Container.draw's reverse-iteration
walk). This is the only correct sort for alpha-blended sprites
under perspective projection, where neither pos.z nor pos.x/y
layering produces correct occlusion (the closer/farther
relationship flips as the camera orbits). Set automatically
when an Application or Stage is constructed with
cameraClass: Camera3d. Has no useful effect under Camera2d
(ortho projection doesn't need camera-distance ordering) and
pays an O(N log N) sort per frame, so don't enable it manually
in 2D-only games.define a tint for this renderable. a (255, 255, 255) r, g, b value will remove the tint effect.
Takes a Color to copy, or a CSS colour string.
It COPIES rather than holds, so a caller that goes on mutating what it
passed does not steer this renderable's tint by accident. What the
getter hands back is always a Color, whichever form went in.
the colour to tint with
top coordinate of the Rectangle
width of the Rectangle
StaticfocusThe element with the keyboard and gamepad focus, or undefined when
none has it.
Add a child to the container
if auto-sort is disabled, the object will be appended at the bottom of the list.
Adding a child to the container will automatically remove it from its other container.
Meaning a child can only have one parent. This is important if you add a renderable
to a container then add it to the World container it will move it out of the
original container. Then when the World container reset() method is called the renderable
will not be in any container.
if the given child implements an onActivateEvent method, that method will be called
once the child is added to this container, when this container is in the
world (or as soon as it is added to it). Each onActivateEvent is matched
by exactly one onDeactivateEvent when the child leaves the world again.
Once this container is in the world, the physics body of the child
(its bodyDef, or a pre-built Body) is registered with the world's
physics adapter, and so is the body of every renderable below it if it is
a container, at any depth. They are taken out again when the child leaves
the world, so moving a whole group from one container to another keeps
its bodies simulated, once each.
Child to be added
Optionalz: number
forces the z index of the child to the specified
value. This depth is scoped to THIS container: it orders the child among
its siblings only, and says nothing about children of another container.
Both drawing and pointer hit-testing resolve a cross-container pair at
the common ancestor instead, so to put a whole subtree in front use
Container#moveToTop on the container rather than a large z on
something inside it. Left out, autoDepth numbers children from 1.
the added child
Add a child to the container at the specified index
(the list won't be sorted after insertion)
Child to be added
The index at which to insert the child
the added child
Add a post-processing shader effect to this renderable.
With the prewarm application setting on (the default), what the
effect will need to draw here is compiled from this call, off the
frame, rather than on the frame the renderable first draws with it.
That takes a moment to finish, so attach effects when the renderable
is built (a pool, a stage starting) rather than when it is shown.
the effect to add
the added effect
return the angle to the specified target
angle in radians
Call off a press in progress, without calling onRelease:
UIBaseElement#onCancel runs instead.
The element goes back to its released look, and the pointer-up that
follows does nothing. A scrolling UIPanel calls this when a drag
that started on the element turns out to be a scroll, so a button
dragged to scroll its list is not clicked. Setting enabled to false,
losing the focus or the window losing focus while Enter or A is held,
and removing the element while it is held call it too.
center the rectangle position around the given coordinates
the x coordinate around which to center this rectangle
the y coordinate around which to center this rectangle
this rectangle
Whether this container shows its children at a point.
Always true unless Container#clipping is on, in which case only its own rectangle is shown. The pointer asks every container above a region before letting it answer, so a child cropped out of view cannot be clicked where it is not drawn.
the point, in the same coordinates as the bounds of this container (screen pixels for a floating one)
the point
false where the children are clipped away
Returns true if the polygon contains the given point.
(Note: it is highly recommended to first do a hit test on the corresponding
bounding rect, as the function can be highly consuming with complex shapes)
x coordinate or a vector point to check
y coordinate
True if the polygon contain the point, otherwise false
Returns true if the polygon contains the given point.
(Note: it is highly recommended to first do a hit test on the corresponding
bounding rect, as the function can be highly consuming with complex shapes)
True if the polygon contain the point, otherwise false
Returns true if the rectangle contains the given rectangle
rectangle to test
True if the rectangle contain the given rectangle, otherwise false
copy the position and size of the given rectangle into this one
Source rectangle
new rectangle
return the distance to the specified target
distance
Check if this rectangle is identical to the specified one.
Other rectangle.
true if equals
flip the renderable on the horizontal axis (around the center of the renderable)
Optionalflip: boolean = true
true to flip this renderable.
Reference to this object for method chaining
flip the renderable on the vertical axis (around the center of the renderable)
Optionalflip: boolean = true
true to flip this renderable.
Reference to this object for method chaining
Take the keyboard and gamepad focus, for a game played without a mouse or a touch screen. Call it once the element is in the scene.
Nothing has the focus until a game gives it to an element, and until then the arrow keys and the pad are left to the game. From then on: the arrows or the D-pad move the focus to the nearest focusable element that way; Enter, Space or the pad's A button press the focused one as a click does (a slider steps on left and right instead). The focus ring shows, and hides again while the mouse is used. A focused element in a scrolling panel is scrolled into view.
Does nothing on an element that is not focusable.
Called when Enter, Space or A is pressed with the focus here: the
widget goes down, as under the pointer, and onClick runs with no
event. Override it only to change what accept does.
whether it went down: not when disabled, or already held
Called when Enter, Space or A is let go after
UIBaseElement#focusPress: the widget comes back up and
onRelease runs with no event. The built-in widgets complete their
action here, as on a click: a button calls its onClick setting, a
checkbox toggles.
The forEach() method executes a provided function once per child element.
the callback function is invoked with three arguments:
function to execute on each element
OptionalthisArg: object
value to use as this(i.e reference Object) when executing callback.
Where this renderable IS in the game world — its own pos plus every
ancestor's, as a Vector3d so the z component is summed across
the chain too (important for Camera3d's frustum culling, which
previously read obj.depth — local pos.z — and mis-culled children
nested under a container with its own non-zero depth).
Reach for this for anything positional: culling, distance checks, hit tests, placing one renderable relative to another. It is cheap, and it is what the engine's own culling uses.
Reach for Renderable#getWorldTransform instead when a position is not enough — when rotation, scale or flip along the ancestor chain matters, or when you need to map an arbitrary point rather than just the origin. This method sums translations only, so under a rotated or scaled ancestor it reports where the renderable's pivot is and nothing about how its content is oriented.
Note the two also frame the question differently. This one is "where am
I"; getWorldTransform() is "what space is my content drawn in". For a
Container those coincide, because a container offsets its
children by its own position. For a leaf they differ by exactly that
position, which a leaf applies inside its own draw().
The returned vector is pooled and reused — copy it if you need to hold onto the value across another call.
this renderable's absolute position
Returns the Child at the specified index
The index of the child
the child at the specified index
return the child corresponding to the specified GUID
note : avoid calling this function every frame since
it parses the whole object list each time
child GUID
corresponding child or null
returns the list of children with the specified name
as defined in Tiled (Name field of the Object Properties)
note : avoid calling this function every frame since
it parses the whole object list each time
child name
Array of children
return the child corresponding to the given property and value.
note : avoid calling this function every frame since
it parses the whole object tree each time
Property name
Value of the property
Array of children
// get the first child object called "mainPlayer" in a specific container :
let ent = myContainer.getChildByProp("name", "mainPlayer");
// or query the whole world :
let ent = container.getChildByProp("name", "mainPlayer");
// partial property matches are also allowed by using a RegExp.
// the following matches "redCOIN", "bluecoin", "bagOfCoins", etc :
let allCoins = container.getChildByProp("name", /coin/i);
// searching for numbers or other data types :
let depth10 = container.getChildByProp("depth", 10);
let inViewport = container.getChildByProp("inViewport", true);
returns the list of children with the specified class type
Class type
Array of children
Returns the index of the given Child
The child object
index
returns a list of indices for all triangles defined in this polygon
an array of vertex indices for all triangles forming this polygon.
ProtectedgetProtected
A container additionally offsets its children by its own position — the
translate() at the top of Container#draw — which is what makes
a child's coordinates mean "relative to my parent" rather than naming a
place in the world. A leaf renderable has no such term.
matrix to write into
out, for chaining
Returns the next child within the container or undefined if none
The child object
child
get the renderable alpha channel value
This is the renderable's OWN value. What it finally draws at is this multiplied by every ancestor's — see Renderable#alpha.
current opacity value between 0 and 1
Get post-processing shader effects. When called with a class, returns the first effect matching the given class. When called without arguments, returns the full effects array.
OptionaleffectClass: Function
the effect class to search for
the matching effect, the effects array, or undefined
Returns the instance of the root container (i.e. the current application World container).
root container
The space this renderable's content is drawn IN, as a matrix — the full form of Renderable#getAbsolutePosition, which sums positions up the ancestor chain and therefore cannot represent the rotation, scale or flip accumulated along the way.
Reach for getAbsolutePosition() instead for ordinary positional
work — culling, distance checks, hit tests. It is cheaper and it is what
the engine culls with. Use this when a position is not enough:
inv(A) · B converts
between two frames, which is how ParticleEmitter.referenceSpace
measures particles against a container that is not their parent)The two also frame the question differently, and it shows on a leaf.
getAbsolutePosition() is "where am I"; this is "what space is my
content drawn in". For a Container those coincide, because a
container offsets its children by its own position. For a leaf they
differ by exactly that position, which a leaf applies inside its own
draw(). So with no rotation, scale or flip anywhere, a container's
translation column equals its getAbsolutePosition() while a leaf's
equals its PARENT's.
The walk stops at a floating ancestor, because a floating renderable
draws in screen space: Container#draw resets the transform
outright for those, so the chain genuinely ends there rather than
continuing to the root.
The camera needs no special handling — Camera2d folds its view
transform into the root container's currentTransform, so it is picked
up like any other level.
matrix to write into; nothing is stored on the renderable itself, so callers own the lifetime
out, for chaining
Returns true if contains the specified Child
The child object
Checks if this container is root or if it's attached to the root container.
true if this container is root or if it's attached to the root container
Returns true if the vertices composing this polygon form a convex shape (vertices must be in clockwise order).
true if the vertices are convex, false if not, null if not computable
Determines whether all coordinates of this rectangle are finite numbers.
false if all coordinates are positive or negative Infinity or NaN; otherwise, true.
Rotate this renderable towards the given target.
the renderable or position to look at
Reference to this object for method chaining
Move the child in the group one step backward (z depth).
Child to be moved
Move the specified child the bottom (z depth).
Child to be moved
Move the specified child to the top(z depth).
Moves the whole subtree: the child's own children keep their depths among themselves and come with it, because depth is resolved per container. This is how one overlapping panel is brought in front of another, for drawing and for pointer hit-testing alike.
Child to be moved
Move the child in the group one step forward (z depth).
Child to be moved
Called when a press is called off rather than completed: see
UIBaseElement#cancelPress. Override it to undo what onClick
started, such as a charge-up effect.
Called when the element is pressed: the pointer went down on it, or Enter / Space / A with the focus here (then with no event). Override it in a subclass.
This is the press, not a completed click: see UIBaseElement#onRelease for the end of it.
Optional_event: Pointer
the pointer event, or undefined from the keyboard or
the pad
false, the default, to stop the event here; true to let
elements below get it too
Legacy collision callback — fires every frame this renderable body is overlapping another body. Kept for backward compatibility with code written against pre-19.5 melonJS; semantics are unchanged from the 19.4 contract.
NOTE — onCollision is NOT equivalent to Renderable.onCollisionActive.
The two handlers exist side by side and have intentionally different
contracts:
onCollision (legacy) |
onCollisionActive (modern) |
|
|---|---|---|
| Cadence for dynamic-dynamic pairs | 2× per frame per side | 1× per frame per side |
response.a semantics |
Fixed per pair (first body in detector call) | Always the receiver (response.a === this) |
response.b semantics |
Fixed per pair | Always the partner (response.b === other) |
response.normal / response.depth |
✗ | ✓ — normal.y < -0.7 = "push me up" |
return false to skip push-out |
✓ (honored by SAT) | ✗ — use bodyDef.isSensor or setSensor instead |
If you're writing new code, prefer onCollisionActive. Keep
onCollision only when its every-frame, return-false, fixed-a/b
semantics are what you want.
the SAT response object; the legacy handler receives this, not the adapter's CollisionResponse, which is why normal and depth are absent from the table above
the other renderable touching this one (a reference to response.a or response.b)
true if the object should respond to the collision (its position and velocity will be corrected); the return value is only honored by the builtin SAT adapter.
OnDestroy Notification function
Called by engine before deleting the object. Receives whatever
destroy(...args) was called with — the production path
(Container.removeChildNow) passes nothing. Stage has its own
onDestroyEvent, which does forward the active Application.
forwarded by destroy(...args); normally empty
Called once a press has been held for holdThreshold milliseconds,
when isHoldable is set. Override it in a subclass.
Called on each pointer move while the element is dragged (see
UIBaseElement#isDraggable), after pos has followed the
pointer. Override it in a subclass.
Optional_event: Pointer
the pointer event
Called for an arrow key or a D-pad direction while this element has
the focus. Return true to handle it yourself (the focus stays here),
as a slider does to step. Return false, the default, to move the
focus to the nearest widget that way.
Enter, Space and A do not come here: they press the widget through UIBaseElement#focusPress and UIBaseElement#focusRelease.
which way: "up", "down", "left" or "right"
true when handled
// a picker: left and right change the choice, up and down move on
class Picker extends UIBaseElement {
constructor(x, y, choices) {
super(x, y, 160, 32);
this.focusable = true;
this.choices = choices;
this.index = 0;
}
onNavigate(action) {
if (action === "left" || action === "right") {
const step = action === "right" ? 1 : -1;
const n = this.choices.length;
this.index = (this.index + step + n) % n;
this.isDirty = true;
return true;
}
return false;
}
}
Called when the pointer leaves the element. Override it in a subclass.
Also fires when the pointer is still inside but something drawn above
has stopped the move, since the pointer is then over that instead. A
press in progress ends first, through onRelease.
Unlike UIBaseElement#onOver it cannot stop the event: an element that skipped its own leave would stay lit after the pointer had gone.
Optional_event: Pointer
the pointer event
Called when the pointer comes over the element. Override it in a subclass.
Fires once, on the frame the pointer crosses into the element. To stay
opaque to hover for as long as the pointer rests on it, also register a
"pointermove" callback through input.registerPointerEvent
that returns false (see the class example).
Optional_event: Pointer
the pointer event
false to stop the event here, so an element covered by this
one does not also light up
Called when a press ends. Override it in a subclass.
It runs when the pointer comes up, but also when the pointer leaves the
element while held, or the browser cancels the press: it is the end
of a press, not proof of a completed click. (For a click that only
counts when completed, use a UITextButton and its onClick
setting.) A press called off by UIBaseElement#cancelPress does
not come here.
Optional_event: Pointer
the pointer event, or undefined from the keyboard or
the pad
false, the default, to stop the event here; true to let
elements below get it too
check if this rectangle is intersecting with the specified one
Other rectangle.
true if overlaps
restore the rendering context after drawing (automatically called by melonJS).
a renderer object
Apply the bounce, and draw the focus ring, behind the widget.
Here and not in draw: a container translates to its own position in
draw, so from preDraw on, the widget and the ring share the
parent's coordinates, whatever the widget does in its own draw.
the renderer to draw with
Computes the calculated collision polygon.
This must be called if the points array, angle, or offset is modified manually.
Reference to this object for method chaining
Invokes the removeChildNow in a defer, to ensure the child is removed safely after the update & draw stack has completed.
if the given child implements an onDeactivateEvent() method, that method will be called once the child is removed from this container
(exactly once, for a child that had its onActivateEvent: the children of a removed container are told once, however deep they sit).
Child to be removed
Optionalkeepalive: boolean
true to prevent calling child.destroy()
Removes (and optionally destroys) a child from the container.
(removal is immediate and unconditional)
A child that had its onActivateEvent gets one onDeactivateEvent, and
so does each child below it if it is a container — once, even though the
container's own onDeactivateEvent and its destroy() both reach them.
The physics bodies of the child and of everything below it are taken out
of the simulation, at any depth and with or without keepalive; a child
kept alive and added back gets them registered again.
Never use keepalive=true with objects from pool. Doing so will create a memory leak.
Child to be removed
Optionalkeepalive: boolean
True to prevent calling child.destroy()
Remove a specific post-processing shader effect.
the effect to remove
reset the container, removing all children, and resetting transforms. Persistent children (Renderable#isPersistent) are kept, and a sort still pending for them still happens.
resize the rectangle
new width of the rectangle
new height of the rectangle
this rectangle
Rotate this renderable by the specified angle (in radians). When called with just an angle, rotates around the Z axis (2D rotation). When called with an angle and a Vector3d axis, rotates around that axis in 3D.
The angle to rotate (in radians)
Optionalv: Vector3d
the axis to rotate around (defaults to Z axis for 2D)
Reference to this object for method chaining
scale the renderable around his anchor point. Scaling actually applies changes to the currentTransform member which is used by the renderer to scale the object when rendering. It does not scale the object itself. For example if the renderable is an image, the image.width and image.height properties are unaltered but the currentTransform member will be changed.
a number representing the abscissa of the scaling vector.
Optionaly: number = x
a number representing the ordinate of the scaling vector.
Optionalz: number = 1
a number representing the depth of the scaling vector.
Reference to this object for method chaining
scale the renderable around his anchor point
scaling vector
Reference to this object for method chaining
Automatically set the specified property of all childs to the given value
This ASSIGNS to the children — after it, their own property carries the value. To fade a subtree without touching what the children are, set Renderable#alpha on the container instead: opacity cascades at draw time and leaves every child's own value alone.
property name
property value; whatever the named property holds, so a flag is a boolean and a colour is a string, not only an object
Optionalrecursive: boolean
recursively apply the value to child containers if true
set the renderable alpha channel value
opacity value between 0.0 and 1.0
Move this renderable, optionally in three dimensions.
pos holds an ObservableVector3d, but the geometry this class
inherits from declares it as a 2D vector, so from TypeScript
pos.set(x, y) takes two arguments and silently writes a zero z.
Anything with a depth then drops to the near plane. Reaching past that
previously meant a double cast or assigning pos.x, pos.y and
depth by hand, which is why that pattern is written out dozens of
times across the examples.
Omitting z leaves the depth exactly as it was, rather than
zeroing it. That is the whole difference from pos.set(x, y), and it
is what makes this safe to call on a 2D sprite that happens to sit at
a depth, or on a Camera2d, without having to know whether it does.
the new x position
the new y position
Optionalz: number
the new depth; left untouched when omitted
this renderable, for chaining
set new value to the Polygon
position of the Polygon
position of the Polygon
array of vector or vertices defining the Polygon
this instance for object chaining
Set new dimensions for the rectangle.
The new width of the rectangle.
The new height of the rectangle.
Tint this renderable, chainably.
Exactly Renderable#tint's own setter, returning the renderable
so it can be chained with the other set* methods. It exists because
tint is a live Color, so reaching for it means choosing
between setColor (0 to 255), setFloat (0 to 1), parseCSS,
setHSL and setLinear — and picking the wrong one is silent, it just
renders the wrong colour.
Deliberately sRGB only. A LINEAR value, which in practice means a glTF
baseColorFactor or emissiveFactor, stays an explicit
tint.setLinear(...) so the conversion is never silent; for a mesh
built from an asset, pass Mesh#baseColorFactor as a setting and
the loader's value is applied for you.
a Color to copy, or a CSS colour string
this renderable, for chaining
set the vertices defining this Polygon
array of vector or vertices defining the Polygon
this instance for object chaining
Manually trigger the sort of all the childs in the container
Optionalrecursive: boolean
recursively sort all containers if true
Synchronous variant of Container#sort. Sorts immediately
— no defer — using the current _comparator. Intended for
per-frame callers that need the order to be valid for the very
next render (e.g. Camera3d refreshing the "depth" sort after
the camera has moved, where waiting for the deferred sort tick
would render a stale frame).
Optionalrecursive: boolean
recursively sort sub-containers
Swaps the position (z-index) of 2 children
Child to be added
Child to be added
apply a 2d projection to this shape
Reference to this object for method chaining
apply an isometric projection to this shape
Reference to this object for method chaining
Returns a polygon whose edges are the same as this box.
a new Polygon that represents this rectangle.
multiply the renderable currentTransform with the given matrix
Reference to this object for method chaining
Translate the renderable by the specified offset.
Reference to this object for method chaining
merge this rectangle with another one
other rectangle to union with
the union(ed) rectangle
Ease the bounce.
time since the last frame, in milliseconds
whether it needs redrawing
update the bounding box for this container.
Optionalabsolute: boolean = true
update the bounds size and position in (world) absolute coordinates
this container bounding box Rectangle object
A clickable, draggable container: the base every UI widget builds on (UITextButton, UICheckbox, UISlider, UIPanel, UISpriteElement). Extend it to make a widget of your own; it can hold other renderables as children.
It uses screen coordinates (
floatingistrue), so it stays put when the camera moves. Children added to it should keepfloatingatfalse.Pointer callbacks
Override these in a subclass:
hoveristruein between.holdThresholdms, whenisHoldableis set.Elements under the pointer are asked topmost first, and the event carries on to the ones below until a handler returns
false.onClickandonReleasereturnfalseby default, so a press on a UI element stops there: a button over the game does not also click the world behind it. Returntruefrom them to let the press through as well. Hover is not stopped by default: returnfalsefromonOverfor that.Turning it off
Set UIBaseElement#enabled to
false: it stops answering the pointer, the keys and the pad, and a press in progress is called off.Dragging
Set UIBaseElement#isDraggable: the element then follows the pointer while held.
onClickis the pick-up, UIBaseElement#onMove runs on each move, andonReleaseis the drop. Inside a scrolling UIPanel, a drag that starts on a widget scrolls the panel instead; set UIBaseElement#keepsDrag on a widget that is dragged itself.Bounce
UIBaseElement#hoverScale and UIBaseElement#pressScale scale the drawing under the pointer and while held, easing there and back. The hit area and the layout do not change.
Keyboard and gamepad focus
For a game played without a mouse or a touch screen. Nothing listens until a widget takes the focus with UIBaseElement#focus; until then the arrow keys and the pad are left to the game. With a widget focused:
The built-in widgets are focusable. A widget of your own sets
focusableand can override UIBaseElement#onNavigate to use the arrows itself.Example
Example
Example
Example