
Melonjs Renderables
Use this skill when subclassing Renderable, writing a custom draw() method, handling...
Install
npx skills add melonjs/melonJS --skill melonjs-renderables -g -a claude-code -y- Repository
- melonjs/melonJS6.4k
- Category
- Writing
- Updated
- 3d ago
- License
- MIT
- Context cost
- Mediumabout 3,000 tokens
- Runs scripts
- No, instructions only
What it does
Use this skill when subclassing Renderable, writing a custom draw() method, handling pointer or click events on game objects, applying post effects and shaders, or controlling draw order. Covers the pos-relative draw contract, isKinematic and input, addPostEffect vs the deprecated shader property, and z-ordering. Triggers on: Tween, easing, animate, Renderable, extends Renderable, draw(, update(, isKinematic, pointerEvent, registerPointerEvent, onClick, addPostEffect, removePostEffect, ShaderEffect, addChild, z-order, anchorPoint, floating.
Renderables, input and effects
Subclassing
Renderable, custom drawing, receiving pointer events, and applying post effects, with the traps that produce silently wrong output rather than an error.
Everything here is a silent failure: the code runs, nothing throws, and the result is wrong. Those are the cases worth memorising, because nothing in the type signatures warns you.
1. A custom draw() must position itself from this.pos
The renderer is not pre-translated to the renderable's position when draw()
is called. Container.draw translates by the container's own pos and then
calls child.preDraw / draw / postDraw; preDraw never translates by the
child's pos. Read this.pos and draw relative to it.
class Marker extends Renderable {
draw(renderer) {
// ✗ draws at the parent container's origin, not at the marker
renderer.fillRect(0, 0, this.width, this.height);
// ✓
renderer.fillRect(this.pos.x, this.pos.y, this.width, this.height);
}
}
The symptom is an object that renders correctly at position (0, 0) and appears stuck at the top-left as soon as you move it.
Zero the anchor in custom-draw renderables. preDraw does not translate to
pos, but it does apply the anchor offset (-width * anchorPoint.x, -height * anchorPoint.y). With the default centred anchor, drawing at
this.pos therefore lands half a size off:
constructor(x, y, w, h) {
super(x, y, w, h);
this.anchorPoint.set(0, 0); // ← or every custom draw is offset by -w/2, -h/2
}
2. isKinematic must be false to receive input or collisions
Renderable.isKinematic defaults to true, which means "physics collision
and input events will not impact this renderable". A kinematic renderable is
skipped by the pointer-event dispatcher entirely.
