Table of Contents
8. Light¶
The engine provides an opt-in, per-target lighting system exposed through the global mbm table.
Lighting uses a classic (Phong-style) material model: ambient, directional (diffuse) and point lights combine
with each subset’s material to produce the final lit color.
Attention
'3d' and '2dw'
(exact, case sensitive). '2ds' lighting is not implemented.8.1. Lighting only affects objects created after it is turned on¶
Attention
true
for that object’s target at that exact moment.This is an easy contract to trip over, so here is the exact scenario:
-- lighting for '3d' is still OFF here
local meshesBeforeLight = {}
for i = 1, 5 do
meshesBeforeLight[i] = mesh:new('3d')
meshesBeforeLight[i]:load('crate.msh') -- classified unlit right now
end
mbm.setLightEnabled('3d', true) -- turn the light ON
local meshesAfterLight = {}
for i = 1, 3 do
meshesAfterLight[i] = mesh:new('3d')
meshesAfterLight[i]:load('crate.msh') -- classified lit right now
end
-- meshesBeforeLight (5 objects) stay unlit forever, even though the '3d' light is now on.
-- meshesAfterLight (3 objects) are lit and will react to mbm.setAmbientLight/setDirectionalLight/etc.
If you need previously-created objects to become lit (or unlit), you have to make them go through
that same classification moment again — for example by calling load (or the equivalent
load/loadAsync method for sprite, tile, particle
or backGround) again after changing setLightEnabled, or by
adding a fresh animation to the object. Simply toggling the light does not reach back and change shaders
that already exist.
Note
In practice this means: decide and set lighting for a target with setLightEnabled before creating/loading the objects that should be lit for that target.
8.2. Light methods¶
8.2.1. setLightEnabled¶
- setLightEnabled(string target, boolean enabled)
Enable or disable lighting for a target. When disabled the target renders unlit, same as before lighting existed.
- Parameters
string – target either
'3d'or'2dw'.boolean – enabled value.
Example:
mbm.setLightEnabled('3d', true)
8.2.2. resetLight¶
- resetLight(string target)
Reset every light setting for a target back to its default values: disables lighting, restores the default ambient/directional colors and direction, clears the point-light list added through addPointLight, and restores the default requested max lights and selection mode.
- Parameters
string – target either
'3d'or'2dw'.
Example:
mbm.resetLight('3d')
8.2.3. getLightState¶
- getLightState(string target)
Return a snapshot table describing the current light state of a target.
- Parameters
string – target either
'3d'or'2dw'.- Returns
tablewith the fields below.
enabled-boolean.target-string,'3d'or'2dw'.requestedMaxLights-number.supportedMaxLights-number.validatedMaxLights-number(0if the requested value is invalid).lightSelectionMode-string.ambientColor-{r, g, b, a}.directionalColor-{r, g, b, a}.directionalDirection-{x, y, z}(normalized).pointColor-{r, g, b, a}of the legacy single point light slot.pointPosition-{x, y, z}of the legacy single point light slot.pointRadius-numberof the legacy single point light slot.pointLights- 1-indexed array of{position={x,y,z}, radius, color={r,g,b,a}}, one per light added with addPointLight.Example:
local light = mbm.getLightState('3d')
print(light.enabled, light.ambientColor.r)
8.2.4. Default values¶
enabled = falseambientColor = {r = 0.2, g = 0.2, b = 0.2, a = 1.0}directionalColor = {r = 1.0, g = 1.0, b = 1.0, a = 1.0}directionalDirectionnormalized{x = 0.0, y = -0.707, z = -0.707}requestedMaxLightsequals the engine’s compiled maximum (currently4)lightSelectionMode = 'per_object_nearest'point-light list (see addPointLight) starts emptyColor channels passed to any light function below are silently clamped to the
0..1range.
8.3. Ambient & Directional Light¶
8.3.1. setAmbientLight¶
- setAmbientLight(string target, table color)
Set the ambient light color of a target, applied uniformly regardless of light direction or distance.
- Parameters
string – target either
'3d'or'2dw'.table – color
{r, g, b, *a}(aoptional, defaults to1.0).
Example:
mbm.setAmbientLight('3d', {r = 0.2, g = 0.2, b = 0.2, a = 1.0})
- setAmbientLight(string target, number r, number g, number b, number * a)
Same as above passing the color channels directly instead of a table.
- Parameters
string – target either
'3d'or'2dw'.number – r red channel.
number – g green channel.
number – b blue channel.
number – a alpha channel (optional, defaults to
1.0).
Example:
mbm.setAmbientLight('3d', 0.2, 0.2, 0.2)
8.3.2. setDirectionalLight¶
- setDirectionalLight(string target, table direction, table color)
Set the directional (diffuse) light of a target: a single light with a direction but no position, similar to sunlight.
- Parameters
string – target either
'3d'or'2dw'.table – direction
{x, y, z}. It is normalized internally; a zero-length direction silently falls back to the default direction instead of raising an error.table – color
{r, g, b, *a}(aoptional, defaults to1.0).
Example:
mbm.setDirectionalLight('3d',
{x = 0.0, y = -0.707, z = -0.707},
{r = 1.0, g = 1.0, b = 1.0, a = 1.0})
- setDirectionalLight(string target, number x, number y, number z, number r, number g, number b, number * a)
Same as above passing direction and color channels directly instead of tables.
- Parameters
string – target either
'3d'or'2dw'.number – x, y, z direction.
number – r, g, b color, a alpha (optional, defaults to
1.0).
8.3.3. setDirectionalLightDirection¶
- setDirectionalLightDirection(string target, table direction)
Update only the direction of the target’s directional light, keeping its current color.
- Parameters
string – target either
'3d'or'2dw'.table – direction
{x, y, z}(normalized internally, same zero-length fallback as above).
- setDirectionalLightDirection(string target, number x, number y, number z)
Same as above passing the direction channels directly.
8.3.4. setDirectionalLightColor¶
- setDirectionalLightColor(string target, table color)
Update only the color of the target’s directional light, keeping its current direction.
- Parameters
string – target either
'3d'or'2dw'.table – color
{r, g, b, *a}(aoptional, defaults to1.0).
- setDirectionalLightColor(string target, number r, number g, number b, number * a)
Same as above passing the color channels directly.
8.4. Point Light¶
Note
setPointLight* functions below.8.4.1. setPointLight¶
- setPointLight(string target, table position, number radius, table color)
Set the legacy single point-light slot of a target (position, radius and color).
- Parameters
string – target either
'3d'or'2dw'.table – position
{x, y, z}(or a vec3).number – radius of influence. Negative values are clamped to
0.table – color
{r, g, b, *a}(aoptional, defaults to1.0).
Example:
mbm.setPointLight('3d', {x = 0, y = 0, z = 128}, 512, {r = 1, g = 1, b = 1, a = 1})
- setPointLight(string target, number x, number y, number z, number radius, number r, number g, number b, number * a)
Same as above passing position and color channels directly instead of tables.
8.4.2. setPointLightPosition¶
- setPointLightPosition(string target, table position)
Update only the position of the legacy single point-light slot.
- Parameters
string – target either
'3d'or'2dw'.table – position
{x, y, z}(or a vec3).
- setPointLightPosition(string target, number x, number y, number z)
Same as above passing the position channels directly.
8.4.3. setPointLightRadius¶
- setPointLightRadius(string target, number radius)
Update only the radius of the legacy single point-light slot. Negative values are clamped to
0.- Parameters
string – target either
'3d'or'2dw'.number – radius of influence.
8.4.4. setPointLightColor¶
- setPointLightColor(string target, table color)
Update only the color of the legacy single point-light slot.
- Parameters
string – target either
'3d'or'2dw'.table – color
{r, g, b, *a}(aoptional, defaults to1.0).
- setPointLightColor(string target, number r, number g, number b, number * a)
Same as above passing the color channels directly.
8.4.5. addPointLight¶
- addPointLight(string target, table position, number radius, table color)
Append a new point light to the target’s point-light list. There is no fixed cap enforced when adding - only getSelectedPointLights limits how many of them are actually used at render time (see setRequestedMaxLights).
- Parameters
string – target either
'3d'or'2dw'.table – position
{x, y, z}(or a vec3).number – radius of influence. Negative values are clamped to
0.table – color
{r, g, b, *a}(aoptional, defaults to1.0).
Example:
mbm.addPointLight('3d', {x = 100, y = 0, z = 0}, 300, {r = 1, g = 0, b = 0, a = 1})
mbm.addPointLight('3d', {x = -100, y = 0, z = 0}, 300, {r = 0, g = 0, b = 1, a = 1})
- addPointLight(string target, number x, number y, number z, number radius, number r, number g, number b, number * a)
Same as above passing position and color channels directly instead of tables.
8.4.6. clearPointLights¶
- clearPointLights(string target)
Remove every point light previously added with addPointLight for a target. This is the only way to remove point lights from the list; there is no function to remove a single entry by index.
- Parameters
string – target either
'3d'or'2dw'.
Example:
mbm.clearPointLights('3d')
8.5. Multi-light Limits & Selection¶
Note
The engine renders a bounded number of point lights per object (shader arrays need a fixed size). There are three related numbers per target: what the game requests, what the active backend actually supports, and what ends up validated (the smaller of the two).
8.5.1. setRequestedMaxLights¶
- setRequestedMaxLights(string target, number max_lights)
Request how many point lights should be considered per object for a target. Values below
1are silently raised to1. Requesting more than getSupportedMaxLights raises a Lua error.- Parameters
string – target either
'3d'or'2dw'.number – max lights requested.
Example:
mbm.setRequestedMaxLights('3d', 4)
8.5.2. getSupportedMaxLights¶
- getSupportedMaxLights(string target)
Get the maximum number of point lights the active backend supports for a target (currently a fixed engine constant regardless of graphics backend).
- Parameters
string – target either
'3d'or'2dw'.- Returns
number.
8.5.3. getValidatedMaxLights¶
- getValidatedMaxLights(string target)
Get the currently requested max lights re-validated against the backend’s supported max lights for a target.
- Parameters
string – target either
'3d'or'2dw'.- Returns
number.
8.5.4. setLightSelectionMode¶
- setLightSelectionMode(string target, string mode)
Set how point lights are selected per object for a target. Currently the only supported (and default) mode is
'per_object_nearest'.- Parameters
string – target either
'3d'or'2dw'.string – mode, exact string
'per_object_nearest'.
8.5.5. getSelectedPointLights¶
- getSelectedPointLights(string target, table objectCenter, table objectBoundingAABB)
Compute which point lights (from the list added through addPointLight) would affect an object, following the target’s selection mode. Lights whose distance to
objectCenteris greater than their own radius plus the object’s radius are discarded; the remaining ones are sorted by distance (nearest first) and truncated tomin(validatedMaxLights, supportedMaxLights)entries.- Parameters
string – target either
'3d'or'2dw'.table – objectCenter
{x, y, z}(or a vec3).table – objectBoundingAABB
{x, y, z}full size (not half-extents) of the object’s bounding box.
- Returns
1-indexed
tablearray, each entry shaped as{sourceIndex, distanceToObjectCenter, position={x,y,z}, radius, color={r,g,b,a}}.
Example:
local lights = mbm.getSelectedPointLights('3d', tMesh:getPos(), tMesh:getAABB())
for i, l in ipairs(lights) do
print(i, l.sourceIndex, l.distanceToObjectCenter, l.radius)
end