Content types
On this page
- content_prefabs
- content_samples
- thematic:noop
- status_effects
- thematic:status_effect
- damage_elements
- thematic:element
- vfx
- thematic:ring
- thematic:dome
- thematic:sphere
- thematic:column
- thematic:beam
- thematic:tornado
- thematic:helix
- thematic:burst
- thematic:atmospheric
- thematic:smoke_cloud
- thematic:puddle
- thematic:wall
- thematic:trail
- thematic:fog_layers
- thematic:bolt
- thematic:flame_pillar
- thematic:bat_swarm
- thematic:bubble
- thematic:pane
- thematic:tiles
- thematic:shock_ring
- thematic:ground_fracture
- thematic:dust_burst
- thematic:impact_lines
- thematic:pressure_wave
- thematic:shards
- thematic:flare
- thematic:implode
- thematic:fissure
- thematic:lock_on
- thematic:flame_curtain
- thematic:fire_bubble
- thematic:flame_dome
- thematic:strand_dome
- thematic:rope
- thematic:strand_burst
- thematic:fractal_bolt
- thematic:fork_wall
- thematic:fork_burst
- thematic:fork_cloud
- thematic:particle_system
- blocks
- thematic:solid
- thematic:glass
- thematic:slab
- thematic:stairs
- thematic:wall
- thematic:fence
- thematic:fence_gate
- thematic:door
- thematic:trapdoor
- thematic:pane
- thematic:pillar
- thematic:ladder
- thematic:chain
- thematic:button
- thematic:pressure_plate
- thematic:lightning_rod
- thematic:carpet
- thematic:furniture
- thematic:behavior
- thematic:lift_column
- thematic:brushable
- thematic:container
- thematic:player_inventory
- thematic:processor
- thematic:geo
- thematic:visual
- thematic:storage_link
- thematic:storage_conduit
- thematic:storage_terminal
- thematic:storage_port
- thematic:storage_hopper
- thematic:storage_uplink
- thematic:fabricator
- thematic:storage_core_array
- thematic:storage_drive
- items
- thematic:weapon
- thematic:weapon_equippable
- thematic:shield
- thematic:thrown_weapon
- thematic:tether_launcher
- thematic:melee
- thematic:ingredient
- thematic:modeled
- thematic:status_wearable
- thematic:spyglass
- thematic:fluid_container
- thematic:currency
- thematic:wallet
- thematic:food
- thematic:bound_link
- thematic:encoded_recipe
- thematic:spawn_egg
- thematic:bow
- thematic:loot_box
- thematic:upgrade_card
- thematic:data_core
- thematic:builder_tool
- arrows
- thematic:arrow
- throwables
- thematic:thrown
- criminals
- thematic:criminal
- entities
- thematic:thrown
- thematic:bolt
- thematic:tether
- thematic:zone
- thematic:owner_copy
- thematic:mob
- thematic:owned_summon
- thematic:vehicle
- thematic:seat
- thematic:pin
- thematic:strike
- thematic:arc
- thematic:mushroom_cloud
- thematic:perch
- thematic:strand
- professions
- thematic:profession
- armors
- thematic:suit
- thematic:ladder
- ability_effects
- thematic:action_list
- effect_visuals
- thematic:effect_visual
- anim_controllers
- thematic:suit_controllers
- encounters
- thematic:encounter
- arena_themes
- thematic:arena_theme
- pocket_dimensions
- thematic:pocket_dimension
- multiblocks
- thematic:multiblock
Every scripted content kind: the folder its files live in, the generic types a file picks with "type", the
fields and hooks each type takes, and the old type ids kept as aliases.
- The file name is the id.
data/<namespace>/<folder>/<any folders>/<id>.json(or.js) defines<namespace>:<id>; folders only organise. A family.jsfile may define several ids, naming each. - A
.jsfile calls its kind's global once:item("thematic:weapon", item => { item.set({...}); item.onHit(hit => ...); }).settakes the type's fields; each hook is a builder method (on_hitisonHit) whose callback is handed the sameActionsan ability's callbacks are, so every verb inthematic.d.tsworks there.use(id, options)applies a preset fromcontent_prefabs. The script runs once, at load, and builds the JSON a file would hold. - A hook in a file is an action list,
"on_use": [ ... ], or"on_use": { "cooldown": 2, "if": {guard}, "every": 5, ...options, "do": [ ... ] }. - Reload vs restart.
/reloadre-reads behaviour (hooks, stats, looks). A field marked identity changes what gets registered; changing it needs a restart, and a reload says so.
content_prefabs#
data/<namespace>/content_prefabs/, script global preset.
Preset libraries: data/<namespace>/content_prefabs/<any folders>/<file>.js. A file declares any number of presets, preset(id, { kind, doc, options }, (def, options) => { ... }), each a bundle of fields and hooks a definition of that kind applies by name with def.use(id, options). The function is handed the definition's own builder, so it calls the same set() and hook methods the file would. A bare id is thematic:.
content_samples#
data/<namespace>/content_samples/, script global contentSample, default type thematic:noop.
A sample kind that proves the scripted-content pipeline end to end; the engine ships no files of it. data/<namespace>/content_samples/<any folders>/<id>.json or .js.
thematic:noop#
Does nothing: its fields are read and kept, and its hook's actions run when the engine fires on_trigger, which nothing does.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
note | string | "" | free text, kept as it is | |
weight | number | 1 | yes | a number that would change registration if the kind registered anything |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_trigger | onTrigger | times how many times the actions run (1) | When the engine fires the sample's trigger (it never does). | owner, source: the entity it fired for; hit: none; stats: the definition's |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
Traits: sample_marker: no effect; shows where a type documents the traits it reads.
- Alias
thematic:noop_legacy: a definition naming it loads asthematic:noopwith{"note":"legacy"}under its own fields.
status_effects#
data/<namespace>/status_effects/, script global statusEffect, default type thematic:status_effect (registers at startup).
Status effects: data/<namespace>/status_effects/<any folders>/<id>.json or .js. The file name is the effect's id (status_effects/stun.json is thematic:stun). Each id registers its own status effect at startup, so a new one, or a changed category, colour, attribute modifier or stun flag, needs a restart; everything else reloads with /reload. How the effect looks on a suit is an effect_visuals file of the same id.
thematic:status_effect#
A status effect. Every field but category is optional; a file with only a category is an effect that does nothing but show (a marker other code or moves ask about).
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
category | "beneficial" | "harmful" | "neutral" | required | yes | whether the effect counts as good, bad or neither for the game (the icon's frame, milk, beacons) |
color | string | number | "#ffffff" | yes | the particle and potion colour, "#rrggbb" or a number |
attribute_modifiers | Array<{ attribute: string, uuid: string, amount: number, operation: "addition" | "multiply_base" | "multiply_total", per_level?: boolean }> | - | yes | attribute modifiers held on the body while the effect lasts, by attribute id ("minecraft:generic.movement_speed"); amount is multiplied by the amplifier + 1, as vanilla does, unless per_level is false (a flat amount at every level, for stacking effects whose level runs high). The uuid names the modifier: two effects sharing one replace each other |
stun | boolean | false | yes | a stun: a body with it can use no keybind, ability or item that is not stun-immune, and "clear": ["stun"] removes it |
tick_interval | number | - | ticks between the effect's ticks (1 is every tick), counted on the ticks it has left; left out, it never ticks, and item_cooldown, freeze_ticks and amplifier_by_duration do nothing | |
tick_interval_halves | boolean | false | each amplifier level halves tick_interval (interval >> amplifier, as vanilla's regeneration does); once that reaches 0 it ticks every tick | |
tick_interval_min | number | 0 | with tick_interval_halves, the fewest ticks between the effect's ticks however high the amplifier (which then counts as 0 to 31, so a huge one cannot wrap the halving round): 20, halves and 2 give 20, 10, 5, 2, 2... ticks | |
tick_damage | { damage_type: string, amount?: number, per_level?: number, credit_last_attacker?: boolean, ignore_hit_cooldown?: boolean, keep_velocity?: boolean } | Array<{ damage_type: string, amount?: number, per_level?: number, credit_last_attacker?: boolean, ignore_hit_cooldown?: boolean, keep_velocity?: boolean }> | - | on each tick (server side), a hit of amount + per_level x amplifier of the damage type ("thematic:bleed", "minecraft:in_wall"), in list order. credit_last_attacker: the body is the hit's source and whoever last attacked it gets the credit (otherwise the hit has no source); ignore_hit_cooldown: the invulnerability window is cleared for the hit and put back after it, so a drop neither gets swallowed by the window nor opens a new one; keep_velocity: the hit's knockback is taken back | |
ping | { particle: string, every?: number, count?: number, height?: number, spread?: number, speed?: number } | - | on the effect's ticks (server side, seen by everybody), count particles (a particle id that takes no options) at height of the body (0 feet, 1 head; default 0.5), spread each way, at speed, whenever the body's age is a multiple of every (default 1); needs tick_interval 1 to see every age | |
block_melee | boolean | false | a body with the effect lands no melee blow: a player's swing fails (on both sides), a mob's melee hit is cancelled; projectiles and moves still land | |
traits | string[] | - | wearer traits the body holds while it has the effect, on both sides, as if its suit declared them: ["no_sprint"] keeps a player from sprinting | |
readout | boolean | true | whether the HUD draws this effect's stack readout (the top-middle line with its level, bar and time left) when it has a stack and a level_decay; false hides that line and leaves the icon alone | |
heal_on_hit | { amount?: number, game_rule?: string, levels_to_full?: number } | - | each hit the holder lands heals it amount, or the value of the numeric game rule named game_rule ("lifeStealModifier"; amount stands in when there is none), times min(1, (amplifier + 1) / levels_to_full) when levels_to_full is set | |
tint | { color: string | number | [number, number, number], min?: number, max?: number, ramp_ticks?: number, pulse?: number, pulse_speed?: number, bright?: boolean, glow?: string | { texture: string, scroll?: number, strength?: number } } | - | the body is drawn in color ("#rrggbb", or [red, green, blue] from 0 to 1) times an intensity that climbs from min to max over the effect's last ramp_ticks, wobbles by pulse at pulse_speed radians per tick of the body's age, and stays between min and max (both default 1); bright draws it at full light so the colour glows in the dark (false); glow lays a texture ("thematic:textures/armor/molten.png") over the body adding its light, scrolling scroll of it a tick (0.01) at strength 0 to 1 (0.8) -- molten cracks, a crawling charge; the first effect on a body with a tint wins | |
pose | "lying" | - | how every body with the effect is drawn, a player's or a mob's: lying, rolled onto its side on the ground as a body falls when it dies (knocked flat); the first effect on a body with a pose wins. Only how it looks: its hitbox and movement are the effect's other fields' | |
overlay | { texture?: string, model?: { suit: string, within?: number, scale?: number, lift?: number, jitter?: number }, fade?: number, order?: number } | - | a texture ("thematic:textures/gui/flash_bang.png") drawn over the whole screen of a player with the effect (client side, only for that player), at an opacity of the seconds left over fade (default 1): solid until the last fade seconds, then fading out; with several at once, the lowest order (default 0) draws first and the next on top, then by effect id. model draws the head of the nearest player within within blocks (8) wearing the suit suit, close on the screen over the texture: scale times the screen's height (0.8), lift of the screen's height up from centre (0), jittered jitter pixels a frame (0); a texture, a model or both | |
item_cooldown | number | - | on each tick, a player's whole main inventory goes on this many ticks of item cooldown (server side), so nothing can be used while it lasts | |
freeze_ticks | number | - | on each tick, the body's frozen ticks are set to this (the powder snow shiver and frost overlay) | |
fog | { far: number, near?: number, max_level?: number, start?: number, color?: string | number } | - | while the client player has the effect, the world's fog closes in (client side, only for that player): fully dark at far blocks at level 1 (amplifier + 1), at near blocks at max_level (default 1; levels between interpolate linearly, further levels hold at near), in color ("#rrggbb", default black). The fog begins start (0.6) of the way out. Eased in and out as the level changes, so it never pops, and never further than vanilla's own fog (the tightest of several fogs wins) | |
stack | { max_level: number, hold: number } | - | how a stack_effect with by builds this effect, so the cap and the clock live in one place and not in every script: it never passes max_level (level = amplifier + 1), and each gain puts its length back to hold seconds | |
lift_cut | { per_level: number, max?: number, while?: string, no_flight_from?: number } | - | while the body has the effect, this share of its upward lift is taken away (0 to 1, so 0.33 leaves two thirds): per_level for each level (amplifier + 1), never above max (default 1). It cuts vanilla jumping, Thematic hover and fast flight lift and a web's upward pull, read off the synced effect so the client's prediction and the server agree. With while (an effect id, e.g. "example:weighed_down") it counts only while the body also has that effect, so a script can switch it on for a condition such as being in a fight. From level no_flight_from, hover and fast flight can't climb at all, whatever while says; jumps keep the plain cut | |
resisted_by | Array<{ effect: string, fog?: number, lift?: number }> | - | a body that also has the effect named here sees fog times as far through this effect's fog (still never past vanilla's own) and has this effect's lift_cut scaled by lift (0.67 is a third less); both default 1, and several resistances multiply. The named effect is usually a marker a passive keeps on its wearer, which the client sees too | |
level_decay | { every?: number, levels?: number } | - | when the effect runs out with levels left, it does not end: it comes back levels (1) lower for every (20) ticks, and so on down, until none are left. With a stack a hit refreshes to a few seconds (stack_effect with max_duration), the stack holds while hits keep coming and then wears off a step at a time | |
amplifier_by_duration | Array<[number, number]> | - | pairs [ticks left, amplifier]: on each tick the effect's amplifier becomes the one of the highest pair whose ticks left it has reached, so a long effect starts strong and eases as it runs out | |
damage_taken_multiplier | number | 1 | every hit the body takes is this many times as hard (1.15 is 15% more), added inside the hit so the invulnerability window cannot swallow it | |
damage_taken_per_level | number | 0 | every hit the body takes gains this share of itself per amplifier level (0.05: +5% at amplifier 0, +20% at 3), on top of damage_taken_multiplier | |
damage_taken_element | string | - | only hits made of this element ("psychic") take the damage_taken_multiplier and damage_taken_per_level share; left out, every hit does. A weakness worn for a while: 10% more psychic damage is { damage_taken_multiplier: 1.1, damage_taken_element: "psychic" } | |
damage_dealt_multiplier | number | - | every hit the body lands is this many times as hard (0.5 halves them, 0 turns them away); only the hits damage_dealt_origin names, when it is given | |
damage_dealt_origin | string[] | - | narrows damage_dealt_multiplier to the hits that leave from these places: "head", the eyes, head or mouth of a beam, a breath or a shot; left out, every hit | |
cooldown_moves | boolean | false | when the effect lands, the first amplifier + 1 of the wearer's suit moves that are not stun-immune and not running go on cooldown for as long as the effect lasts | |
player_animation | { clip?: string, priority: number } | - | a player-animator clip played on a player while the effect lasts, on a layer of this priority; clip left out, the one the anim controllers' effect_clips name for the effect |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_hit | onHit | - | runs when a body with the effect hits something (any damage it deals, turned away or not) | owner and source: the body with the effect; hit: the entity it struck; stats: duration and amplifier are the effect's own remaining ones |
on_hurt | onHurt | - | runs when a body with the effect is struck by a living attacker (any damage, turned away or not; not again while one on_hurt is already answering): thorns, retaliation | owner and source: the body with the effect; hit: the attacker; stats: duration and amplifier are the effect's own remaining ones |
on_expire | onExpire | - | runs on the server when the effect leaves the body: it runs out, is cleared (milk, a clear), or a stronger application replaces it (vanilla takes the old one off first) | owner and source: the body that carried the effect, at its position; no hit; stats: amplifier is the effect's, duration 0 |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
damage_elements#
data/<namespace>/damage_elements/, script global damageElement, default type thematic:element.
What a hit can be made of, for the weakness, resistance and immunity system: data/<namespace>/damage_elements/<any folders>/<id>.json or .js. The file name is the element's word (damage_elements/fire.json is "fire", the word suits, ability options and the element option use). The damage types themselves stay vanilla damage_type JSON; an element says which of them, and which damage-type tags, count as it. A hit also counts when its type is in the tag <namespace>:is_<id> (when the element has a damage_type) or <namespace>:compat/<mod>/<id> (while that compat module bridges damage types). Read on each side at startup and reloaded with /reload; a pack overrides an engine element by writing the same id.
thematic:element#
One damage element: what counts as it, and the colour it is shown in. An element with none of damage_type, tags and types is never matched, like "none".
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
damage_type | string | - | the element's own damage type (a vanilla damage_type JSON id, e.g. "thematic:fire"): what a move that hits with this element deals, and a hit of it always counts | |
tags | string[] | [] | damage-type tags whose members count as this element, e.g. ["minecraft:is_fire"], so lava burns a suit weak to fire | |
types | string[] | [] | damage types that simply are this element, for damage the game deals itself, e.g. ["minecraft:drown", "minecraft:in_wall"] | |
color | string | "gray" | the text colour the element is shown in (tooltips, the weakness line): one of black, dark_blue, dark_green, dark_aqua, dark_red, dark_purple, gold, gray, dark_gray, blue, green, aqua, red, light_purple, yellow, white |
vfx#
data/<namespace>/vfx/, script global vfxPreset, default type thematic:burst.
Named effects the vfx action plays: data/<namespace>/vfx/<any folders>/<id>.json or .js. The file name is the id (vfx/sonar_beam.json is thematic:sonar_beam); the old upper-case preset names still find them ("SONAR_BEAM" is thematic:sonar_beam). Read on the server, which sends the finished effect to every client near it, and reloaded with /reload.
thematic:ring#
Draws a ring of radius, height tall, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:dome#
Draws a dome of radius, height tall, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:sphere#
Draws a ball of radius, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:column#
Draws a column of radius, height long, along its direction (up when none), on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:beam#
Draws a beam height long along its direction (up when none), radius thick; played at a point it runs there, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:tornado#
Draws a funnel of radius, height tall, about its direction, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:helix#
Draws two strands wound about its direction, radius out and height long, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:burst#
Draws a burst out to radius, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:atmospheric#
Draws particles drifting through radius, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:smoke_cloud#
Draws a cloud of smoke of radius, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:puddle#
Draws a flat pool of radius on the ground, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:wall#
Draws a standing sheet radius wide either side of the point, along its direction, height tall, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:trail#
Draws a ribbon from the point along its direction for height, arcing up to radius / 2, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:fog_layers#
Draws stacked translucent fog banks of radius, spread over height from the feet up, each turning and drifting at its own pace, with wisps rising out of them; they fade in, hang, then thin out, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
layers | number | 5 | how many banks are stacked, from the feet up | |
speed | number | 1 | a multiplier on how fast each layer turns and drifts | |
color_variation | number | 0.12 | how far each layer's tint strays from color, 0-1 | |
fade_in | number | 0.35 | seconds to fade in | |
fade_out | number | 1.2 | seconds to thin out before the end | |
wisps | number | 8 | how many camera-facing wisps rise out of the banks |
thematic:bolt#
Draws a bolt, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:flame_pillar#
Draws a pillar of dark-hearted fire bursting height up out of the ground along its direction (up when none), radius wide, with a flash at its foot, tongues and rising embers; it shoots up, roars, then sinks and fades. color is its burning rim, the heart a dim shade of it, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:bat_swarm#
Draws density vanilla bats (the bat model and skin, or texture's), drawn on the client with no entities: radius out from the point, flying through height from the point up, lit by the world and tinted color ("#FFFFFFFF" shows the skin as it is); motion says how they fly, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
motion | "swirl" | "gather" | "scatter" | "flock" | "swirl" | swirl: they burst out of the point, circle it and break away outward; gather: they fly in, circle and close in on the point, vanishing into it; scatter: flung outward every way; flock: a loose flock fluttering about the point, heading wherever it moves (with the vfx action's follow, or riding a wave) | |
size | number | 1 | each bat's size, 1 being a vanilla bat |
thematic:bubble#
Draws a force-field bubble of radius about the point (lift raises it): a hex lattice of glowing lines, nearly clear where it faces the eye and bright towards its rim (color, its top byte the opacity, shading to rim_color), with a light band sweeping across the cells and ripples wherever a projectile crosses it or the body it follows is struck; motes may swirl into a glowing core or rise through it. It swells from grow of its radius over form seconds, holds for duration ticks (or, held under a session, until stopped) and then ends over release seconds as end says, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
cell | number | 0.6 | blocks across one hex cell: of a bubble's lattice (fewer, larger cells far off), of the pattern a pane's ripples draw (a tiles shape: one tile) | |
rim_color | string | - | "#RRGGBB": the colour its rim, ripples and motes shade to (color's own when left out) | |
rim | number | 1 | how bright its rim and edges glow, 1 being normal | |
waves | number | 0 | round instead of hex: a bubble gets a smooth rippling skin like the water shield's (this many radii of swing at the most, 0.02 is gentle), tiles and a pane's cells are drawn as circles; 0: hex | |
form | number | 0.25 | seconds it takes to form: a bubble swells from grow of its radius, a pane unfolds up from the floor | |
release | number | 0.25 | seconds its ending takes, after duration ticks or as soon as its session is stopped | |
motes | "none" | "swirl" | "rise" | "none" | what drifts inside it, density of them: swirl: spiral arms turning in towards the middle, faster near it (a vortex); rise: motes climbing in slow spirals, from the floor to half its radius up when it sits on the ground (no lift, anchor feet), else through the whole bubble | |
arms | number | 3 | a swirl's spiral arms, 1 to 8 | |
spin | number | 0.5 | degrees a tick the lattice turns about the vertical, and how fast a swirl or a rise turns | |
core | number | 0 | a glowing core at its middle, as a share of its radius, beating once a second (0: none) | |
end | "fade" | "collapse" | "burst" | "fade" | how it ends: fade where it is; collapse to a bright point; burst, swelling a third bigger as it fades | |
anchor | "feet" | "middle" | "eyes" | "feet" | where it sits on the body the vfx action's follow carries it with: a head-sized bubble takes eyes | |
arc | number | 0 | draws only the cap of the sphere within this many degrees of the direction the vfx action points it (a wave thrown ahead); 0: the whole sphere | |
belt | number | 0 | draws only the band this many blocks either side of its middle (an upright wave running out along the ground); 0: the whole sphere |
thematic:pane#
Draws an upright, nearly clear plate of force radius wide either side of the point and height tall, facing its direction (the vfx action's direction: "look" faces it the wearer's way; up is ignored): faint fill, a sliding sheen and softly glowing edges. Wherever a projectile crosses it, from either side, it flashes and a ring runs out uncovering a hex pattern of cell blocks. It unfolds up from the floor over form seconds and fades over release seconds after duration ticks or once stopped, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
cell | number | 0.6 | blocks across one hex cell: of a bubble's lattice (fewer, larger cells far off), of the pattern a pane's ripples draw (a tiles shape: one tile) | |
rim_color | string | - | "#RRGGBB": the colour its rim, ripples and motes shade to (color's own when left out) | |
rim | number | 1 | how bright its rim and edges glow, 1 being normal | |
waves | number | 0 | round instead of hex: a bubble gets a smooth rippling skin like the water shield's (this many radii of swing at the most, 0.02 is gentle), tiles and a pane's cells are drawn as circles; 0: hex | |
form | number | 0.25 | seconds it takes to form: a bubble swells from grow of its radius, a pane unfolds up from the floor | |
release | number | 0.25 | seconds its ending takes, after duration ticks or as soon as its session is stopped |
thematic:tiles#
Draws loose flat hex tiles, cell blocks across, at most density of them, laid out as layout says: ring (rings of tiles running out over the ground, each flipping up as the front passes), floor (a disc of tiles over the whole radius that peel up into the air height blocks, one by one, and come back down), swirl (streams of tiles spiralling in towards a bright core, with a tiled disc on the ground), spray (tiles flung out along the ground and up, tumbling, with a flash), wave (shells of tiles in a cone of arc degrees along the direction, each lighting as a front sweeps out to radius) or pull (a wave whose front sweeps in), on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
cell | number | 0.6 | blocks across one hex cell: of a bubble's lattice (fewer, larger cells far off), of the pattern a pane's ripples draw (a tiles shape: one tile) | |
rim_color | string | - | "#RRGGBB": the colour its rim, ripples and motes shade to (color's own when left out) | |
rim | number | 1 | how bright its rim and edges glow, 1 being normal | |
waves | number | 0 | round instead of hex: a bubble gets a smooth rippling skin like the water shield's (this many radii of swing at the most, 0.02 is gentle), tiles and a pane's cells are drawn as circles; 0: hex | |
form | number | 0.25 | seconds it takes to form: a bubble swells from grow of its radius, a pane unfolds up from the floor | |
release | number | 0.25 | seconds its ending takes, after duration ticks or as soon as its session is stopped | |
layout | "ring" | "floor" | "swirl" | "spray" | "wave" | "pull" | "ring" | how the tiles are laid out and move (see the shape) | |
arms | number | 3 | ring: how many staggered rings run out, 1 to 3; swirl: its arms of motes, 1 to 6 | |
spin | number | 0.5 | degrees a tick the tiles turn: a ring's, a swirl's or a spray's tumble | |
core | number | 0 | the flash or glow at the middle, as a share of radius (ring, swirl, spray; 0: none) | |
arc | number | 0 | wave and pull: half angle in degrees of the cone the tiles fill (0: 30) |
thematic:shock_ring#
Draws a concussive air burst standing across its direction (up when none): a flat front with a soft near-white condensation rim over a dusty wake races out to radius while travelling height along the direction (0 for one lying on the ground), with a faint cone back to the point when height is above 0; density is how many segments round it, so how smooth; lit by the world, tinted color (its alpha is how thick the front is), on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:ground_fracture#
Draws the ground split open: density jagged cracks run out from a crushed centre to radius, forking and joined by broken rings, each a dark seam (color) in a pale lip of dust, flat where it is played and lit by the world; they race out over the first ticks, sit, and fade at the end. With glow the seams burn in color instead, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:dust_burst#
Draws density soft, ragged dust billows thrown out low along the ground to radius, dragging to a stop as they swell and thin, with a heavier plume over the centre climbing to height; lit by the world, tinted color (its alpha is how thick the dust is), texture laid across each billow if named, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:impact_lines#
Draws comic-book speed lines bursting off the point in a flat star turned to the viewer: density streaks race out to radius from a hot flash, then thin away; color tints their tails, the heads are white, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:pressure_wave#
Draws a narrow cone of vapour thrown along its direction (up when none), radius across at the far end and height long: three soft bands race off the tip with streaks along the skin; lit by the world, tinted color (its alpha is how thick the vapour is); density is how many streaks, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:shards#
Draws density faceted crystal shards (at most 64) bursting out of a column height tall and radius / 5 wide at the point, flung about radius out, tumbling, falling with gravity and lying where they land until they fade at the end; color tints them and its alpha is how clear they are, glow draws them as light instead, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
size | number | 0.4 | a shard's length in blocks; each varies about it | |
gravity | number | 0.045 | blocks per tick per tick they fall by; 0 flies them straight out |
thematic:flare#
Draws a starburst glint facing the camera: density spikes (4 to 16, long and short in turn) radius long round a white-hot core, a flat shock ring racing out and a level streak across it; it flares in its first quarter and fades out, a parry's or a struck guard's flash, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:implode#
Draws density streaks (4 to 24) rushing in to the point from radius out over the first half of its life, then a jagged crack-star and a flash popping out of it: a crush, a snap, something squeezed until it breaks, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:fissure#
Draws density jagged cracks (3 to 12) torn across the ground from the point, each up to radius long and height wide at its root and forking once, round a dark broken patch; they rip open in the first eighth of its life with rims glowing color, cool to dark gashes and fade at the end. Lies flat on the level of the point, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:lock_on#
Draws corner brackets snapping in round a body and locking onto it, with a turning diamond at its middle and a broken ring at its feet: sized to the body it follows (vfx follow), else radius wide either side and height tall from the point. color is the brackets, a lighter shade the diamond, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:flame_curtain#
Draws a closed ring wall of fire radius round the point and height tall, dense enough to read as solid: an alpha-blended body of churning flame under counter-turning sheets of additive fire, tongues licking off a jagged top, a glow on the ground and embers rising; it rises in its first rise share of life, turns, heats from color to hot_color, then shrinks in and sputters out over its last fall share, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
hot_color | string | - | "#RRGGBB": the colour it heats to over its life (a curtain or dome) or its white-hot heart (a bubble); left out, it stays color | |
spin | number | 1 | how fast it turns, times its own pace | |
twist | number | 1 | how far its flames spiral round it as they climb, times its own | |
flicker | number | 1 | how much it licks, surges and sputters, times its own; 0 holds it steady | |
rise | number | 0.1 | the share of its life it takes to rise or swell to full | |
fall | number | 0.25 | the share at the end of its life over which it collapses and fades | |
narrow | number | 1 | a curtain's foot as a share of its radius, widening to the full radius at the top: 0.4 is a tornado's funnel, 1 a straight wall (0.05 to 1) |
thematic:fire_bubble#
Draws a ball of boiling fire swelling from the point out to radius over all but its last fall share of life: a seething shell brightest at its rim, color, round a white-hot hot_color flash that fades as it grows, corona tongues flicking off it and a shock ring racing over the ground under it (give it lift to centre it above the point), on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
hot_color | string | - | "#RRGGBB": the colour it heats to over its life (a curtain or dome) or its white-hot heart (a bubble); left out, it stays color | |
spin | number | 1 | how fast it turns, times its own pace | |
twist | number | 1 | how far its flames spiral round it as they climb, times its own | |
flicker | number | 1 | how much it licks, surges and sputters, times its own; 0 holds it steady | |
rise | number | 0.1 | the share of its life it takes to rise or swell to full | |
fall | number | 0.25 | the share at the end of its life over which it collapses and fades | |
narrow | number | 1 | a curtain's foot as a share of its radius, widening to the full radius at the top: 0.4 is a tornado's funnel, 1 a straight wall (0.05 to 1) |
thematic:flame_dome#
Draws a standing hemisphere of fire radius round the point: flames climb the shell from the ground and burn out toward its crown, hot_color at its foot fading through color, over a faint smoky body, tongues licking up round its rim and embers rising; it breathes slowly, flares in over its rise share and dies away over its fall share, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
hot_color | string | - | "#RRGGBB": the colour it heats to over its life (a curtain or dome) or its white-hot heart (a bubble); left out, it stays color | |
spin | number | 1 | how fast it turns, times its own pace | |
twist | number | 1 | how far its flames spiral round it as they climb, times its own | |
flicker | number | 1 | how much it licks, surges and sputters, times its own; 0 holds it steady | |
rise | number | 0.1 | the share of its life it takes to rise or swell to full | |
fall | number | 0.25 | the share at the end of its life over which it collapses and fades | |
narrow | number | 1 | a curtain's foot as a share of its radius, widening to the full radius at the top: 0.4 is a tornado's funnel, 1 a straight wall (0.05 to 1) |
thematic:strand_dome#
Draws a dome of web, radius out and height up (0.7 of radius when height is 0): density sets how many anchors ring its edge (6-20); a sheet splats over the floor with holes and heaped gobs, short strands glue its edge down, and every living body inside is draped in a shroud of web where it stands; it sags and collapses over its last 0.4 seconds. color is the web (its alpha the opacity), glow adds it as light, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:rope#
Draws a twisted line of thin white strands from the point along its direction, height long, that shoots out over its first ticks, sags a little and fades over its last 40%; color tints it (white leaves it as it is), on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:strand_burst#
Draws density web strands thrown out of the point in every direction (more up than down), up to radius long, each shooting out over its first ticks, sagging a little and fading over its last 40%; color tints them (white leaves them as they are), on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it |
thematic:fractal_bolt#
Draws a comic-book storm bolt from height above the point down to it: a zigzag of a few sharp straight stretches swinging about radius sideways with hard-angled forks that end in points, drawn in flat bands (a white core_color core, a glow_color band, a deeper rim) over a faint color bloom; it strikes for flash ticks, holding a pose for 3 ticks then snapping to a new shape, with a starburst and krackle dots where it lands, then hangs for afterglow ticks as its core dies and it thins; with scorch a dark cracked starburst stays on the ground under it for the rest of its life. Held (loop or hold) it crackles on as a standing column, re-snapping every 3 ticks, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
depth | number | 2 | levels of forks off the main channel, forks off forks (at most 2) | |
branch | number | 0.22 | 0 to 1: the chance each corner of a bolt throws a fork (scaled up a little, capped at 0.42) | |
width | number | 0.4 | the main channel's band width in blocks; the core is a third of it, the edge a sixth of it either side, each fork level a little over half its parent's | |
flash | number | 12 | ticks it strikes, snapping to a new pose every 3, before its afterglow (a burst: ticks it takes to spread out) | |
afterglow | number | 10 | ticks it hangs after the flash, its core dying first and its bloom lingering | |
scorch | boolean | false | leaves a dark scorch on the ground for the rest of its life (duration) | |
ground | boolean | false | fork_wall only: lies along the floor, arcs crawling across its lane | |
glow_color | string | "#39E0EC" | "#RRGGBB": the flat band round the core, its rim derived from it; color is the faint outer bloom | |
core_color | string | "#FFFFFF" | "#RRGGBB": the core |
thematic:fork_wall#
Draws a rolling wall of zigzag bolts radius either side of the point across its direction and height tall: density bolts side by side, stood on the ground and leaning into the way it goes, linked by arcs, their forks sweeping forward, krackle dots at their feet; moving (a wave's vfx), it leaves fading bolts behind it. With ground it lies along the floor instead: zigzags crawling across its lane, forks stabbing down. Poses hold 3 ticks; it fades over its last afterglow ticks, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
depth | number | 2 | levels of forks off the main channel, forks off forks (at most 2) | |
branch | number | 0.22 | 0 to 1: the chance each corner of a bolt throws a fork (scaled up a little, capped at 0.42) | |
width | number | 0.4 | the main channel's band width in blocks; the core is a third of it, the edge a sixth of it either side, each fork level a little over half its parent's | |
flash | number | 12 | ticks it strikes, snapping to a new pose every 3, before its afterglow (a burst: ticks it takes to spread out) | |
afterglow | number | 10 | ticks it hangs after the flash, its core dying first and its bloom lingering | |
scorch | boolean | false | leaves a dark scorch on the ground for the rest of its life (duration) | |
ground | boolean | false | fork_wall only: lies along the floor, arcs crawling across its lane | |
glow_color | string | "#39E0EC" | "#RRGGBB": the flat band round the core, its rim derived from it; color is the faint outer bloom | |
core_color | string | "#FFFFFF" | "#RRGGBB": the core |
thematic:fork_burst#
Draws zigzag bolts racing out along the ground from the point to radius over flash ticks, lengthening in steps (density / 4 of them, at most 8), krackle dots riding their heads and boiling at the middle where a starburst pops; then they hang for afterglow ticks and, with scorch, leave a cracked dark starburst with streaks along the bolts. No dome or ring, on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
depth | number | 2 | levels of forks off the main channel, forks off forks (at most 2) | |
branch | number | 0.22 | 0 to 1: the chance each corner of a bolt throws a fork (scaled up a little, capped at 0.42) | |
width | number | 0.4 | the main channel's band width in blocks; the core is a third of it, the edge a sixth of it either side, each fork level a little over half its parent's | |
flash | number | 12 | ticks it strikes, snapping to a new pose every 3, before its afterglow (a burst: ticks it takes to spread out) | |
afterglow | number | 10 | ticks it hangs after the flash, its core dying first and its bloom lingering | |
scorch | boolean | false | leaves a dark scorch on the ground for the rest of its life (duration) | |
ground | boolean | false | fork_wall only: lies along the floor, arcs crawling across its lane | |
glow_color | string | "#39E0EC" | "#RRGGBB": the flat band round the core, its rim derived from it; color is the faint outer bloom | |
core_color | string | "#FFFFFF" | "#RRGGBB": the core |
thematic:fork_cloud#
Draws a dark swirling cloud disc radius wide hung height above the point (density puffs, the middle turning faster than the rim) that fades in over half a second, with bolts stubbing down out of its underside and flashing it as they snap; use it held (hold or loop, with a session and follow), on every client that can see it, for duration ticks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifecycle | "once" | "loop" | "hold" | "once" | once: plays and ends; loop and hold: last while a vfx action's session holds them, until one with stop ends it | |
radius | number | 5 | blocks; the vfx action's radius replaces it | |
height | number | 2 | blocks; the length of an axial shape; the vfx action's height, or its to, replaces it | |
density | number | 20 | how many particles | |
duration | number | 30 | ticks | |
color | string | "#80FFFFFF" | "#AARRGGBB" (alpha first) or "#RRGGBB" (opaque) | |
texture | string | - | a texture (its full path, e.g. "minecraft:textures/entity/beacon_beam.png") the shape is drawn with instead of plain white | |
direction | [number, number, number] | up | the axis of an axial shape; the vfx action's direction or to replaces it | |
lift | number | 0 | blocks the whole shape is raised above where it is played | |
grow | number | 0 | a sphere or bubble only: 0 to 1, the share of its radius it starts at and swells from (a sphere over its whole life, staying solid until its last moments; a bubble over form seconds); 0 keeps a sphere's plain pop-out and fade | |
pulse | number | 0 | a sphere or bubble only: 0 to 1, how far it throbs in size and brightness (a sphere faster as it swells, a bubble once a second) | |
glow | boolean | false | a sphere, ground_fracture or shards only: drawn with its light added to the picture, so it burns bright rather than lying over it | |
depth | number | 2 | levels of forks off the main channel, forks off forks (at most 2) | |
branch | number | 0.22 | 0 to 1: the chance each corner of a bolt throws a fork (scaled up a little, capped at 0.42) | |
width | number | 0.4 | the main channel's band width in blocks; the core is a third of it, the edge a sixth of it either side, each fork level a little over half its parent's | |
flash | number | 12 | ticks it strikes, snapping to a new pose every 3, before its afterglow (a burst: ticks it takes to spread out) | |
afterglow | number | 10 | ticks it hangs after the flash, its core dying first and its bloom lingering | |
scorch | boolean | false | leaves a dark scorch on the ground for the rest of its life (duration) | |
ground | boolean | false | fork_wall only: lies along the floor, arcs crawling across its lane | |
glow_color | string | "#39E0EC" | "#RRGGBB": the flat band round the core, its rim derived from it; color is the faint outer bloom | |
core_color | string | "#FFFFFF" | "#RRGGBB": the core |
thematic:particle_system#
One of Thematic's particle systems, spawned once where it is played. Each system reads the numbers below its own way, and some ignore them (see system); a particle system has no session and no direction.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
system | string | required | the system: circle, unfilled_circle, tornado, whirlpool, helix, ground_slam, sonic_scream, solar_explosion, thick_smoke, green_haze (green dust; particle not read), spiral_tornado (a fixed 5.5-block spiral; only particle read), spinning_ring (a turning ring one block up, at most 18 particles), surge, green_wave (fixed; nothing read), fire_vortex, cloud_puff (particle not read) | |
particle | ParticleSpec | "minecraft:campfire_signal_smoke" | the particle it draws with: an id, or { type: "minecraft:dust", color, scale } | |
radius | number | 2 | blocks; the vfx action's radius replaces it | |
height | number | 1 | blocks; the vfx action's height replaces it | |
count | number | 32 | how many particles (the whirlpool and fire vortex read it as the tick that turns them) |
blocks#
data/<namespace>/blocks/, script global block, default type thematic:solid (registers at startup).
Blocks: data/<namespace>/blocks/<any folders>/<id>.json or .js registers the block <namespace>:<id> and its block item. Blocks are registry entries, read once at startup from mod jars, the dev tree and thematic/packs: a new block or a changed identity field needs a restart. The type is the block's shape and rules (a vanilla shape: solid, slab, stairs, wall, door...); a .json file names it (or a parent that does), a script's block(def => ...) is solid when it names none. Its model, blockstate, loot table and lang lines are ordinary resource files under the same id.
Fields every type takes:
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
copy | string | - | yes | a block (vanilla's, Thematic's, or a data block whose id sorts earlier) whose settings this one starts from: sounds, map colour, hardness, light, opacity; the fields below then change them |
hardness | number | - | yes | how long it takes to break (stone is 1.5; -1 cannot be broken) |
resistance | number | - | yes | how well it stands up to explosions (stone is 6) |
requires_tool | boolean | false | yes | drops nothing unless broken with the right tool (the mineable tags say which) |
luminance | number | { [property: string]: { [value: string]: number } } | 0 | yes | the light it gives, 0-15: a number, or per value of one of its state properties ({ "lit": { "true": 15 } }; a value left out gives 0) |
non_opaque | boolean | false | yes | light and faces behind it show through (glass, leaves); doors, trapdoors, panes, ladders, chains and lightning rods always are |
render_layer | "solid" | "cutout" | "cutout_mipped" | "translucent" | "solid" | how its textures are drawn: cutout for holes (leaves, grates), translucent for stained glass | |
block_set | string | "oak" | yes | the door, trapdoor, button and pressure plate sounds and rules it follows: a vanilla set ("oak", "iron", "stone"...) or Thematic's ("thematic:charred", "thematic:driftwood", "thematic:willow") |
wood_type | string | "oak" | yes | the fence gate sounds it uses: a vanilla wood ("oak", "cherry"...) or Thematic's ("thematic:charred"...) |
flammable | [burn: number, spread: number] | - | yes | fire catches and spreads on it, in vanilla's numbers (planks are [5, 20], logs [5, 5], leaves [30, 60]) |
strips_to | string | - | yes | the block an axe strips it into, keeping its axis; both must be pillars |
item | false | { creative_tab?: string, creative_order?: number, tooltip?: string | string[], rarity?: "common" | "uncommon" | "rare" | "epic" } | - | yes | its block item (same id): the tab it is listed in ("thematic:blocks"; data blocks follow the tab's own items, by creative_order then id), tooltip lines as translation keys, the name's colour; false for no item |
piston_behavior | "normal" | "destroy" | "block" | "push_only" | "ignore" | that of the block it copies (normal) | yes | what a piston does to it: normal pushes and pulls it, destroy breaks it (as amethyst buds), block stops the piston (as obsidian), push_only pushes but never pulls it (as a glazed terracotta), ignore leaves it alone |
drops | "self" | "none" | string | "self" | yes | what breaking it drops: self is its own loot table (data/<ns>/loot_tables/blocks/<id>.json, which the pack ships), none is nothing, a block id drops what that block drops |
enabled | boolean | true | yes | false leaves the block out |
requires | string | string[] | - | yes | the mod ids that must be loaded for the block to exist |
thematic:solid#
A full cube with no state (vanilla's plain Block): stone, planks, an ore. The default type.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
experience | [min: number, max: number] | - | yes | breaking it (without Silk Touch) drops this much experience, as an ore does |
thematic:glass#
A full see-through cube of glass; neighbours draw no face between them. Pair with render_layer translucent.
thematic:slab#
A slab (vanilla's SlabBlock): top, bottom or double, waterloggable. Its loot table decides that a double slab drops two.
thematic:stairs#
Stairs (vanilla's StairsBlock): faces the way it is placed, joins its neighbours into corners, waterloggable.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
base | string | "minecraft:stone" | yes | the block the stairs take their explosion and walk-on behaviour from |
thematic:wall#
A wall (vanilla's WallBlock): posts and low or tall sides joining its neighbours. List it in the minecraft:walls tag so others join it.
thematic:fence#
A fence (vanilla's FenceBlock): joins its neighbours, a leash ties to it. List it in minecraft:fences (and minecraft:wooden_fences for wood) so others join it.
thematic:fence_gate#
A fence gate (vanilla's FenceGateBlock): opens by hand or redstone, drops into a wall. Its sounds follow wood_type.
thematic:door#
A door (vanilla's DoorBlock): two blocks tall, opens by hand when its block_set allows (iron does not) and by redstone. Always non-opaque; breaks when a piston pushes it.
thematic:trapdoor#
A trapdoor (vanilla's TrapdoorBlock): top or bottom half, opens by hand when its block_set allows and by redstone, waterloggable. Always non-opaque.
thematic:pane#
A pane or bars (vanilla's PaneBlock): a thin cross joining its neighbours, waterloggable. Always non-opaque.
thematic:pillar#
A pillar (vanilla's PillarBlock): a log-like block along the axis it is placed on; strips_to needs one.
thematic:ladder#
A ladder (vanilla's LadderBlock): climbable, on a wall, waterloggable. Always non-opaque. List it in minecraft:climbable so it can be climbed.
thematic:chain#
A chain (vanilla's ChainBlock): a thin post along its axis, waterloggable. Always non-opaque.
thematic:button#
A button (vanilla's ButtonBlock): on a floor, wall or ceiling, gives a redstone pulse when pressed. No collision; breaks when pushed. Its sounds follow block_set.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
press_ticks | number | 30 | yes | how long a press lasts, in ticks (stone buttons are 20) |
arrows_press | boolean | true | yes | an arrow landing on it presses it, as on a wooden button |
thematic:pressure_plate#
A pressure plate (vanilla's PressurePlateBlock): powered while something stands on it. No collision; breaks when pushed. Its sounds follow block_set.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
activation | "everything" | "mobs" | "everything" | yes | what presses it: any entity (wooden), or only living ones (stone) |
thematic:lightning_rod#
A lightning rod (vanilla's LightningRodBlock): draws lightning strikes near it and gives a redstone pulse when struck, waterloggable. Always non-opaque.
thematic:carpet#
A carpet (vanilla's CarpetBlock): one pixel high, needs a block under it.
thematic:furniture#
Furniture: a block with its own shape (written once, facing north, in pixels) that faces the way it is placed, stands on the floor or hangs on a wall or ceiling, and may be waterlogged or sat on. Always non-opaque. Its model is an ordinary blockstate and model the pack ships, turned per facing.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
facing | "none" | "horizontal" | "all" | "look" | "all_horizontal" | "horizontal" | yes | which way it faces: none; horizontal (four ways, its front towards whoever placed it); all (six ways, away from the face it was placed on, as an end rod); look (six ways, towards whoever placed it, as a dispenser); all_horizontal (the six-way property of all, but placed as horizontal is: level, towards whoever placed it). Adds the facing state property |
flip | boolean | false | yes | turn the placed facing around: its front points away from whoever placed it (a block on a wall still faces away from the wall) |
attach | "floor" | "wall" | "ceiling" | "wall_or_floor" | "floor" | yes | where it can be placed: floor stands anywhere, as Thematic's furniture does; wall only against the side of a solid block, facing away from it; ceiling only under a block; wall_or_floor either, with a face state property (floor, wall) that shapes_by_state can give its own shape. Wall and ceiling blocks drop when their support goes. wall and wall_or_floor need facing: horizontal |
waterloggable | boolean | false | yes | it can hold water, as a slab can; adds the waterlogged state property |
shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | [[0, 0, 0, 16, 16, 16]] | yes | its outline, as boxes in pixels (0-16 across the block; up to 32 past it for a big piece), written facing north (the front is the z = 0 side, a wall block's back is z = 16) and turned for the other facings |
collision_shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | - | yes | what entities bump into, as shape; [] walks through it. Left out, it is the outline |
shapes_by_state | { [state: string]: [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] } | - | yes | a different outline for some states: "face=wall" (or several, "face=wall,waterlogged=true") to its north-facing boxes; the first entry a state matches wins, else shape |
footprint | [dx: number, dy: number, dz: number][] | - | yes | the neighbour cells its model reaches into, facing north (east, up and south are positive; [0, 0, -1] is the block in front), turned with it: it can only be placed where they are empty. Nothing is placed in them |
pick_item | string | - | the item pick-block gives; its own item when left out | |
seat | true | { offset_y?: number, tooltip?: string } | - | yes | players sit on it by using it with the main hand: offset_y is how far above the block's floor they sit, in blocks (0 for a chair, 0.35 for a stool); tooltip is a translation key shown in italics under its name (Thematic's chairs use block.thematic.chair.tooltip). Breaking or changing the block stands them up |
thematic:behavior#
A block with behaviour: a furniture block (every furniture field: its shape, facing, attach, seat...) that runs action lists at its moments (on_use, on_step, on_inside, on_collide, on_random_tick, on_scheduled_tick, on_break, on_neighbor, on_projectile_hit) with the verbs abilities and items use, may declare state properties of its own for its hooks to read and set, and takes the behaviour options (contact, ambient_particles, redstone, spread, layers, lift_column, jukebox, furnace). Hooks run on the server; the hooks, stats, contact, ambient_particles and spread reload with /reload, the rest needs a restart. Non-opaque unless opaque says otherwise; a furnace's block entity draws the block-entity visuals.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
facing | "none" | "horizontal" | "all" | "look" | "all_horizontal" | "horizontal" | yes | which way it faces: none; horizontal (four ways, its front towards whoever placed it); all (six ways, away from the face it was placed on, as an end rod); look (six ways, towards whoever placed it, as a dispenser); all_horizontal (the six-way property of all, but placed as horizontal is: level, towards whoever placed it). Adds the facing state property |
flip | boolean | false | yes | turn the placed facing around: its front points away from whoever placed it (a block on a wall still faces away from the wall) |
attach | "floor" | "wall" | "ceiling" | "wall_or_floor" | "floor" | yes | where it can be placed: floor stands anywhere, as Thematic's furniture does; wall only against the side of a solid block, facing away from it; ceiling only under a block; wall_or_floor either, with a face state property (floor, wall) that shapes_by_state can give its own shape. Wall and ceiling blocks drop when their support goes. wall and wall_or_floor need facing: horizontal |
waterloggable | boolean | false | yes | it can hold water, as a slab can; adds the waterlogged state property |
shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | [[0, 0, 0, 16, 16, 16]] | yes | its outline, as boxes in pixels (0-16 across the block; up to 32 past it for a big piece), written facing north (the front is the z = 0 side, a wall block's back is z = 16) and turned for the other facings |
collision_shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | - | yes | what entities bump into, as shape; [] walks through it. Left out, it is the outline |
shapes_by_state | { [state: string]: [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] } | - | yes | a different outline for some states: "face=wall" (or several, "face=wall,waterlogged=true") to its north-facing boxes; the first entry a state matches wins, else shape |
footprint | [dx: number, dy: number, dz: number][] | - | yes | the neighbour cells its model reaches into, facing north (east, up and south are positive; [0, 0, -1] is the block in front), turned with it: it can only be placed where they are empty. Nothing is placed in them |
pick_item | string | - | the item pick-block gives; its own item when left out | |
seat | true | { offset_y?: number, tooltip?: string } | - | yes | players sit on it by using it with the main hand: offset_y is how far above the block's floor they sit, in blocks (0 for a chair, 0.35 for a stool); tooltip is a translation key shown in italics under its name (Thematic's chairs use block.thematic.chair.tooltip). Breaking or changing the block stands them up |
properties | { [name: string]: "boolean" | string[] | { min: number, max: number, default?: number } | { values: string[] | "boolean", default?: string } } | - | yes | state properties of its own, which hooks read (state) and change (set_state): "boolean"; a list of names (the first is where a placed block starts); or numbers from min to max (0 or more). Its blockstate file needs a variant per combination, as for any property |
stats | { damage?: number, radius?: number, duration?: number, amplifier?: number } | - | the numbers its hooks' actions read when they leave their own out (duration in seconds) | |
contact | { on?: "inside" | "step" | "land", effects?: { effect: string, duration?: number, amplifier?: number, refresh_below?: number, ambient?: boolean, show_particles?: boolean }[], damage?: number | { amount: number, type?: string }, slow?: [x: number, y: number, z: number], consume_layer?: boolean } | - | what touching it does, with no action list: on is when (inside: standing in its cell, the default; step: walking on top; land: falling onto it); effects are status effects given to a living entity (duration in seconds, default 1; refresh_below: seconds -- given again only once the running one has less than that left); damage hurts it (a number, or { amount, type: a damage type id such as "minecraft:cactus" }); slow multiplies its movement as a cobweb does ([0.75, 0.75, 0.75]); consume_layer takes one of a layered block's layers each time it gives an effect or deals damage. The effects and damage happen on the server | |
ambient_particles | { particle?: string, count?: number, chance?: number, at?: [x: number, y: number, z: number], spread?: [x: number, y: number, z: number], velocity?: [x: number, y: number, z: number], important?: boolean, sound?: string, volume?: number, pitch?: number, when?: { [property: string]: string } } | { particle?: string, count?: number, chance?: number, at?: [x: number, y: number, z: number], spread?: [x: number, y: number, z: number], velocity?: [x: number, y: number, z: number], important?: boolean, sound?: string, volume?: number, pitch?: number, when?: { [property: string]: string } }[] | - | what it shows and plays by itself on the client, as a torch smokes: each entry rolls chance (default 1) every display tick, then shows count particles (a particle id with no options, such as "minecraft:cloud") at "at" (blocks from its lower north-west corner, default the centre) plus a random part of spread, moving at velocity, and plays sound (volume, pitch). when limits it to states ({ "lit": "true" }); important shows the particles from further away | |
redstone | { emit_on?: string[], power?: number, ticks?: number, from_property?: string, scale?: number, strong?: boolean } | - | yes | it gives off a redstone signal: emit_on lists hooks ("on_step", "on_use"...) whose firing turns it on at power (default 15) for ticks (default 20; adds the power state property, 0-15), or from_property names one of its number state properties the signal follows, times scale (default 1; the dartboard's score of 50 is 15 at 0.3). strong also powers the block it sits on or against |
spread | { chance?: number, into?: string[], stages: string[] } | - | it grows things into its neighbours on random ticks: with chance (0-1, default 0.2) a random side is picked; a cell there that is one of into ("air", "water" for a full source, or block ids; default ["air", "water"]) gets stages[0], and a stage already there facing that side grows into the next one. A stage with a facing property faces away from this block, and one that can hold water keeps the water it grew into | |
layers | true | { melt_interval?: number, melt_on_random_tick?: boolean } | - | yes | it stacks in layers of two pixels as snow does (adds the layers state property, 1-8; its own item adds a layer; it stands where snow can; mobs walk through it under five layers) and melts: a scheduled tick melts a layer and asks for the next melt_interval ticks later (default 40; 0 melts one and stops), a random tick melts one unless melt_on_random_tick is false, and the Nether melts it whole. Its outline follows its layers, so shape is not used |
lift_column | string | { column_block: string, delay?: number } | - | it is the source of a lift column (a fan): shortly after it is placed, and when the column's carrier block is put on top of it, the carrier blocks stacked above it become column_block (a thematic:lift_column block, which lists this block among its rising or lowering sources). delay is in ticks (default 20). A bare string is column_block | |
jukebox | true | { block_entity?: string, ticks?: boolean } | - | yes | it plays music discs: using it with a disc puts it in and plays it, using it again or breaking it throws the disc out; a playing disc gives a redstone signal of 15 and a comparator reads it. Adds the has_record state property. block_entity is the block-entity id its disc is saved under (default the block's own id; blocks may share one); ticks: false stops the disc's clock (the song never ends and shows no notes) |
furnace | true | { recipe_type?: "smelting" | "smoking" | "blasting", block_entity?: string, title?: string } | - | yes | it cooks as a furnace (smelting, the default), smoker (smoking) or blast furnace (blasting) does, with that furnace's screen: lit while it burns (adds the lit state property), drops its items and stored experience when broken, and a comparator reads how full it is. block_entity is the block-entity id its items are saved under (default the block's own id; blocks may share one); title is the screen's translation key (default the block's name) |
hardness_by_state | { when: { [property: string]: string }, hardness: number }[] | - | how hard it is to break in some states, the first entry whose when matches (as a hook's state does): a machine that can not be broken while it is damaged, only repaired. -1 can not be broken at all; a state no entry matches breaks at the block's own hardness | |
opaque | boolean | false | yes | it hides what is behind it and blocks light, as stone does, instead of being non-opaque as furniture is; only for a block that fills its whole cell (or a layered one, as snow is) |
item_display | { slots: { slot?: number | number[], offset?: [number, number, number], rotation?: [number, number, number], scale?: number, mode?: "fixed" | "gui" | "ground" | "head" }[], cull?: boolean, glint_light?: number } | - | yes | items its block entity draws from its own inventory: each of slots shows slot (0; a list shows the first that is not empty) at offset [x, y, z] from the block's corner as if it faced north ([0.5, 0.5, 0.5]; turned with its facing), turned by rotation [x, y, z] degrees, at scale (0.5), drawn as mode (fixed, as an item frame does). cull hides the items past the display-stand distance and behind walls, as Thematic's render settings say for display stands; glint_light is the lowest block light an enchanted item is lit with (0, none). Only a block entity with an inventory that it sends to the client (a container's) has items to show |
light_beam | { texture?: string, color?: [number, number, number], length?: number, radius?: number, glow_radius?: number, tilt?: number, origin?: [number, number, number], end_texture?: string, end_size?: number, end_alpha?: number, active_when?: { base_block: string, pattern?: "below" | "3x3_below" | [number, number, number][] } } | - | yes | a beacon-style beam its block entity draws: texture ("minecraft:textures/entity/beacon_beam.png"), color [r, g, b] 0-1 ([1, 1, 1]), length in blocks (64, up to 1024), radius and glow_radius (the core's and the glow's half-width, 0.2 and 0.25), tilt in degrees towards its facing (0, straight up), origin [x, y, z] from the block's corner ([0.5, 1, 0.5]; not turned with its facing, only the tilt is), end_texture a picture across its far end (end_size its half-width, 4; end_alpha 0-1, about 0.59). active_when shows it only while every cell of pattern (3x3_below, the default; below; or [dx, dy, dz] cells) is base_block, checked every tick on the server and saved with the block entity as Active; left out, it always shows |
text_readout | { source: string, color?: number | string, offset?: [number, number, number], rotation?: [number, number, number], scale?: number, shadow?: boolean, glow?: boolean, billboard?: boolean } | - | yes | a line of text its block entity draws: source is "state:<property>" (that state property's value), "item:<slot>" (the name of the item in that inventory slot), "count:<slot>" (how many) or "text:<translation key>"; color 0xRRGGBB or "#RRGGBB" (white); offset [x, y, z] is the line's top middle from the block's corner as if it faced north ([0.5, 1.25, 0.5]; turned with its facing), rotation [x, y, z] degrees after that; scale is the line's height in blocks (0.2); shadow draws a drop shadow, glow ignores the light, billboard always faces the viewer |
book | { texture: string, open_when?: string, frantic_when?: string, offset?: [number, number, number], scale?: number, near?: number } | - | yes | vanilla's enchanting-table book, drawn floating over the block with its own texture (<ns>:<path> is a full path, e.g. thematic:textures/entity/my_book.png, in the layout of vanilla's entity/enchanting_table_book.png), bobbing and turning to face the nearest player within near blocks (3). open_when is when it is open: "player_near" (default, as the enchanting table), "always", or "state:<property>=<value>" to follow the block state ("state:phase=charged"). frantic_when (same forms; default never) makes it wide open and flipping pages fast. offset [x, y, z] from the block's corner is its resting place ([0.5, 0.75, 0.5], the table's); scale 1 is vanilla's size |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_use | onUse | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own; hand which hand's click runs it; empty_hand runs only when that hand holds nothing, so a click with a block in hand still places it against this one; transform a click while the block stands on one of requires_below (a block id or a list; left out, any) turns it into replace_with (a block id, air by default) and leaves count (1) of the item drop where it stood, instead of the hook's actions, a seat or anything else the click would do: a throne on an altar breaking into a book | a player uses it (right-clicks it); the click is answered (the arm swings) whenever it runs | owner and source: the player; hit: the block; the point: where they clicked (on_break: the block's centre). The stats are the definition's stats |
on_step | onStep | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own | an entity walks on top of it (every tick it does) | no owner and no source (a block has none); hit: the entity touching it, so damage, effect and the other target verbs land on it; the point: where it is. The stats are the definition's stats |
on_inside | onInside | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own | an entity is inside its cell (every tick it is; a block with a collision shape is entered only where it is not solid) | no owner and no source (a block has none); hit: the entity touching it, so damage, effect and the other target verbs land on it; the point: where it is. The stats are the definition's stats |
on_collide | onCollide | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own | an entity falls onto it (once, as it lands) | no owner and no source (a block has none); hit: the entity touching it, so damage, effect and the other target verbs land on it; the point: where it is. The stats are the definition's stats |
on_random_tick | onRandomTick | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own | a random tick (on average every 68 seconds at the default random tick speed; a block takes them when it has this hook, spread or layers at startup) | no owner and no source; hit: the block itself; the point: its centre. The stats are the definition's stats |
on_scheduled_tick | onScheduledTick | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own | a scheduled tick comes due: one a hook's schedule asked for (or a behaviour: layers melting, a redstone signal ending, a lift column filling, which share the block's scheduled tick) | no owner and no source; hit: the block itself; the point: its centre. The stats are the definition's stats |
on_break | onBreak | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own | a player breaks it | owner and source: the player; hit: the block; the point: where they clicked (on_break: the block's centre). The stats are the definition's stats |
on_neighbor | onNeighbor | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own | a neighbouring block changes, a redstone signal next to it included | no owner and no source; hit: the block itself; the point: its centre. The stats are the definition's stats |
on_projectile_hit | onProjectileHit | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own; players_only only a projectile a player shot runs it; hit_rings sets a state property from where the hit landed, after the actions (over set_state): the distance from the middle of the struck face, in blocks (0.5 reaches an edge's middle), picks the first ring whose radius it is under, smallest first, else outside; top_or_bottom is what a hit on the top or bottom face sets instead (left out, those faces have rings too). A target's score: { property: "score", rings: [[0.2, 50], [0.4, 25]], outside: 5 } | a projectile (an arrow, a snowball, a thrown gadget) hits it | owner: whoever shot it (none for a dispenser's); source: the projectile; hit: the face it struck; the point: where. The stats are the definition's stats |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
thematic:lift_column#
A lift column: the air-like block a lift-column source (a block with lift_column naming this one) fills the carrier blocks stacked above it with. Whoever stands in it is lifted (above a source_up block) or lowered (above a source_down block), as in a bubble column; it puffs particles at its top, stands only on itself or a source, turns back into the carrier when the source goes, and has no collision. Adds the drag state property (true lowers).
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
via | string | required | yes | the carrier block the column fills and turns back into when its source goes (the bat pole); the column picks as it, and should drop as it ("drops": its id) |
source_up | string[] | - | yes | the blocks under the column that make it lift (their lift_column names this block) |
source_down | string[] | - | yes | the blocks under the column that make it lower |
particle | string | "minecraft:cloud" | the puffs it shows at its top and inside, a particle id with no options |
thematic:brushable#
A suspicious block: a brush uncovers the loot its block entity holds (set the vanilla way: a structure, or a LootTable tag), it falls like sand, and once brushed clean it becomes base_block. Adds the dusted state property (0-3). Start it from vanilla's with "copy": "minecraft:suspicious_sand".
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
base_block | string | required | yes | what it becomes once brushed clean (a block registered before it: vanilla's, Thematic's, or a data block whose id sorts earlier) |
brush_sound | string | "minecraft:item.brush.brushing.sand" | yes | the sound each brush stroke makes |
brushed_sound | string | "minecraft:item.brush.brushing.sand.complete" | yes | the sound it makes when brushed clean |
block_entity | string | its own id | yes | the block-entity id it is saved under; blocks may share one |
thematic:container#
A container: a furniture block (every furniture field but seat: its shape, facing, attach...) with a storage of its own that players open with a screen (the chest screen of its rows, or one the engine bound), as Thematic's cabinets, crates and trash cans. Its items drop when it is broken and a comparator reads how full it is. Its block entity is saved under block_entity, which containers may share. Its block entity may draw the block-entity visuals (item_display shows what is in it, as the display stands). Always non-opaque.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
facing | "none" | "horizontal" | "all" | "look" | "all_horizontal" | "horizontal" | yes | which way it faces: none; horizontal (four ways, its front towards whoever placed it); all (six ways, away from the face it was placed on, as an end rod); look (six ways, towards whoever placed it, as a dispenser); all_horizontal (the six-way property of all, but placed as horizontal is: level, towards whoever placed it). Adds the facing state property |
flip | boolean | false | yes | turn the placed facing around: its front points away from whoever placed it (a block on a wall still faces away from the wall) |
attach | "floor" | "wall" | "ceiling" | "wall_or_floor" | "floor" | yes | where it can be placed: floor stands anywhere, as Thematic's furniture does; wall only against the side of a solid block, facing away from it; ceiling only under a block; wall_or_floor either, with a face state property (floor, wall) that shapes_by_state can give its own shape. Wall and ceiling blocks drop when their support goes. wall and wall_or_floor need facing: horizontal |
waterloggable | boolean | false | yes | it can hold water, as a slab can; adds the waterlogged state property |
shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | [[0, 0, 0, 16, 16, 16]] | yes | its outline, as boxes in pixels (0-16 across the block; up to 32 past it for a big piece), written facing north (the front is the z = 0 side, a wall block's back is z = 16) and turned for the other facings |
collision_shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | - | yes | what entities bump into, as shape; [] walks through it. Left out, it is the outline |
shapes_by_state | { [state: string]: [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] } | - | yes | a different outline for some states: "face=wall" (or several, "face=wall,waterlogged=true") to its north-facing boxes; the first entry a state matches wins, else shape |
footprint | [dx: number, dy: number, dz: number][] | - | yes | the neighbour cells its model reaches into, facing north (east, up and south are positive; [0, 0, -1] is the block in front), turned with it: it can only be placed where they are empty. Nothing is placed in them |
pick_item | string | - | the item pick-block gives; its own item when left out | |
container | true | { rows?: number, size?: number, title?: string, sound_open?: string, sound_close?: string, open_property?: string, void_on_close?: boolean, void_on_insert?: boolean, screen?: string, respect_claims?: boolean } | - | yes | its storage: rows of nine slots (1-6, default 3), opened with the chest screen of that many rows; title is the screen's translation key (default the block's name); sound_open / sound_close play at its front when the first viewer opens it and the last closes it (default the barrel's); open_property names a boolean state property it adds and sets true while anyone looks in ("open"); void_on_close destroys what is left in it when the last viewer closes it; void_on_insert destroys whatever a player or a hopper puts in it at once, so it always reads empty and nothing can be taken out (a trash can); screen is a screen handler id Java bound a screen to, and size its slot count when that screen shows fewer than rows x 9; respect_claims (default true) keeps out a player the land-claim or spawn-protection check refuses. Its items are saved under Items, drop when it is broken, and a comparator reads how full it is |
block_entity | string | its own id | yes | the block-entity id its items are saved under (a converted block keeps its old one); blocks of the same kind may share one |
item_display | { slots: { slot?: number | number[], offset?: [number, number, number], rotation?: [number, number, number], scale?: number, mode?: "fixed" | "gui" | "ground" | "head" }[], cull?: boolean, glint_light?: number } | - | yes | items its block entity draws from its own inventory: each of slots shows slot (0; a list shows the first that is not empty) at offset [x, y, z] from the block's corner as if it faced north ([0.5, 0.5, 0.5]; turned with its facing), turned by rotation [x, y, z] degrees, at scale (0.5), drawn as mode (fixed, as an item frame does). cull hides the items past the display-stand distance and behind walls, as Thematic's render settings say for display stands; glint_light is the lowest block light an enchanted item is lit with (0, none). Only a block entity with an inventory that it sends to the client (a container's) has items to show |
light_beam | { texture?: string, color?: [number, number, number], length?: number, radius?: number, glow_radius?: number, tilt?: number, origin?: [number, number, number], end_texture?: string, end_size?: number, end_alpha?: number, active_when?: { base_block: string, pattern?: "below" | "3x3_below" | [number, number, number][] } } | - | yes | a beacon-style beam its block entity draws: texture ("minecraft:textures/entity/beacon_beam.png"), color [r, g, b] 0-1 ([1, 1, 1]), length in blocks (64, up to 1024), radius and glow_radius (the core's and the glow's half-width, 0.2 and 0.25), tilt in degrees towards its facing (0, straight up), origin [x, y, z] from the block's corner ([0.5, 1, 0.5]; not turned with its facing, only the tilt is), end_texture a picture across its far end (end_size its half-width, 4; end_alpha 0-1, about 0.59). active_when shows it only while every cell of pattern (3x3_below, the default; below; or [dx, dy, dz] cells) is base_block, checked every tick on the server and saved with the block entity as Active; left out, it always shows |
text_readout | { source: string, color?: number | string, offset?: [number, number, number], rotation?: [number, number, number], scale?: number, shadow?: boolean, glow?: boolean, billboard?: boolean } | - | yes | a line of text its block entity draws: source is "state:<property>" (that state property's value), "item:<slot>" (the name of the item in that inventory slot), "count:<slot>" (how many) or "text:<translation key>"; color 0xRRGGBB or "#RRGGBB" (white); offset [x, y, z] is the line's top middle from the block's corner as if it faced north ([0.5, 1.25, 0.5]; turned with its facing), rotation [x, y, z] degrees after that; scale is the line's height in blocks (0.2); shadow draws a drop shadow, glow ignores the light, billboard always faces the viewer |
book | { texture: string, open_when?: string, frantic_when?: string, offset?: [number, number, number], scale?: number, near?: number } | - | yes | vanilla's enchanting-table book, drawn floating over the block with its own texture (<ns>:<path> is a full path, e.g. thematic:textures/entity/my_book.png, in the layout of vanilla's entity/enchanting_table_book.png), bobbing and turning to face the nearest player within near blocks (3). open_when is when it is open: "player_near" (default, as the enchanting table), "always", or "state:<property>=<value>" to follow the block state ("state:phase=charged"). frantic_when (same forms; default never) makes it wide open and flipping pages fast. offset [x, y, z] from the block's corner is its resting place ([0.5, 0.75, 0.5], the table's); scale 1 is vanilla's size |
thematic:player_inventory#
A bench for one of the user's own inventories: a furniture block (every furniture field but seat) that, used, opens that inventory's screen, as Thematic's gadget and arrow benches do. It keeps nothing itself, so it has no block entity. Always non-opaque.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
facing | "none" | "horizontal" | "all" | "look" | "all_horizontal" | "horizontal" | yes | which way it faces: none; horizontal (four ways, its front towards whoever placed it); all (six ways, away from the face it was placed on, as an end rod); look (six ways, towards whoever placed it, as a dispenser); all_horizontal (the six-way property of all, but placed as horizontal is: level, towards whoever placed it). Adds the facing state property |
flip | boolean | false | yes | turn the placed facing around: its front points away from whoever placed it (a block on a wall still faces away from the wall) |
attach | "floor" | "wall" | "ceiling" | "wall_or_floor" | "floor" | yes | where it can be placed: floor stands anywhere, as Thematic's furniture does; wall only against the side of a solid block, facing away from it; ceiling only under a block; wall_or_floor either, with a face state property (floor, wall) that shapes_by_state can give its own shape. Wall and ceiling blocks drop when their support goes. wall and wall_or_floor need facing: horizontal |
waterloggable | boolean | false | yes | it can hold water, as a slab can; adds the waterlogged state property |
shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | [[0, 0, 0, 16, 16, 16]] | yes | its outline, as boxes in pixels (0-16 across the block; up to 32 past it for a big piece), written facing north (the front is the z = 0 side, a wall block's back is z = 16) and turned for the other facings |
collision_shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | - | yes | what entities bump into, as shape; [] walks through it. Left out, it is the outline |
shapes_by_state | { [state: string]: [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] } | - | yes | a different outline for some states: "face=wall" (or several, "face=wall,waterlogged=true") to its north-facing boxes; the first entry a state matches wins, else shape |
footprint | [dx: number, dy: number, dz: number][] | - | yes | the neighbour cells its model reaches into, facing north (east, up and south are positive; [0, 0, -1] is the block in front), turned with it: it can only be placed where they are empty. Nothing is placed in them |
pick_item | string | - | the item pick-block gives; its own item when left out | |
player_inventory | { inventory: string, size?: number, requires_clear_above?: boolean, refuse_if?: string | { check: string, message?: string }, screen?: string, title?: string } | required | yes | opens one of the user's own inventories rather than a storage of its own: inventory is its name ("gadgets", "quiver"), grown to size slots first (default 36); requires_clear_above (default true) keeps it shut under a solid block; refuse_if names a check the engine provides ("fixed_roster": the suit fills that inventory itself) and message the action-bar line a refused player sees; screen names the screen the engine bound (default the inventory's name); title is the screen's translation key (default the block's name). Anyone may open it |
thematic:processor#
A processor: a furniture block (every furniture field but seat: its shape, facing, attach...) that makes a recipe type's recipes from its input slots, as Thematic's alloy smelter, centrifuge and plate press: through a screen the engine bound, or by hand in the world. With fuel it burns furnace fuel and adds the lit state property. Its items drop when it is broken. Its block entity is saved under block_entity, which processors may share. Its block entity may draw a geo model (geo, with working and resting clips) and the block-entity visuals (item_display...); what follows its items or its work (item_display, an item or count text_readout, the working and resting clips) needs interaction in_world, which sends them to the players. Non-opaque unless opaque says otherwise.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
facing | "none" | "horizontal" | "all" | "look" | "all_horizontal" | "horizontal" | yes | which way it faces: none; horizontal (four ways, its front towards whoever placed it); all (six ways, away from the face it was placed on, as an end rod); look (six ways, towards whoever placed it, as a dispenser); all_horizontal (the six-way property of all, but placed as horizontal is: level, towards whoever placed it). Adds the facing state property |
flip | boolean | false | yes | turn the placed facing around: its front points away from whoever placed it (a block on a wall still faces away from the wall) |
attach | "floor" | "wall" | "ceiling" | "wall_or_floor" | "floor" | yes | where it can be placed: floor stands anywhere, as Thematic's furniture does; wall only against the side of a solid block, facing away from it; ceiling only under a block; wall_or_floor either, with a face state property (floor, wall) that shapes_by_state can give its own shape. Wall and ceiling blocks drop when their support goes. wall and wall_or_floor need facing: horizontal |
waterloggable | boolean | false | yes | it can hold water, as a slab can; adds the waterlogged state property |
shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | [[0, 0, 0, 16, 16, 16]] | yes | its outline, as boxes in pixels (0-16 across the block; up to 32 past it for a big piece), written facing north (the front is the z = 0 side, a wall block's back is z = 16) and turned for the other facings |
collision_shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | - | yes | what entities bump into, as shape; [] walks through it. Left out, it is the outline |
shapes_by_state | { [state: string]: [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] } | - | yes | a different outline for some states: "face=wall" (or several, "face=wall,waterlogged=true") to its north-facing boxes; the first entry a state matches wins, else shape |
footprint | [dx: number, dy: number, dz: number][] | - | yes | the neighbour cells its model reaches into, facing north (east, up and south are positive; [0, 0, -1] is the block in front), turned with it: it can only be placed where they are empty. Nothing is placed in them |
pick_item | string | - | the item pick-block gives; its own item when left out | |
processor | { recipe_type: string, input_slots?: number, fuel?: boolean, output_slots?: number, interaction?: "screen" | "in_world" | "instant", time?: number, rest_ticks?: number, done_sound?: string, done_particles?: string, screen?: string, title?: string, nbt_keys?: { progress?: string, total?: string, burn?: string, working?: string, resting?: string, slots?: string[] }, charges?: { revert_to: string, revert_sound?: string, revert_particles?: string }, imbue?: { pay?: "health" | "item", fill?: number, per_use?: number, min_health?: number, with_item?: string, item?: string, consume?: boolean, use_sound?: string, full_sound?: string, full_volume?: number, full_pitch?: number, requires?: { sky?: boolean, clear?: { radius: number, height: number } }, refuse_sound?: string, refuse_volume?: number, refuse_pitch?: number, on_full: { encounter: string, grant_charges?: number, fail_keep?: number } } } | required | yes | the machine: it matches recipe_type's recipes (a registered recipe type id, e.g. "minecraft:smelting") against its input_slots (default 1, in order), works for the recipe's time (or time, default 200 ticks), then takes one of each input and adds the output to the first of its output_slots (default 1) with room. fuel (default false) adds a fuel slot after the inputs that burns furnace fuel, and the lit state property while it burns; without fuel it works whenever a recipe fits and may rest rest_ticks after each output. interaction: screen (default) opens the screen Java bound to the screen handler id screen (titled title, default the block's name); in_world takes an item that makes a recipe by hand, one at a time, and hands the output back when used empty-handed; instant takes one of the held item that makes a recipe on its own and turns it into the output at once, handed to the player (dropped at them when the inventory is full), whatever time says. done_sound and done_particles (a particle type id) play at each output. Hoppers feed it from above (inputs) and the sides (fuel, else inputs) and empty it from below. Its items are saved under Items and its clock under ProcessTime / ProcessTimeTotal / BurnTime; nbt_keys renames them (slots: one key per slot instead of Items) so a converted machine reads its old saves. charges makes it a ritual block: it adds the phase state property (dormant, awakening, charged), crafting works only while charged and spends the recipe's charge_cost for every item made, no hopper can reach it, and at none left it becomes revert_to (revert_sound, revert_particles play) while its items drop as usual. imbue is how a player charges it: while dormant, using it with an empty hand (or holding with_item) pays per_use health (display units, 1000 is a full bar, never below min_health) and adds one point to a meter that fills at fill. pay: "item" instead takes a main-hand click holding item (consumed unless consume is false) and adds per_use points (default fill, so one item fills it). A full meter plays full_sound (volume, pitch), awakens it and starts the on_full.encounter on the player, a win charges it with grant_charges, anything else keeps fail_keep (0-1) of the meter; requires gates the start: sky needs the block above to see the sky, clear needs the square of radius around the block (its own column excluded) to be air or replaceable plants for height levels from the block up, and when unmet nothing is taken, refuse_sound (volume, pitch) plays and smoke hints at the blocking spots to that player; each accepted use plays use_sound. Breaking it keeps its phase, charges and meter in the dropped item |
block_entity | string | its own id | yes | the block-entity id its items are saved under (a converted block keeps its old one); blocks of the same kind may share one |
opaque | boolean | false | yes | it hides what is behind it and blocks light, as a furnace does, instead of being non-opaque as furniture is; only for a machine that fills its whole cell |
geo | { model?: string, texture?: string, render_type?: "cutout" | "translucent" | "emissive", animation?: { idle?: string, working?: string, resting?: string }, glow?: string[], item_geo?: boolean | { scale?: number, offset?: [number, number, number] } } | - | yes | its geo model: model <ns>:<path> is assets/<ns>/geo/block/<path>.geo.json, with its clips in assets/<ns>/animations/block/<path>.animation.json (the block's id); texture <ns>:<path> is assets/<ns>/textures/block/<path>.png (the model's id); render_type cutout (see-through pixels), translucent (glassy) or emissive (lit whatever the light); glow the names of bones drawn a second time at full brightness whatever the light, so a dark model has parts that shine; animation.idle the clip it loops; animation.working the clip it plays and holds while its block entity works and animation.resting the one it plays while it rests after an output (an in_world processor's only; the plate press's press_down and press_retract); item_geo draws its item with the model (true; the pack's item model needs "parent": "builtin/entity" and its display transforms), false leaves it to its item model, { scale, offset } tunes the draw |
item_display | { slots: { slot?: number | number[], offset?: [number, number, number], rotation?: [number, number, number], scale?: number, mode?: "fixed" | "gui" | "ground" | "head" }[], cull?: boolean, glint_light?: number } | - | yes | items its block entity draws from its own inventory: each of slots shows slot (0; a list shows the first that is not empty) at offset [x, y, z] from the block's corner as if it faced north ([0.5, 0.5, 0.5]; turned with its facing), turned by rotation [x, y, z] degrees, at scale (0.5), drawn as mode (fixed, as an item frame does). cull hides the items past the display-stand distance and behind walls, as Thematic's render settings say for display stands; glint_light is the lowest block light an enchanted item is lit with (0, none). Only a block entity with an inventory that it sends to the client (a container's) has items to show |
light_beam | { texture?: string, color?: [number, number, number], length?: number, radius?: number, glow_radius?: number, tilt?: number, origin?: [number, number, number], end_texture?: string, end_size?: number, end_alpha?: number, active_when?: { base_block: string, pattern?: "below" | "3x3_below" | [number, number, number][] } } | - | yes | a beacon-style beam its block entity draws: texture ("minecraft:textures/entity/beacon_beam.png"), color [r, g, b] 0-1 ([1, 1, 1]), length in blocks (64, up to 1024), radius and glow_radius (the core's and the glow's half-width, 0.2 and 0.25), tilt in degrees towards its facing (0, straight up), origin [x, y, z] from the block's corner ([0.5, 1, 0.5]; not turned with its facing, only the tilt is), end_texture a picture across its far end (end_size its half-width, 4; end_alpha 0-1, about 0.59). active_when shows it only while every cell of pattern (3x3_below, the default; below; or [dx, dy, dz] cells) is base_block, checked every tick on the server and saved with the block entity as Active; left out, it always shows |
text_readout | { source: string, color?: number | string, offset?: [number, number, number], rotation?: [number, number, number], scale?: number, shadow?: boolean, glow?: boolean, billboard?: boolean } | - | yes | a line of text its block entity draws: source is "state:<property>" (that state property's value), "item:<slot>" (the name of the item in that inventory slot), "count:<slot>" (how many) or "text:<translation key>"; color 0xRRGGBB or "#RRGGBB" (white); offset [x, y, z] is the line's top middle from the block's corner as if it faced north ([0.5, 1.25, 0.5]; turned with its facing), rotation [x, y, z] degrees after that; scale is the line's height in blocks (0.2); shadow draws a drop shadow, glow ignores the light, billboard always faces the viewer |
book | { texture: string, open_when?: string, frantic_when?: string, offset?: [number, number, number], scale?: number, near?: number } | - | yes | vanilla's enchanting-table book, drawn floating over the block with its own texture (<ns>:<path> is a full path, e.g. thematic:textures/entity/my_book.png, in the layout of vanilla's entity/enchanting_table_book.png), bobbing and turning to face the nearest player within near blocks (3). open_when is when it is open: "player_near" (default, as the enchanting table), "always", or "state:<property>=<value>" to follow the block state ("state:phase=charged"). frantic_when (same forms; default never) makes it wide open and flipping pages fast. offset [x, y, z] from the block's corner is its resting place ([0.5, 0.75, 0.5], the table's); scale 1 is vanilla's size |
thematic:geo#
A block drawn by a geo model: a furniture block (every furniture field: its shape, facing, attach, seat...) whose block entity draws the model named after its id (geo.model to name another), turned with its facing, looping geo.animation.idle if it has one; its item is drawn with the same model unless geo.item_geo is false. It takes light_beam and text_readout too (its block entity holds no items, so no item_display). The block model the pack ships is only used for breaking particles. Always non-opaque.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
facing | "none" | "horizontal" | "all" | "look" | "all_horizontal" | "horizontal" | yes | which way it faces: none; horizontal (four ways, its front towards whoever placed it); all (six ways, away from the face it was placed on, as an end rod); look (six ways, towards whoever placed it, as a dispenser); all_horizontal (the six-way property of all, but placed as horizontal is: level, towards whoever placed it). Adds the facing state property |
flip | boolean | false | yes | turn the placed facing around: its front points away from whoever placed it (a block on a wall still faces away from the wall) |
attach | "floor" | "wall" | "ceiling" | "wall_or_floor" | "floor" | yes | where it can be placed: floor stands anywhere, as Thematic's furniture does; wall only against the side of a solid block, facing away from it; ceiling only under a block; wall_or_floor either, with a face state property (floor, wall) that shapes_by_state can give its own shape. Wall and ceiling blocks drop when their support goes. wall and wall_or_floor need facing: horizontal |
waterloggable | boolean | false | yes | it can hold water, as a slab can; adds the waterlogged state property |
shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | [[0, 0, 0, 16, 16, 16]] | yes | its outline, as boxes in pixels (0-16 across the block; up to 32 past it for a big piece), written facing north (the front is the z = 0 side, a wall block's back is z = 16) and turned for the other facings |
collision_shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | - | yes | what entities bump into, as shape; [] walks through it. Left out, it is the outline |
shapes_by_state | { [state: string]: [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] } | - | yes | a different outline for some states: "face=wall" (or several, "face=wall,waterlogged=true") to its north-facing boxes; the first entry a state matches wins, else shape |
footprint | [dx: number, dy: number, dz: number][] | - | yes | the neighbour cells its model reaches into, facing north (east, up and south are positive; [0, 0, -1] is the block in front), turned with it: it can only be placed where they are empty. Nothing is placed in them |
pick_item | string | - | the item pick-block gives; its own item when left out | |
seat | true | { offset_y?: number, tooltip?: string } | - | yes | players sit on it by using it with the main hand: offset_y is how far above the block's floor they sit, in blocks (0 for a chair, 0.35 for a stool); tooltip is a translation key shown in italics under its name (Thematic's chairs use block.thematic.chair.tooltip). Breaking or changing the block stands them up |
geo | { model?: string, texture?: string, render_type?: "cutout" | "translucent" | "emissive", animation?: { idle?: string, working?: string, resting?: string }, glow?: string[], item_geo?: boolean | { scale?: number, offset?: [number, number, number] } } | {} | yes | its geo model: model <ns>:<path> is assets/<ns>/geo/block/<path>.geo.json, with its clips in assets/<ns>/animations/block/<path>.animation.json (the block's id); texture <ns>:<path> is assets/<ns>/textures/block/<path>.png (the model's id); render_type cutout (see-through pixels), translucent (glassy) or emissive (lit whatever the light); glow the names of bones drawn a second time at full brightness whatever the light, so a dark model has parts that shine; animation.idle the clip it loops; animation.working the clip it plays and holds while its block entity works and animation.resting the one it plays while it rests after an output (an in_world processor's only; the plate press's press_down and press_retract); item_geo draws its item with the model (true; the pack's item model needs "parent": "builtin/entity" and its display transforms), false leaves it to its item model, { scale, offset } tunes the draw |
light_beam | { texture?: string, color?: [number, number, number], length?: number, radius?: number, glow_radius?: number, tilt?: number, origin?: [number, number, number], end_texture?: string, end_size?: number, end_alpha?: number, active_when?: { base_block: string, pattern?: "below" | "3x3_below" | [number, number, number][] } } | - | yes | a beacon-style beam its block entity draws: texture ("minecraft:textures/entity/beacon_beam.png"), color [r, g, b] 0-1 ([1, 1, 1]), length in blocks (64, up to 1024), radius and glow_radius (the core's and the glow's half-width, 0.2 and 0.25), tilt in degrees towards its facing (0, straight up), origin [x, y, z] from the block's corner ([0.5, 1, 0.5]; not turned with its facing, only the tilt is), end_texture a picture across its far end (end_size its half-width, 4; end_alpha 0-1, about 0.59). active_when shows it only while every cell of pattern (3x3_below, the default; below; or [dx, dy, dz] cells) is base_block, checked every tick on the server and saved with the block entity as Active; left out, it always shows |
text_readout | { source: string, color?: number | string, offset?: [number, number, number], rotation?: [number, number, number], scale?: number, shadow?: boolean, glow?: boolean, billboard?: boolean } | - | yes | a line of text its block entity draws: source is "state:<property>" (that state property's value), "item:<slot>" (the name of the item in that inventory slot), "count:<slot>" (how many) or "text:<translation key>"; color 0xRRGGBB or "#RRGGBB" (white); offset [x, y, z] is the line's top middle from the block's corner as if it faced north ([0.5, 1.25, 0.5]; turned with its facing), rotation [x, y, z] degrees after that; scale is the line's height in blocks (0.2); shadow draws a drop shadow, glow ignores the light, billboard always faces the viewer |
block_entity | string | - | yes | the id its block entity is saved under (its own id); several geo and visual blocks may share one |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_use | onUse | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own; hand which hand's click runs it; empty_hand runs only when that hand holds nothing, so a click with a block in hand still places it against this one; transform a click while the block stands on one of requires_below (a block id or a list; left out, any) turns it into replace_with (a block id, air by default) and leaves count (1) of the item drop where it stood, instead of the hook's actions, a seat or anything else the click would do: a throne on an altar breaking into a book | a player uses it (right-clicks it); the click is answered (the arm swings) whenever it runs | owner and source: the player; hit: the block; the point: where they clicked (on_break: the block's centre). The stats are the definition's stats |
on_break | onBreak | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own | a player breaks it | owner and source: the player; hit: the block; the point: where they clicked (on_break: the block's centre). The stats are the definition's stats |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
thematic:visual#
A block whose block entity draws on it: a furniture block (every furniture field) with its ordinary block model, plus at least one block-entity visual (light_beam, text_readout; its block entity holds no items, so no item_display). Always non-opaque.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
facing | "none" | "horizontal" | "all" | "look" | "all_horizontal" | "horizontal" | yes | which way it faces: none; horizontal (four ways, its front towards whoever placed it); all (six ways, away from the face it was placed on, as an end rod); look (six ways, towards whoever placed it, as a dispenser); all_horizontal (the six-way property of all, but placed as horizontal is: level, towards whoever placed it). Adds the facing state property |
flip | boolean | false | yes | turn the placed facing around: its front points away from whoever placed it (a block on a wall still faces away from the wall) |
attach | "floor" | "wall" | "ceiling" | "wall_or_floor" | "floor" | yes | where it can be placed: floor stands anywhere, as Thematic's furniture does; wall only against the side of a solid block, facing away from it; ceiling only under a block; wall_or_floor either, with a face state property (floor, wall) that shapes_by_state can give its own shape. Wall and ceiling blocks drop when their support goes. wall and wall_or_floor need facing: horizontal |
waterloggable | boolean | false | yes | it can hold water, as a slab can; adds the waterlogged state property |
shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | [[0, 0, 0, 16, 16, 16]] | yes | its outline, as boxes in pixels (0-16 across the block; up to 32 past it for a big piece), written facing north (the front is the z = 0 side, a wall block's back is z = 16) and turned for the other facings |
collision_shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | - | yes | what entities bump into, as shape; [] walks through it. Left out, it is the outline |
shapes_by_state | { [state: string]: [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] } | - | yes | a different outline for some states: "face=wall" (or several, "face=wall,waterlogged=true") to its north-facing boxes; the first entry a state matches wins, else shape |
footprint | [dx: number, dy: number, dz: number][] | - | yes | the neighbour cells its model reaches into, facing north (east, up and south are positive; [0, 0, -1] is the block in front), turned with it: it can only be placed where they are empty. Nothing is placed in them |
pick_item | string | - | the item pick-block gives; its own item when left out | |
seat | true | { offset_y?: number, tooltip?: string } | - | yes | players sit on it by using it with the main hand: offset_y is how far above the block's floor they sit, in blocks (0 for a chair, 0.35 for a stool); tooltip is a translation key shown in italics under its name (Thematic's chairs use block.thematic.chair.tooltip). Breaking or changing the block stands them up |
light_beam | { texture?: string, color?: [number, number, number], length?: number, radius?: number, glow_radius?: number, tilt?: number, origin?: [number, number, number], end_texture?: string, end_size?: number, end_alpha?: number, active_when?: { base_block: string, pattern?: "below" | "3x3_below" | [number, number, number][] } } | - | yes | a beacon-style beam its block entity draws: texture ("minecraft:textures/entity/beacon_beam.png"), color [r, g, b] 0-1 ([1, 1, 1]), length in blocks (64, up to 1024), radius and glow_radius (the core's and the glow's half-width, 0.2 and 0.25), tilt in degrees towards its facing (0, straight up), origin [x, y, z] from the block's corner ([0.5, 1, 0.5]; not turned with its facing, only the tilt is), end_texture a picture across its far end (end_size its half-width, 4; end_alpha 0-1, about 0.59). active_when shows it only while every cell of pattern (3x3_below, the default; below; or [dx, dy, dz] cells) is base_block, checked every tick on the server and saved with the block entity as Active; left out, it always shows |
text_readout | { source: string, color?: number | string, offset?: [number, number, number], rotation?: [number, number, number], scale?: number, shadow?: boolean, glow?: boolean, billboard?: boolean } | - | yes | a line of text its block entity draws: source is "state:<property>" (that state property's value), "item:<slot>" (the name of the item in that inventory slot), "count:<slot>" (how many) or "text:<translation key>"; color 0xRRGGBB or "#RRGGBB" (white); offset [x, y, z] is the line's top middle from the block's corner as if it faced north ([0.5, 1.25, 0.5]; turned with its facing), rotation [x, y, z] degrees after that; scale is the line's height in blocks (0.2); shadow draws a drop shadow, glow ignores the light, billboard always faces the viewer |
block_entity | string | - | yes | the id its block entity is saved under (its own id); several geo and visual blocks may share one |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_use | onUse | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own; hand which hand's click runs it; empty_hand runs only when that hand holds nothing, so a click with a block in hand still places it against this one; transform a click while the block stands on one of requires_below (a block id or a list; left out, any) turns it into replace_with (a block id, air by default) and leaves count (1) of the item drop where it stood, instead of the hook's actions, a seat or anything else the click would do: a throne on an altar breaking into a book | a player uses it (right-clicks it); the click is answered (the arm swings) whenever it runs | owner and source: the player; hit: the block; the point: where they clicked (on_break: the block's centre). The stats are the definition's stats |
on_break | onBreak | state runs only while the block's state properties have these values ({ "repair": "default" }), as block-state strings; set_state after the actions, sets these state properties on the block: a value ("damaged", "true", "3"), "cycle" for the next value, or "+1" / "-1" to count a number property up (held at its highest) or down (below its lowest the block is used up and removed, as a last layer melts); schedule after the actions, asks for a scheduled tick this many ticks later, which fires on_scheduled_tick. Scheduled ticks are saved with the chunk, so one survives the chunk unloading and fires when it loads again; one already waiting is kept; cooldown_group the cooldown (the cooldown option) is shared by every hook and block naming this group, per player (per block when no player is behind the hook); left out, each hook of each block has its own | a player breaks it | owner and source: the player; hit: the block; the point: where they clicked (on_break: the block's centre). The stats are the definition's stats |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
thematic:storage_link#
A storage link: a full cube that joins the inventories (chests, barrels, any modded container) touching its faces to the storage network it is part of. Adjacent network blocks (links, conduits, terminals) form one network. Items are inserted into higher priority links first, preferring inventories that already hold the item.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
priority | number | 0 | inserts go to higher priority links first; ties fill the inventory that already holds the item | |
sides | ("down" | "up" | "north" | "south" | "west" | "east")[] | all six | the faces whose neighbouring inventory is joined |
thematic:storage_conduit#
A storage conduit: a cable that extends the storage network, connecting to every adjacent network block. Adds the north, east, south, west, up and down boolean state properties (true when connected) for the blockstate to draw arms by. Always non-opaque.
thematic:storage_terminal#
A storage terminal: an interface type for a storage network. A furniture block (every furniture field but seat: its shape, facing, attach...) that, used, opens the items of the network it touches (only while the block is in the #thematic:storage_terminals tag; otherwise it is decoration) in a screen with a search box (name, @mod, #tag, $tooltip), a sort button and compact counts. theme sets the screen's look with no Java (title, frame texture, colours, boot sound, scanlines) and features turns on a 3x3 crafting grid that refills from the network. blueprints (it needs crafting) adds a blueprint slot with an Encode button and autocrafting: craftable items show with a marker even at zero, middle-click opens a request, and a job list shows the fabricator jobs. A pack may define as many terminals as it likes, each as small as { "parent": "thematic:batcomputer", "theme": { "accent": "#7CFF4F" } } (or "theme": "<preset>"); tools/new_storage_terminal.py writes the block's other files. Its crafting grid is saved in its block entity (block_entity, default its own id) and drops, with the blueprint, when it is broken. Always non-opaque.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
facing | "none" | "horizontal" | "all" | "look" | "all_horizontal" | "horizontal" | yes | which way it faces: none; horizontal (four ways, its front towards whoever placed it); all (six ways, away from the face it was placed on, as an end rod); look (six ways, towards whoever placed it, as a dispenser); all_horizontal (the six-way property of all, but placed as horizontal is: level, towards whoever placed it). Adds the facing state property |
flip | boolean | false | yes | turn the placed facing around: its front points away from whoever placed it (a block on a wall still faces away from the wall) |
attach | "floor" | "wall" | "ceiling" | "wall_or_floor" | "floor" | yes | where it can be placed: floor stands anywhere, as Thematic's furniture does; wall only against the side of a solid block, facing away from it; ceiling only under a block; wall_or_floor either, with a face state property (floor, wall) that shapes_by_state can give its own shape. Wall and ceiling blocks drop when their support goes. wall and wall_or_floor need facing: horizontal |
waterloggable | boolean | false | yes | it can hold water, as a slab can; adds the waterlogged state property |
shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | [[0, 0, 0, 16, 16, 16]] | yes | its outline, as boxes in pixels (0-16 across the block; up to 32 past it for a big piece), written facing north (the front is the z = 0 side, a wall block's back is z = 16) and turned for the other facings |
collision_shape | [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] | - | yes | what entities bump into, as shape; [] walks through it. Left out, it is the outline |
shapes_by_state | { [state: string]: [x1: number, y1: number, z1: number, x2: number, y2: number, z2: number][] } | - | yes | a different outline for some states: "face=wall" (or several, "face=wall,waterlogged=true") to its north-facing boxes; the first entry a state matches wins, else shape |
footprint | [dx: number, dy: number, dz: number][] | - | yes | the neighbour cells its model reaches into, facing north (east, up and south are positive; [0, 0, -1] is the block in front), turned with it: it can only be placed where they are empty. Nothing is placed in them |
pick_item | string | - | the item pick-block gives; its own item when left out | |
theme | string | { preset?: string, title?: string, frame?: string, accent?: string, background?: string, text?: string, boot_sound?: string, scanlines?: boolean, gui?: string } | - | yes | the screen's look, so one Java screen serves every terminal. A bare string is a preset (a palette from data/<ns>/terminal_themes/<name>.json, e.g. "wayne"), and preset: "name" inside the object starts from one with the other keys overriding it. With a "parent", the child's keys override the parent's one by one (a preset replaces the parent's whole theme), except title, which is never inherited. Keys: title (a lang key or plain text; default the block's name), frame (a texture id, a 32x32 image whose 8-pixel border frames the panel; default a plain drawn frame), accent / background / text (hex colours "#RRGGBB" or "#AARRGGBB"; defaults cyan, dark slate, pale blue), boot_sound (a sound id played when it opens), scanlines (faint horizontal lines over the panel, default false), gui (a texture folder "namespace:path" holding your own art: <path>/base.png, tinted with background, and <path>/accent.png, tinted with accent, two 256x256 sheets laid out like the engine's thematic:storage; default thematic:storage) |
features | { crafting?: boolean, blueprints?: boolean, bench_link?: boolean } | - | yes | what the terminal offers besides the item grid: crafting adds a 3x3 crafting grid whose ingredients refill from the network (default false); blueprints (needs crafting) adds a blueprint slot with an Encode button and autocrafting requests and a job list for the network's fabricators (default false); bench_link is reserved for the suit bench and read but not used yet |
uplink_range | number | 16 | yes | how far (blocks) a player carrying a link chip bound to this terminal may be from it and still open it remotely, with no uplink; an uplink on its network extends that |
block_entity | string | its own id | yes | the block-entity id its items are saved under (a converted block keeps its old one); blocks of the same kind may share one |
thematic:storage_port#
A storage port: a cube that faces an inventory and moves items between it and the storage network it is part of. Placed against a block it faces it. Used, it opens a screen with nine ghost filter slots (whitelist or blacklist, match data, match by tag with a tag filter card, only what the destination already holds), upgrade card slots (speed, bulk, tag filter), a redstone mode and, for dispatch, an amount to keep in stock. Its filter and cards are saved in its block entity (block_entity, default its own id); the cards drop when it is broken.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
mode | "intake" | "dispatch" | "intake" | intake pulls from the inventory the port faces into the network; dispatch pushes filtered items from the network into that inventory | |
rate | number | 8 | items moved per operation, before bulk cards | |
interval | number | 20 | ticks between operations, before speed cards | |
card_slots | number | 2 | upgrade card slots, 0 to 6 | |
theme | string | { preset?: string, title?: string, frame?: string, accent?: string, background?: string, text?: string, boot_sound?: string, scanlines?: boolean, gui?: string } | - | yes | the screen's look, so one Java screen serves every terminal. A bare string is a preset (a palette from data/<ns>/terminal_themes/<name>.json, e.g. "wayne"), and preset: "name" inside the object starts from one with the other keys overriding it. With a "parent", the child's keys override the parent's one by one (a preset replaces the parent's whole theme), except title, which is never inherited. Keys: title (a lang key or plain text; default the block's name), frame (a texture id, a 32x32 image whose 8-pixel border frames the panel; default a plain drawn frame), accent / background / text (hex colours "#RRGGBB" or "#AARRGGBB"; defaults cyan, dark slate, pale blue), boot_sound (a sound id played when it opens), scanlines (faint horizontal lines over the panel, default false), gui (a texture folder "namespace:path" holding your own art: <path>/base.png, tinted with background, and <path>/accent.png, tinted with accent, two 256x256 sheets laid out like the engine's thematic:storage; default thematic:storage) |
block_entity | string | its own id | yes | the block-entity id its items are saved under (a converted block keeps its old one); blocks of the same kind may share one |
thematic:storage_hopper#
A storage hopper: a storage port in a hopper's shape that connects to the network by touching it. Its spout faces down or sideways, set from the clicked face as a hopper's is. An intake hopper vacuums the item entities in the space above it and pulls from the inventory directly above, into the network; what the network cannot take stays where it was. An output hopper pushes items the filter names from the network through its spout into the inventory it points at; with an empty filter it does nothing. Powered, it is locked like a hopper unless the screen's redstone mode says otherwise. It has a port's filter, cards and screen, and moves 1 item every 8 ticks by default.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
mode | "intake" | "dispatch" | "intake" | intake pulls from the inventory the port faces into the network; dispatch pushes filtered items from the network into that inventory | |
rate | number | 1 | items moved per operation, before bulk cards | |
interval | number | 8 | ticks between operations, before speed cards | |
card_slots | number | 2 | upgrade card slots, 0 to 6 | |
theme | string | { preset?: string, title?: string, frame?: string, accent?: string, background?: string, text?: string, boot_sound?: string, scanlines?: boolean, gui?: string } | - | yes | the screen's look, so one Java screen serves every terminal. A bare string is a preset (a palette from data/<ns>/terminal_themes/<name>.json, e.g. "wayne"), and preset: "name" inside the object starts from one with the other keys overriding it. With a "parent", the child's keys override the parent's one by one (a preset replaces the parent's whole theme), except title, which is never inherited. Keys: title (a lang key or plain text; default the block's name), frame (a texture id, a 32x32 image whose 8-pixel border frames the panel; default a plain drawn frame), accent / background / text (hex colours "#RRGGBB" or "#AARRGGBB"; defaults cyan, dark slate, pale blue), boot_sound (a sound id played when it opens), scanlines (faint horizontal lines over the panel, default false), gui (a texture folder "namespace:path" holding your own art: <path>/base.png, tinted with background, and <path>/accent.png, tinted with accent, two 256x256 sheets laid out like the engine's thematic:storage; default thematic:storage) |
drop_items | boolean | false | an output hopper whose spout points at no inventory drops the items there as item entities (for item conveyors) | |
block_entity | string | its own id | yes | the block-entity id its items are saved under (a converted block keeps its old one); blocks of the same kind may share one |
thematic:storage_uplink#
A storage uplink: a full cube on the storage network that relays it to players carrying a bound link chip. A player can open a terminal from afar when they are within the terminal's own uplink_range of it, within range of any uplink on its network, or anywhere when the network has a cross_dimension uplink.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
range | number | 64 | reach in blocks within its dimension; -1 is unlimited | |
cross_dimension | boolean | false | reaches the network from any dimension | |
chunkload | boolean | false | keeps the network's chunks loaded while a player carrying a chip bound to one of its terminals is online |
thematic:fabricator#
A fabricator: a storage network member that holds blueprints (recipes encoded at a terminal with the blueprints feature) and crafts them for the whole network. Requesting an item at a terminal plans the crafts, takes the inputs out of the network and runs the job here, parallel crafts per cycle, then puts the results into the network. Used, it opens a screen with blueprint slots, upgrade card slots (speed, parallel) and nine keep-in-stock rules (an item and a target amount: when the network holds less, a job is queued). Placed it faces the player (adds the horizontal facing property). Its blueprints, cards, rules and running jobs are saved in its block entity (block_entity, default its own id); the blueprints, cards and reserved items drop when it is broken.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
blueprint_slots | number | 9 | slots for blueprints, 1 to 27; each encoded blueprint is a recipe the whole network can request | |
parallel | number | 1 | crafts it runs at once per cycle, before parallel cards | |
ticks_per_craft | number | 20 | ticks one cycle takes, before speed cards | |
card_slots | number | 2 | upgrade card slots (speed, parallel), 0 to 6 | |
theme | string | { preset?: string, title?: string, frame?: string, accent?: string, background?: string, text?: string, boot_sound?: string, scanlines?: boolean, gui?: string } | - | yes | the screen's look, so one Java screen serves every terminal. A bare string is a preset (a palette from data/<ns>/terminal_themes/<name>.json, e.g. "wayne"), and preset: "name" inside the object starts from one with the other keys overriding it. With a "parent", the child's keys override the parent's one by one (a preset replaces the parent's whole theme), except title, which is never inherited. Keys: title (a lang key or plain text; default the block's name), frame (a texture id, a 32x32 image whose 8-pixel border frames the panel; default a plain drawn frame), accent / background / text (hex colours "#RRGGBB" or "#AARRGGBB"; defaults cyan, dark slate, pale blue), boot_sound (a sound id played when it opens), scanlines (faint horizontal lines over the panel, default false), gui (a texture folder "namespace:path" holding your own art: <path>/base.png, tinted with background, and <path>/accent.png, tinted with accent, two 256x256 sheets laid out like the engine's thematic:storage; default thematic:storage) |
block_entity | string | its own id | yes | the block-entity id its items are saved under (a converted block keeps its old one); blocks of the same kind may share one |
thematic:storage_core_array#
A core array: a storage network member that holds data cores (thematic:data_core items) in its slots and stores items in them for the whole network. Inserts go to higher priority members first, so with the default priority cores fill before chests behind a plain link; overflow goes on to the next member. Used, it opens a screen of the core slots with a fill bar each. The cores keep their contents in their own item data and drop, full, when the array is broken.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
slots | number | 10 | data core slots, 1 to 15 | |
priority | number | 10 | inserts go to higher priority members first; the default is above a plain storage link's 0, so cores fill before chests | |
theme | string | { preset?: string, title?: string, frame?: string, accent?: string, background?: string, text?: string, boot_sound?: string, scanlines?: boolean, gui?: string } | - | yes | the screen's look, so one Java screen serves every terminal. A bare string is a preset (a palette from data/<ns>/terminal_themes/<name>.json, e.g. "wayne"), and preset: "name" inside the object starts from one with the other keys overriding it. With a "parent", the child's keys override the parent's one by one (a preset replaces the parent's whole theme), except title, which is never inherited. Keys: title (a lang key or plain text; default the block's name), frame (a texture id, a 32x32 image whose 8-pixel border frames the panel; default a plain drawn frame), accent / background / text (hex colours "#RRGGBB" or "#AARRGGBB"; defaults cyan, dark slate, pale blue), boot_sound (a sound id played when it opens), scanlines (faint horizontal lines over the panel, default false), gui (a texture folder "namespace:path" holding your own art: <path>/base.png, tinted with background, and <path>/accent.png, tinted with accent, two 256x256 sheets laid out like the engine's thematic:storage; default thematic:storage) |
block_entity | string | its own id | yes | the block-entity id its items are saved under (a converted block keeps its old one); blocks of the same kind may share one |
thematic:storage_drive#
A storage drive: a storage network member that is storage itself, with no chest or cores. It joins the network by touching a link, conduit, terminal or any network block, and stores items for the whole network up to its capacity. Inserts go to higher priority members first, so with the default priority drives fill before chests behind a plain link. Broken, it drops its block item carrying everything inside, and placing that item restores it; breaking an empty drive in creative drops nothing. Used with an empty hand it shows its fill. Has the blockstate properties facing (horizontal) and fill (0 empty to 4 full) for its model, and no loot table: the item drops from the block itself so the contents are never duplicated or lost.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
capacity | number | - | how many items it holds in all, at least 1 | |
types | number | 63 | how many different items it holds; 0 is unlimited | |
priority | number | 10 | inserts go to higher priority members first; the default is above a plain storage link's 0, so drives fill before chests | |
block_entity | string | its own id | yes | the block-entity id its items are saved under (a converted block keeps its old one); blocks of the same kind may share one |
items#
data/<namespace>/items/, script global item (registers at startup).
Items: data/<namespace>/items/<any folders>/<id>.json or .js registers the item <namespace>:<id>. Items are registry entries, read once at startup from mod jars, the dev tree and thematic/packs: a new item or a changed identity field needs a restart, while hooks, stats and looks retune on /reload.
Fields every type takes:
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
creative_tab | string | - | yes | the creative tab it is listed in, e.g. "thematic:equipment" |
creative_order | number | - | yes | its place in that tab; unordered items go last, by id |
max_count | number | - | yes | how many stack in one slot |
max_damage | number | - | yes | durability; 0 or left out: none |
rarity | string | - | yes | common, uncommon, rare or epic: the name's colour |
fireproof | boolean | - | yes | survives fire and lava as netherite does (false) |
food | object | - | yes | makes it edible: { hunger, saturation, always_edible, snack, meat, effects } |
enabled | boolean | - | yes | false leaves the item out (true) |
requires | string | string[] | - | yes | the mod ids that must be loaded for the item to exist |
model | string | - | another item's id whose geo model, texture and animations it renders with; left out, its own | |
animations | string[] | - | yes | named animation controllers it runs: hammer, mace, spin, staff_block, bow, trident, boxing_glove |
look | string | { kind: string, texture?: string, folder?: string } | - | how it is drawn: geo (the default: its GeckoLib model), coiled_rope, energy_construct (tinted by the stack's colour; shade 0 to 1 sets how much its faces darken away from the viewer, its depth), with the kind's options. geo takes texture (a full texture id drawn instead of the model's own) and folder (the asset folder, item) | |
visuals | { id: string }[] | - | extra visuals drawn with it, each a visual id and its options | |
stats | { damage?: number, radius?: number, duration?: number, amplifier?: number } | - | the numbers its hooks' verbs read as the tuned stats (duration in seconds) | |
attack_damage | number | - | main-hand attack damage added, as a sword's; with attack_speed | |
attack_speed | number | - | main-hand attack speed added (negative is slower); with attack_damage | |
dual_wield | boolean | - | a copy rides in the off hand while it is held (false) | |
tuning_from | string | - | a move id: its hooks read that move's tuned numbers from the holder's kit -- damage, range as the radius, duration and amplifier -- instead of stats, as a gadget a move hands out reads the move that deployed it; stats when the holder has no such move |
thematic:weapon#
A GeckoLib-rendered weapon. Its hooks run on use, on hit, while held and on release; use draws it back (a staff that blocks, a spear held ready).
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
use | { action?: "block" | "spear" | "bow" | "none", max_ticks?: number, front_only?: boolean, immobilize?: boolean, lock_keys?: boolean, sound?: string, animation?: string } | - | holding the use key draws it: action is the pose and what vanilla makes of it (block blocks hits), max_ticks how long it can be held (72000), front_only blocks only hits from in front, immobilize holds the holder still, lock_keys keeps the suit's ability keys from firing, sound plays as it starts, animation is a GeckoLib clip "<controller>/<clip>" triggered as it starts | |
companion_offhand | { item: string, unless_cooldown?: string, copy_nbt?: boolean } | - | while it is in the main hand and the off hand is empty, the off hand holds a copy of item (unless the ability unless_cooldown is cooling down, or one is already in the inventory); it is taken back when this leaves the main hand. copy_nbt copies this stack's tag onto it | |
reach | number | - | multiplies the holder's entity reach while it is in the main hand (1) | |
renderer | string | - | the look id it is drawn with; the same as look: "<id>" | |
owns_flight_pose_while_using | boolean | - | while it is in use, the flight pose leaves the arms to its own animation (false) | |
use_in_air | boolean | - | a right-click aimed at a block is taken as one in the air: the block is never used, so claim mods never weigh it (false) |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_use | onUse | - | When the holder uses the item (right click), on the server. | owner, source: the holder; hit: none; stack: the held stack; stats: the definition's stats |
on_hit | onHit | - | When the holder strikes an entity with it. | owner, source: the attacker; hit: the entity struck; stack: the weapon; stats: the definition's stats |
while_held | whileHeld | scale a Pehkui scale held on the holder while the item is in their main hand, lifted when it leaves: type is the scale id ("pehkui:entity_reach"), value the multiplier, id what it is kept under (the item's id) | Every tick the item is in the holder's main hand (server side). | owner, source: the holder; hit: none; stack: the held stack; stats: the definition's stats |
on_release | onRelease | - | When the holder lets go of the use key after drawing the item back. | owner, source: the holder; hit: none; stack: the item; charge: ticks it was held in use; stats: the definition's stats |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
Traits: any: a weapon's traits are what abilities and guards ask about ({held_trait: "billy_club"}); staff_block makes a blocking weapon answer as a staff.
thematic:weapon_equippable#
thematic:weapon, kept for the files that name it; the same type.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
use | { action?: "block" | "spear" | "bow" | "none", max_ticks?: number, front_only?: boolean, immobilize?: boolean, lock_keys?: boolean, sound?: string, animation?: string } | - | holding the use key draws it: action is the pose and what vanilla makes of it (block blocks hits), max_ticks how long it can be held (72000), front_only blocks only hits from in front, immobilize holds the holder still, lock_keys keeps the suit's ability keys from firing, sound plays as it starts, animation is a GeckoLib clip "<controller>/<clip>" triggered as it starts | |
companion_offhand | { item: string, unless_cooldown?: string, copy_nbt?: boolean } | - | while it is in the main hand and the off hand is empty, the off hand holds a copy of item (unless the ability unless_cooldown is cooling down, or one is already in the inventory); it is taken back when this leaves the main hand. copy_nbt copies this stack's tag onto it | |
reach | number | - | multiplies the holder's entity reach while it is in the main hand (1) | |
renderer | string | - | the look id it is drawn with; the same as look: "<id>" | |
owns_flight_pose_while_using | boolean | - | while it is in use, the flight pose leaves the arms to its own animation (false) | |
use_in_air | boolean | - | a right-click aimed at a block is taken as one in the air: the block is never used, so claim mods never weigh it (false) |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_use | onUse | - | When the holder uses the item (right click), on the server. | owner, source: the holder; hit: none; stack: the held stack; stats: the definition's stats |
on_hit | onHit | - | When the holder strikes an entity with it. | owner, source: the attacker; hit: the entity struck; stack: the weapon; stats: the definition's stats |
while_held | whileHeld | scale a Pehkui scale held on the holder while the item is in their main hand, lifted when it leaves: type is the scale id ("pehkui:entity_reach"), value the multiplier, id what it is kept under (the item's id) | Every tick the item is in the holder's main hand (server side). | owner, source: the holder; hit: none; stack: the held stack; stats: the definition's stats |
on_release | onRelease | - | When the holder lets go of the use key after drawing the item back. | owner, source: the holder; hit: none; stack: the item; charge: ticks it was held in use; stats: the definition's stats |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
Traits: any: a weapon's traits are what abilities and guards ask about ({held_trait: "billy_club"}); staff_block makes a blocking weapon answer as a staff.
thematic:shield#
A shield: blocks as vanilla's does, drawn with its GeckoLib model.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
auto_offhand | boolean | - | carried anywhere in the inventory while the off hand is empty, it moves there (false) |
thematic:thrown_weapon#
A weapon drawn back and thrown, as a trident: held long enough and let go, it throws a throwable (or any entity) and, with riptide, launches the holder instead.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
charge | { min_ticks?: number } | - | how long it must be drawn back before a release throws (10 ticks) | |
throw | { throwable?: string, entity?: string, velocity?: number, velocity_per_tick?: number, damage?: number, damage_per_tick?: number, max_ticks?: number, divergence?: number, consume?: boolean, sound?: string } | - | what a release throws: a throwables id, or an entity type id; at velocity (2.5) plus velocity_per_tick for every tick drawn back past the minimum; damage plus damage_per_tick per such tick is the throwable's damage for that throw; max_ticks caps the ticks both count; divergence is vanilla's spread (1); consume takes one from the stack outside creative (true); sound plays as it leaves (minecraft:item.trident.throw) | |
riptide | { enabled?: boolean, force_level?: number, cooldown?: number, keep_horizontal?: boolean } | - | a release launches the holder instead of throwing when the stack has Riptide (or force_level is above 0): cooldown in seconds (2); keep_horizontal pushes along the heading without the pitch's shortening, as Aquaman's trident did (false) | |
render_as | string | - | an item whose in-hand look it borrows, e.g. "minecraft:trident" | |
use | { action?: "block" | "spear" | "bow" | "none", max_ticks?: number, front_only?: boolean, immobilize?: boolean, lock_keys?: boolean, sound?: string, animation?: string } | - | holding the use key draws it: action is the pose and what vanilla makes of it (block blocks hits), max_ticks how long it can be held (72000), front_only blocks only hits from in front, immobilize holds the holder still, lock_keys keeps the suit's ability keys from firing, sound plays as it starts, animation is a GeckoLib clip "<controller>/<clip>" triggered as it starts | |
companion_offhand | { item: string, unless_cooldown?: string, copy_nbt?: boolean } | - | while it is in the main hand and the off hand is empty, the off hand holds a copy of item (unless the ability unless_cooldown is cooling down, or one is already in the inventory); it is taken back when this leaves the main hand. copy_nbt copies this stack's tag onto it | |
reach | number | - | multiplies the holder's entity reach while it is in the main hand (1) | |
renderer | string | - | the look id it is drawn with; the same as look: "<id>" | |
owns_flight_pose_while_using | boolean | - | while it is in use, the flight pose leaves the arms to its own animation (false) | |
use_in_air | boolean | - | a right-click aimed at a block is taken as one in the air: the block is never used, so claim mods never weigh it (false) |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_use | onUse | - | When the holder uses the item (right click), on the server. | owner, source: the holder; hit: none; stack: the held stack; stats: the definition's stats |
on_hit | onHit | - | When the holder strikes an entity with it. | owner, source: the attacker; hit: the entity struck; stack: the weapon; stats: the definition's stats |
while_held | whileHeld | scale a Pehkui scale held on the holder while the item is in their main hand, lifted when it leaves: type is the scale id ("pehkui:entity_reach"), value the multiplier, id what it is kept under (the item's id) | Every tick the item is in the holder's main hand (server side). | owner, source: the holder; hit: none; stack: the held stack; stats: the definition's stats |
on_release | onRelease | - | When the holder lets go of the use key after drawing the item back. | owner, source: the holder; hit: none; stack: the item; charge: ticks it was held in use; stats: the definition's stats |
on_throw | onThrow | - | After a release threw the item. | owner, source: the holder; hit: the thrown entity; stack: the item thrown; charge: ticks it was drawn back; stats: the definition's stats |
on_riptide | onRiptide | - | After a release launched the holder. | owner, source: the holder; hit: none; stack: the item; charge: ticks it was held in use; stats: the definition's stats |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
thematic:tether_launcher#
Fires one tethered projectile at a time (a grapple, a gel charge) and remembers it on the stack (NBT key "entity") until it is cut.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
projectile | string | required | the entity type id it fires | |
speed | number | - | launch speed (8) | |
spread | number | - | vanilla's divergence (1) | |
cooldown | number | - | seconds before it fires again (5) | |
recall | "discard" | "kill" | - | how a cut removes the projectile: discard (default) or kill | |
cut_on_use | boolean | - | using it while a projectile is out cuts it (false: something else cuts) | |
companion_offhand | { item: string, unless_cooldown?: string, copy_nbt?: boolean } | - | while it is in the main hand and the off hand is empty, the off hand holds a copy of item (unless the ability unless_cooldown is cooling down, or one is already in the inventory); it is taken back when this leaves the main hand. copy_nbt copies this stack's tag onto it | |
reach | number | - | multiplies the holder's entity reach while it is in the main hand (1) | |
renderer | string | - | the look id it is drawn with; the same as look: "<id>" |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_hit | onHit | - | When the holder strikes an entity with it. | owner, source: the attacker; hit: the entity struck; stack: the weapon; stats: the definition's stats |
while_held | whileHeld | scale a Pehkui scale held on the holder while the item is in their main hand, lifted when it leaves: type is the scale id ("pehkui:entity_reach"), value the multiplier, id what it is kept under (the item's id) | Every tick the item is in the holder's main hand (server side). | owner, source: the holder; hit: none; stack: the held stack; stats: the definition's stats |
on_fire | onFire | - | After it fired. | owner, source: the holder; hit: the projectile; stack: the launcher |
on_cut | onCut | - | After its projectile was cut. | owner, source: the holder; hit: none; stack: the held stack; stats: the definition's stats |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
thematic:melee#
A held tool or weapon with durability, attributes and every use hook: the constructs, and anything else that mines, blocks, charges or casts.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
durability | number | - | yes | uses before it breaks (0: unbreakable) |
knockback | number | - | main-hand attack knockback added | |
mining_speed | number | - | how fast it breaks the blocks mineable names (1) | |
mineable | string | - | a block tag it mines and is the right tool for, e.g. "minecraft:mineable/pickaxe" | |
use_action | "none" | "eat" | "drink" | "block" | "bow" | "spear" | "crossbow" | "spyglass" | - | the pose while it is in use; block blocks hits as a shield does (none) | |
max_use_time | number | - | ticks it can be held in use; 0 means it is never held (0, or 72000 with a use_action) | |
glint | boolean | - | always shimmers as if enchanted (false) | |
guide_lookup | boolean | - | right-clicking it onto a stack in an inventory opens the guide on that item's entry (false) | |
enchantments | Record<string, number> | - | enchantments the stack always carries, put back if taken off | |
attributes | { attribute: string, amount: number, operation?: string, uuid: string }[] | - | more main-hand attribute modifiers, each under its own fixed UUID | |
item_bar | { source?: "durability" | "gauge", gauge?: string, max?: number, color?: string } | - | the bar under the icon: durability (default) or a stack gauge out of max; color is "stack_color" (the stack's colour tag, green without one) or #rrggbb | |
construct | { power_cost?: number, tint?: "corps" } | - | marks a lantern construct: what it costs to summon, and whether it takes the corps' colour | |
use_behaviour | "fishing_rod" | "shield" | { type: "fishing_rod" | "shield" } | { type: "trident", throw: { throwable?: string, entity?: string, velocity?: number, velocity_per_tick?: number, divergence?: number, sound?: string, consume?: boolean }, min_ticks?: number, full_ticks?: number, wear?: number, cooldown?: number, riptide?: boolean } | { type: "bow", arrow?: string, velocity?: number, divergence?: number, pull_ticks?: number, min_pull?: number, wear?: number } | - | a vanilla use it borrows, which also sets the pose when use_action is left out: fishing_rod casts and reels a bobber; shield blocks, and its attributes count in the off hand too; trident is drawn back and, let go after min_ticks (10), thrown as throw says (thrown_weapon's block), faster each tick drawn up to full_ticks (0: no limit), costing wear (0) and resting cooldown seconds (0) -- with riptide, a Riptide enchantment launches the holder instead, in water or rain only; bow is drawn and looses arrow (thematic:arrow) at velocity (5) times the draw, full at pull_ticks (20), never under min_pull (0.1), then wears wear (1) | |
reach | number | - | multiplies the holder's entity reach while it is in the main hand (1) | |
denied_sound | string | - | a swing while the item cools down is refused, and this sound plays to the swinger alone, as a lantern construct's did; left out, every swing lands | |
mining | { tag?: string, blocks?: string | string[], speed?: number, suitable?: boolean }[] | - | per-block mining, the first rule that matches a block deciding: the blocks in tag (a block tag id, as mineable) or listed in blocks (ids and "#tags"; a bare id is minecraft's) -- with neither, every block -- break at speed (mining_speed) and it is their right tool unless suitable is false (true). A block no rule matches falls back to mineable | |
can_mine | string | string[] | - | the only blocks it breaks at all: ids and "#tags", a bare id minecraft's; any other block is left standing, as a sword leaves blocks in creative (any) | |
recipe_remainder | { item?: string, break_chance?: number } | - | what stays in the crafting grid when it is crafted with: item is "self" (one of the stack itself, worn as it was; the default) or an item id; break_chance is the share of crafts, 0 to 1, that leave nothing instead (0) |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_hit | onHit | - | When the holder strikes an entity with it. | owner, source: the attacker; hit: the entity struck; stack: the weapon; stats: the definition's stats |
on_use | onUse | - | When the holder uses the item (right click), on the server. | owner, source: the holder; hit: none; stack: the held stack; stats: the definition's stats |
on_use_tick | onUseTick | - | Every tick it is held in use. | owner, source: the holder; hit: none; stack: the item; charge: ticks it was held in use; stats: the definition's stats |
on_release | onRelease | - | When the holder lets go of the use key after drawing the item back. | owner, source: the holder; hit: none; stack: the item; charge: ticks it was held in use; stats: the definition's stats |
on_use_on_block | onUseOnBlock | - | When it is used on a block. It answers use_block: its if may ask that event's keys (block_type, placed_by_player), and an event its if refuses starts no cooldown. | owner, source: the holder; hit: the block; stack: the item |
on_use_on_entity | onUseOnEntity | - | When it is used on an entity. | owner, source: the holder; hit: the entity; stack: the item |
on_block_broken | onBlockBroken | - | When the holder breaks a block with it in the main hand. It answers block_broken: its if may ask that event's keys (block_type, placed_by_player), and an event its if refuses starts no cooldown. | owner, source: the holder; hit: the block broken; stack: the item |
on_incoming_projectile | onIncomingProjectile | - | When a projectile is about to hit the holder while it is in the main hand. It answers projectile_incoming: its if may ask that event's keys (projectile_type, from_player), and an event its if refuses starts no cooldown; cancel_event lets the projectile pass through the holder. | owner, source: the holder; hit: the projectile; stack: the item |
on_holder_hurt | onHolderHurt | - | When a hit is about to land on the holder while it is in the main hand, past their own invulnerability. It answers damaged: its if may ask that event's keys (melee, source, element, from_player, attacker), and an event its if refuses starts no cooldown; cancel_event calls the hit off: a parry, a moment of immunity. facing: {toward: "attacker"} asks whether the holder faces whoever threw it. | owner, source: the holder; hit: the attacker (none when nothing living threw it); stack: the item |
on_attack | onAttack | - | When the holder starts a strike at a body with it, before the blow lands. cancel_event refuses the strike: a wind-up that lands its own blow later (a held tick, a stack timer). | owner, source: the holder; hit: the body struck; stack: the item |
on_held_tick | onHeldTick | - | Every tick it is in the holder's main hand. | owner, source: the holder; hit: none; stack: the held stack; stats: the definition's stats |
on_inventory_tick | onInventoryTick | - | Every tick it is anywhere in the holder's inventory -- the hotbar, the off hand, a pocket -- on the server; the main hand too (on_held_tick runs after it there). Each stack runs it; every and cooldown count per holder. | owner, source: the holder; hit: none; stack: the held stack; stats: the definition's stats |
on_break | onBreak | - | When it runs out of durability and breaks in a player's inventory (worn, held or carried), on the server, once, at the end of that tick. Players only: a mob's gear is not watched. | owner, source: whoever it broke on; hit: none; stack: one of it with the broken stack's tag (the stack itself is empty by then); stats: the definition's stats |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
Traits: construct: a lantern construct (the roster, the construct HUD); any other trait is what abilities and guards ask about.
thematic:ingredient#
A plain crafting material.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
glint | boolean | - | always shimmers as if enchanted (false) |
thematic:modeled#
A plain item drawn with its GeckoLib model.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
idle_clip | string | - | a clip of its animation file (animations/item/<id>.animation.json) that loops while it is drawn, in hand, on the ground or in a menu, e.g. "animation.sleeping_bag.wriggle" |
thematic:status_wearable#
A head item a move puts on someone (a lasso, a bola, a grab), or one worn for show: a helmet-slot armor item, a stack of one, fireproof. Its flags say what it does to its wearer; a while_worn hook does the rest. It draws a geo model over the whole body from the head slot. Set max_damage for how many swings or uses it lasts.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
stun | boolean | false | its wearer is stunned: each swing wears it down by one and the attack keys stay blocked until it breaks; also the trait stun | |
suit_head_allowed | boolean | false | it may stay on the head while a suit is worn (other head items come off; a stun item always may); also the trait suit_head_allowed | |
cancel_swing | boolean | false | its wearer's swings are cancelled outright; also the trait cancel_swing | |
curses | boolean | false | it gives itself Curse of Binding and Curse of Vanishing while it has no enchantment, so it can't be taken off and is lost on death | |
name_key | string | - | the translation key of its name, in place of the item's own ("Bola'd (Click to break out!)") | |
equip_on_use | boolean | false | using it from the hand puts one on the head when nothing of it is there, instead of swapping it with the helmet | |
owner_nbt | string | "uuid" | the stack NBT key holding its owner's UUID (whoever put it on); expires_unless_owner_active and texture_from read it | |
expires_unless_owner_active | string | - | an ability id: it is removed once its owner is found without that ability active | |
clear_on_owner_respawn | boolean | false | it comes off whoever wears it when its owner dies, and off its wearer when they respawn; also the trait clear_on_owner_respawn | |
render | "geo" | "none" | geo when model is given, else none | yes | geo draws the geo model below; none leaves it to the item model and the armor layers |
model | string | the item's own id | yes | the geo asset id, read as geo/<geo_subtype>/<path>.geo.json and textures/<geo_subtype>/<path>.png |
geo_subtype | "item" | "armor" | "entity" | "item" | yes | the asset folder the worn model and its texture are read from |
item_geo_subtype | "item" | "armor" | "entity" | "item" | yes | the asset folder the in-hand model and its texture are read from |
texture | string | - | yes | the worn texture's full id (thematic:textures/item/gadget_bola.png), in place of the model's own |
item_texture | string | - | yes | the in-hand texture's full id, in place of the model's own |
tint_from_nbt | string | - | a stack NBT key: when the stack has it, the model is drawn glowing with thematic:textures/item/<its value>.png (a corps colour) | |
texture_from | { owner_ability: string } | - | while its owner has that ability, the worn model takes the owner's suit texture, or the ability's own asset texture and model when it names them | |
stats | { damage?: number; radius?: number; duration?: number; amplifier?: number } | damage 3, radius 3, duration 6, amplifier 0 | the numbers this item's hook actions read when they ask for tuned values; duration is in seconds |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
while_worn | whileWorn | - | Every tick it is on a head, on the server. | owner, source: the wearer; hit: none; stats: the definition's stats |
on_break | onBreak | - | When it runs out of durability and breaks in a player's inventory (worn, held or carried), on the server, once, at the end of that tick. Players only: a mob's gear is not watched. | owner, source: whoever it broke on; hit: none; stack: one of it with the broken stack's tag (the stack itself is empty by then); stats: the definition's stats |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
Traits: stun, suit_head_allowed, cancel_swing, clear_on_owner_respawn: the flags of the same names answer them, so a definition may set either the flag or the trait.
thematic:spyglass#
A zoom scope held up to the eye: vanilla's spyglass (its zoom, its sounds, slowed while raised) with a geo model, which is hidden in first person while raised, and its own full-screen overlay.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
model | string | the item's own id | yes | the geo asset id: geo/item/<path>.geo.json and textures/item/<path>.png |
overlay | string | - | the full id of the texture drawn over the screen while it is raised (thematic:textures/gui/batnoculars_scope.png), in place of vanilla's spyglass scope | |
max_use_time | number | 72000 | how many ticks it may stay raised |
thematic:fluid_container#
A bucket for one fluid, as two items that turn into each other: the empty one picks up a source block of its fluid, the filled one places its block. In creative it stays as it is. Edits are refused where the user may not change blocks (claims, spawn protection, the protected worlds).
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
filled | boolean | false | yes | whether this is the filled container, which places, or the empty one, which picks up |
fluid | string | - | the still fluid an empty container picks up (thematic:ooze); required when not filled | |
block | string | - | the block a filled container places (thematic:ooze); required when filled | |
swap_to | string | required | the item it becomes once used: the filled container for an empty one, the empty container for a filled one | |
grief_checks | boolean | true | whether picking up and placing ask the claim and protection rules first | |
model | string | the item's own id | yes | the geo asset id, thematic: only: geo/item/<path>.geo.json and textures/item/<path>.png |
stats | { damage?: number; radius?: number; duration?: number; amplifier?: number } | damage 3, radius 3, duration 6, amplifier 0 | the numbers this item's hook actions read when they ask for tuned values; duration is in seconds |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_fill | onFill | - | After an empty container picked up its fluid, on the server. | owner, source: the user; hit: the block aimed at; stats: the definition's stats |
on_empty | onEmpty | - | After a filled container placed its block, on the server. | owner, source: the user; hit: the block aimed at; stats: the definition's stats |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
thematic:currency#
Money: a note or coin worth amount in a wallet. Every currency counts toward a deposit, and the wallet pays withdrawals out in the largest amounts first, one currency per amount.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
amount | number | required | yes | what one of it is worth in a wallet |
thematic:wallet#
A wallet, a stack of one: using it deposits every currency item in the main inventory, sneak-using it withdraws $100, and /withdrawal <amount> withdraws any sum. Its balance shows above the hotbar while it is held, and lives in the stack's "amount" NBT.
thematic:food#
A food item: the common "food" field ({ "hunger": 4, "saturation": 0.3 }) is required.
thematic:bound_link#
A link chip, a stack of one: shift-using it on a block that can be linked (a storage terminal) binds it there, remembering the dimension, position and name, which the tooltip shows. Using it in the air opens the bound terminal from afar when the range rule allows; the tablet's Terminal app does the same.
thematic:encoded_recipe#
A blueprint, a stack of one: a storage terminal with the blueprints feature encodes its crafting grid into it (the recipe is kept in the stack data), and a fabricator that holds it can craft that recipe for the network on request. Blank until encoded; encoding again overwrites.
thematic:spawn_egg#
Vanilla's spawn egg for an entity type (a mob): used on a block it spawns one, in the two colours given. Its item model is the usual {"parent": "item/template_spawn_egg"}.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
entity | string | required | yes | the entity type id it spawns; it must be registered by the time items finish loading |
primary | number | string | required | yes | the base colour: 0xRRGGBB as a number, or "#rrggbb" |
secondary | number | string | required | yes | the spots' colour: 0xRRGGBB as a number, or "#rrggbb" |
thematic:bow#
A bow fed from its wearer's quiver move: drawing nocks the quiver's selected arrow (the next one off cooldown, else the plain arrow), releasing fires it, scaled by how far the string was drawn, then puts that arrow on cooldown and, with auto-swap on, turns the quiver to the next arrow. A stack of one, +4 attack damage and +0.2 attack speed in the main hand. Its model is geo/item/<id>.geo.json; its clips (idle, pull, hurricane) play on bow_controller.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
pull_speed | number | 1 | how fast the string draws, times the wearer's draw-speed moves | |
ammo | "quiver" | "infinite" | quiver | quiver: arrows come from the wearer's quiver move (without one the bow does nothing); infinite: always the arrow field's arrow, no quiver needed | |
arrow | string | the plain arrow | the arrow item it fires when the quiver is empty or every arrow is cooling down, and always with ammo infinite | |
extra_arrows_from | string[] | none | ability ids: each one the wearer has on looses one more arrow per shot, and nocks one more on the bow | |
arrow_override_from | { ability: string; arrow?: string; track?: string } | - | a move that takes over the shot while it is on (a toggled grapple): drawing nocks the arrow's model; releasing lets a Java move shoot instead, while for a data move the bow looses arrow itself -- at the draw's speed (or the arrow's own), with the move's tuned damage, never picked up -- and, with track, keeps the last one on the wearer under that name (the entity a move's data reads), taking the one before it down | |
draw_sound | string | thematic:bow_draw | the sound played when the string is drawn | |
animation_file | string | the item's own id | the GeckoLib animation file its clips come from: animations/item/<path>.animation.json | |
stats | { damage?: number; radius?: number; duration?: number; amplifier?: number } | damage 3, radius 3, duration 6, amplifier 0 | the numbers this item's hook actions read when they ask for tuned values; duration is in seconds |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_shoot | onShoot | - | Once per arrow loosed, on the server, after it is spawned. | owner, source: the shooter; hit: the arrow; stats: the definition's stats |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
Traits: bow: every bow has it (the bow held-item kind; ItemTraits.has(stack, "bow")).
thematic:loot_box#
A box that is opened by using it: it takes one from the stack, gives one item picked at random from its pool and says which ("You got <item>!"), with a burst of gold dust for the opener.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
pool | string | string[] | required | yes | what it can give: an item tag ("#thematic:comic_covers"), an item id, or a list mixing both; every item they name is equally likely, whatever the tags hold when it is opened |
thematic:upgrade_card#
An upgrade card: slotted into a device's card slots (a storage port, a fabricator, a builder gadget) it changes what the device does. The card id names the card; effects maps effect kinds to values, and the device combines the cards it holds (speed multiplies, stack and parallel add, tag_filter is on if any card has it). A device only reads the kinds it knows.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
card | string | required | the card's id, e.g. "speed"; devices that list accepted cards name them by it | |
effects | { speed?: number, stack?: number, tag_filter?: boolean, parallel?: number } | none | what the card does: speed is a multiplier on how often a device works (2 = twice as often), stack is extra items moved per operation, tag_filter lets a filter match by item tag, parallel is extra crafts a fabricator runs at once; other kinds come from devices that register them |
thematic:data_core#
A data core: slotted into a core array it adds its storage to the storage network. It holds up to capacity items in total, of any mix of kinds, and keeps them in its own item data, so a core carried or broken out of an array loses nothing. The tooltip shows how full it is. Never stacks.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
capacity | number | required | the most items it holds in total, e.g. 16384 | |
max_types | number | 0 | the most different items it holds; 0 is no limit |
thematic:builder_tool#
A construction gadget that only builds: right-click a block to build by its mode (extend the face, line, build to me, surface, grid; right-click the air for air-place), using the clicked block's own item from the inventory and then from the network of a link chip in the inventory. It never breaks or exchanges blocks. Sneak and right-click the air for its card slots; the thematic:upgrade_card cards with the effects capacity (more blocks), range (more reach and spread), network (pull from a link chip's network) and mode_surface / mode_grid / mode_build_to_me / mode_air_place (unlock a mode) upgrade it. Builds can be undone (the last ten), returning the items.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
base_max_blocks | number | 16 | blocks per build before capacity cards | |
base_range | number | 5 | reach of the air-place mode, and the spread and grid-size cap, before range cards | |
card_slots | number | 4 | how many cards it holds, 0 to 9 | |
modes | string[] | all | the modes it may ever have: extend, line, build_to_me, surface, grid, air_place; the last four also need their mode_* card | |
sources | string[] | ["inventory", "network"] | where materials may come from: inventory, network (network also needs the network card) |
arrows#
data/<namespace>/arrows/, script global arrow, default type thematic:arrow (registers at startup).
Trick arrows: data/<namespace>/arrows/<any folders>/<id>.json or .js. Each id registers its own arrow item and entity type at startup (a restart is needed for a new one); the definition is what its hits do, how it looks and how it flies, and it reloads with /reload.
thematic:arrow#
A thematic arrow, fired from a bow or the quiver: a base hit (the tuned damage, scaled by the draw and the archer's utility stat), then its hooks. Numbers the actions read sit at the top level; a projectiles.csv row for the id wins per column.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
damage | number | 6 | the base hit's damage (before the draw and the utility stat), and the damage actions read | |
radius | number | 2 | the radius actions read | |
duration | number | 2 | seconds, the duration actions read | |
amplifier | number | 1 | the amplifier actions read | |
cooldown | number | 20 | ticks the arrow's item waits after a shot, before the utility stat scales it | |
harmless | boolean | false | no base hit: it hurts nobody and may land on an ally or a pet (its on_entity_hit still runs) | |
full_draw_only | boolean | false | only a full draw counts: a shorter one glances off, spent, with no hit and no hooks | |
draw_scaling | boolean | true | the base hit's damage rides how far the bow was drawn | |
speed | number | -1 | a fixed launch speed instead of the bow's; -1 for the bow's | |
break_on_impact | boolean | false | gone after its on_impact runs, on a block as on a body | |
break_on_player_collision | boolean | true | a stuck arrow a player walks into is gone | |
tick_interval | number | 1, or on_tick's every | ticks between on_tick runs | |
classification | { stun?: boolean, single_use?: boolean, bleed?: boolean, damage_type?: string } | - | the loadout rules and element (a typed element also types the base hit); left out, each is worked out from the actions (a freeze makes it a stun and ice) | |
bench | boolean | true | offered at the arrow bench; false for an arrow a fixed roster hands out | |
bow_model | string | this arrow's id | the geo model the bow nocks while it is loaded (geo/entity/<path>.geo.json) | |
look | { model?: string, vanilla?: "arrow" | "spectral_arrow" | "tipped_arrow", tint?: number | string, tether?: boolean | { texture?: string, anchor_bone?: string, face_owner?: boolean, width?: number } } | its own model | how it is drawn: its GeckoLib model (geo/entity/<model>, the id by default), or vanilla's arrow texture of that name (its item then shows as that vanilla arrow, a tipped one in tint); tether adds a rope to the archer's hand | |
item | { glint_when?: "holds_entity" | "never", tooltip?: "held_entity" | "none", key?: string, empty_tooltip?: string } | - | the arrow item: glint while its stack stores an entity under key (StoredEntity), and a tooltip naming it, else the empty_tooltip translation key | |
roster | { name: string, slot: number, rung: number } | - | a place in a named fixed-quiver roster (a fixed_quiver ability's "roster"): slot 0 is the free default, then the quiver slots in order; rung is the starter ladder rung it unlocks at | |
return | true | { mode?: "direct" | "pull", after_ticks?: number, on_entity_hit?: boolean, stuck_ticks?: number, speed?: number, catch_distance?: number, outbound_gravity?: boolean, rise?: number, sound?: string, volume?: number } | - | turns back to its archer and is caught (on_return): direct flies straight home after after_ticks (17) at speed (1), caught within catch_distance (1.5) | |
tether | true | { attach?: "any" | "block" | "entity", strength?: number | "damage", release_on_sneak?: boolean, max_length?: number } | - | once lodged, hauls its archer toward it each tick (the gap times -strength; "damage": the damage over 100, else 0.1) until they crouch, stray past max_length or are gone (on_release); the launcher's line is cut when it lets go | |
split | true | { every_ticks?: number, max?: number, count?: number, angle?: number, jitter?: number } | - | while it flies, sheds count (2) copies every every_ticks (7), up to max (6) times; the copies never split | |
max_hits | number | 0 | gone after meeting this many things (blocks and bodies); 0 for no limit | |
lifetime | number | -1 | ticks after which it is gone; -1 for the arrow's own bound (10 s) | |
impact_once | boolean | false | its hit hooks run on the first thing it meets, never again |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_entity_hit | onEntityHit | - | It struck a body, after the base hit landed (not when the hit was refused, or a short draw glanced off a full_draw_only arrow). | owner: the archer; source: the arrow; hit: what it hit (none for a tick); stack: the arrow item it was fired as; stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
on_block_hit | onBlockHit | - | It met a block (it has stuck in it). | owner: the archer; source: the arrow; hit: what it hit (none for a tick); stack: the arrow item it was fired as; stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
on_impact | onImpact | - | Any hit, a body or a block, at the point it hit: after on_entity_hit or on_block_hit. With break_on_impact the arrow is gone after it. | owner: the archer; source: the arrow; hit: what it hit (none for a tick); stack: the arrow item it was fired as; stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
on_tick | onTick | - | Every tick_interval ticks (or the hook's every) while it exists, on the server. | owner: the archer; source: the arrow; hit: what it hit (none for a tick); stack: the arrow item it was fired as; stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
on_return | onReturn | - | A return brought it home. | owner: the archer; source: the arrow; hit: what it hit (none for a tick); stack: the arrow item it was fired as; stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
on_release | onRelease | - | A tether let go: its archer crouched, strayed past max_length, or is gone. | owner: the archer; source: the arrow; hit: what it hit (none for a tick); stack: the arrow item it was fired as; stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
Traits: free words the engine and kits may ask about (read through ContentTraits)
throwables#
data/<namespace>/throwables/, script global throwable, default type thematic:thrown (registers at startup).
Things thrown and flying: gadgets, grenades, vials, thrown items. data/<namespace>/throwables/<any folders>/<id>.json or .js. Every one is the entity thematic:thrown; the definition is how it flies, looks and what its hits do. A definition with an item block also registers that item (a restart is needed for a new one).
thematic:thrown#
A thrown body: a GeckoLib model (or an item) in flight, with the throwable's flight rules and action lists. Numbers the actions read sit at the top level; a projectiles.csv row for the id wins per column.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
model | string | this throwable's id | GeckoLib model id: geo/entity/<path>.geo.json and textures/entity/<path>.png in its namespace | |
item_sprite | string | - | an item id drawn flat instead of a model | |
name | string | the item's name, else entity.<ns>.<id> | translation key for death messages | |
render | { scale?: number, face_velocity?: boolean, animated?: boolean, tint_bone?: string, tumble?: number, center?: number, spin?: number | { speed?: number, axis?: "x" | "y" | "z", landed?: boolean }, clips?: string | { flying?: string, returning?: string, landed?: string }, tether?: true | { style?: "rope" | "streak" | "glow" | "chain", preset?: "line" | "strand" | "snare_line" | "cocoon" | "cocoon_strap" | "ball", from?: "main_hand" | "off_hand" | "eyes" | "feet", ticks?: number, sag?: number, wobble?: number, alpha?: number, width?: number, palette?: "gold" | "silver", by_ability?: { [ability: string]: "gold" | "silver" }, target_height?: number, hand_lift?: number, color?: string, texture?: string }, lit?: boolean, item_facing?: "camera" | "flight", orient?: [number, number, number] } | - | scale (0.75), turn to face its flight (true), play the idle animation (false), the bone drawn in the throw's tint, degrees a tick it tumbles, model units lowered to turn about its middle; spin: degrees a tick it turns about its own axis (y, flat, by default; x end over end; z rolling) while it flies, or at rest too with landed; clips: named clips of its animation file looped by what it is doing -- flying out, returning home (else flying), landed once stuck, landed or lodged (else none); tether: a line drawn from the thrower to it, as a tether body's look (e.g. { style: "rope", preset: "strand", ticks: 7, wobble: 0.05, alpha: 0.85 } for a strand that leaves the wrist and lets go); lit: drawn at full brightness wherever it flies (false); item_facing: a flat item look turned to the camera (camera, the default) or along its flight as an arrow is (flight), spin then turning it about that line; orient: [x, y, z] degrees turning the model into the flight frame (x along the flight, z across it) after spin, so a model whose shaft is y flies tip-first with [0, 0, -90]; center then lowers it onto its middle | |
look | "geo" | "item" | "geo_item" | { kind?: "geo" | "item" | "geo_item", model?: string, texture?: string, layer?: "cutout" | "beam", tint?: "none" | "stack_color" | string, default_color?: string, saturate?: number, tether?: boolean | { texture?: string, anchor_bone?: string, face_owner?: boolean, width?: number }, streak?: boolean | { sides?: number, side_offset?: number, width?: number, taper_min?: number, lifetime?: number, max_samples?: number, cut_distance?: number, lead?: boolean | { ticks?: number, max?: number, min_speed?: number, weight?: number }, layers?: Array<[string | number | [number, number, number], number, number]> }, flame_orb?: boolean | { radius?: number, color?: string, core_color?: string, tip_color?: string, haze?: number, haze_color?: string, embers?: number, spin?: number } } | geo | how it is drawn: geo (its model), item (the stack a thrown_item carries, else item_sprite, flat) or geo_item (an item's geo model, geo/item/<model>, in a beam layer over texture, tinted by the carried stack's color NBT); a geo look takes texture, layer and tint too (not model: it is the definition's); tether adds a rope to the thrower's hand; streak draws trailing streaks along its flight (true for the defaults); flame_orb draws it as a ball of fire instead of its model or sprite: a white-hot core_color heart in turning shells of color flame radius (0.35) round, a tail of tongues burning out to tip_color, sparks (embers) and a wavering band of haze_color heat haze haze (2.5) blocks back along its path (true for the defaults) | |
size | number | [number, number] | 0.3 | yes | hitbox in blocks: one number, or [width, height] |
velocity | number | 4.0 | blocks a tick it is thrown at | |
inaccuracy | number | 1.0 | vanilla's spread | |
gravity | number | 0.05 (an arrow's) | blocks a tick squared it falls | |
drag | number | 0.99 (an arrow's) | share of speed kept each tick | |
on_block | "stick" | "pass" | "stop" | "bounce" | stick, or bounce when bounce is set | what it does meeting a block without detonating | |
bounce | number | { vertical?: number, horizontal?: number, min_speed?: number, on_hit?: [number, number, number] } | 0 | share of speed kept per bounce, mirrored off the face (also "ricochet"); or per axis: off a floor or ceiling only its rise turns, kept at vertical (0.6), off a wall only the part into it, kept at horizontal (0.7), leaving no slower than min_speed (0) -- the billy club's; on_hit multiplies its velocity per axis when it strikes a body and flies on ([-1.01, -1.1, -1.01]: straight back off them) | |
ricochet | number | - | the same as bounce | |
max_bounces | number | 3 | bounces before it sticks | |
fuse_ticks | number | 0 | ticks before on_fuse runs and it is gone; 0 for no fuse | |
arming_ticks | number | 0 | ticks before a block hit may detonate it | |
explode_on_impact | boolean | false | shorthand for explode_on_entity_hit and explode_on_block_hit | |
explode_on_entity_hit | boolean | - | a body hit runs on_impact (then on_entity_hit) and it is gone | |
explode_on_block_hit | boolean | - | a block hit runs on_impact and it is gone | |
hits_owner | boolean | false | it may strike its thrower | |
ignore_owner_vehicle | boolean | false | it passes through what its thrower rides | |
collide_with_entities | boolean | true | bodies stop it | |
discard_on_entity_hit | boolean | true | gone after striking a body | |
impact_origin | "hit" | "self_block" | "target_block" | hit | where impact actions are centred | |
homing | number | { strength?: number, range?: number, retarget?: boolean | "nearest" | "on_loss" | "never" } | - | turns toward a body it may hit (strength 0.1 of the way a tick, within range 16): the nearest each tick; with retarget true (on_loss) it keeps to the first it picks until that one is gone or struck, then picks another; false (never) keeps to the first and then flies on straight | |
trail | { particle: string, count?: number, interval?: number, spread?: number } | - | particles left in flight | |
land_after_ticks | number | -1 | ticks after which it counts as landed in mid-air; -1 never | |
tick_interval | number | 1, or on_tick's every | ticks between on_tick runs | |
tick_only_when_landed | boolean | false | on_tick runs only once it has landed | |
lifetime_after_landing | number | -1 | ticks it lasts once landed; -1 for ever | |
damage | number | 3 | the damage actions read | |
radius | number | 3 | the radius actions read | |
duration | number | 6 | seconds, the duration actions read | |
amplifier | number | 2 | the amplifier actions read | |
cooldown | number | 3 | seconds a gadget waits after use, before the utility stat scales it | |
use | ActionObject[] | - | a gadget used in place, never thrown: these run on the user (set it with set({ use: [...] })) | |
item | true | { id?: string, max_count?: number, creative_tab?: string, kind?: "gadget" } | - | yes | registers an item at startup: kind gadget (the only kind) is a gadget item, always in Thematic's Gadgets tab |
classification | { stun?: boolean, single_use?: boolean, bleed?: boolean, damage_type?: string } | - | the loadout rules and element; left out, each is worked out from the actions (a freeze makes it a stun and ice) | |
thrown_item | true | { pickup?: "owner" | "any" | "none" } | - | it is an item in flight: it carries the stack it was thrown from (its hooks' stack), draws it with look item or geo_item, and gives it back when picked up or caught | |
return | true | { mode?: "direct" | "pull", after_ticks?: number, on_entity_hit?: boolean, after_hit?: boolean, stuck_ticks?: number, after_ground_ticks?: number, max_distance?: number, on_block?: boolean, speed?: number, catch_distance?: number, outbound_gravity?: boolean, rise?: number, noclip?: boolean, drop_after?: number, rehit?: boolean, sound?: string, volume?: number } | - | turns back to its thrower and is caught (on_return): direct flies straight home after after_ticks (17) at speed (1), caught within catch_distance (1.5); pull draws it home through blocks once it struck someone or sat stuck stuck_ticks (4), at speed (0.07), rising rise (0.075) of the gap a tick. Either also turns past max_distance blocks from where it left (0: no limit); noclip (pull true, direct false) takes it home through blocks; drop_after waits that many ticks by a player with a full inventory before dropping what it carries there (0: at once); rehit forgets who it struck as it turns, so a piercing bolt strikes each body again on the way home. after_hit and after_ground_ticks are on_entity_hit's and stuck_ticks' other names | |
tether | true | { attach?: "any" | "block" | "entity", strength?: number | "damage", release_on_sneak?: boolean, max_length?: number } | - | once lodged, hauls its thrower toward it each tick (the gap times -strength; "damage": the damage over 100, else 0.1) until they crouch, stray past max_length or are gone (on_release) | |
split | true | { every_ticks?: number, max?: number, count?: number, angle?: number, jitter?: number } | - | while it flies, sheds count (2) copies every every_ticks (7), up to max (6) times, turned angle (0.35) radians off its line either side plus up to jitter (0.25); the copies never split | |
max_hits | number | 0 | gone after meeting this many things (blocks and bodies); 0 for no limit | |
lifetime | number | -1 | ticks after which it is gone without breaking; -1 for the body's own bound (10 s) | |
impact_once | boolean | false | its hit actions run on the first thing it meets, never again | |
chain | true | number | { targets?: number, range?: number, per_hop_damage?: number, players_first?: boolean, line_of_sight?: boolean, recoil_ticks?: number, speed?: number, steer?: number, min_speed?: number, max_speed?: number, from_blocks?: boolean, end_on_player?: boolean } | - | after striking a body it turns onto the next, targets (3) in all (a number is the targets): the nearest within range (15) its thrower may hit and can see (line_of_sight), not struck yet, players first; it recoils recoil_ticks (3), is sent at them at speed (1.6), steers steer (0.25) a tick between min_speed (1.2) and max_speed (2.5) through blocks, and strikes within half a block; each hop's damage is the last times per_hop_damage (1). from_blocks: a block sends it at the next one too; end_on_player: striking a player ends it. When it ends, its return brings it home, else it is gone | |
stick | true | { into_blocks?: boolean, into_entities?: boolean, lifetime?: number } | - | how it lodges: into_blocks (true) keeps it in a block for lifetime ticks (true: 1200) rather than 10 s from the throw; into_entities (false) lodges it in the body it strikes, riding along turned with them, gone after lifetime or with them; -1 lifetime for the body's own 10 s bound | |
orbit | true | { target?: "owner" | "hit", radius?: number, height?: number, speed?: number, turns?: number, then?: "return" | "release" | "discard" } | - | circles its thrower (owner, from the throw) or the first body it strikes (hit), radius (2) out and height (0) above their middle, speed (0.3) radians a tick, for turns (1; 0 for as long as it lives), passing through blocks and striking each body once; then return (its return brings it home, else as release), release (off along the circle) or discard | |
item_source | true | "using" | "mainhand" | "offhand" | "head" | "chest" | "legs" | "feet" | { slot?: string, consume?: boolean, restore?: boolean } | - | when its thrower is set it takes the stack it carries (drawn by look item, its hooks' stack) from their slot, unless a throw already gave it one: using (default) is the item being drawn back, else the main hand. consume (false) takes it for good (never from a creative player), else a copy of one; restore (as consume) puts a taken stack back in that slot, or their inventory, when it is caught, broken or gone | |
pierce | boolean | number | false | it passes through bodies, striking each once: true for every one, a number for that many before one stops it | |
on_land | { zone: string, lasts?: number, end_move?: string, stuck_ticks?: number, on_entity_hit?: boolean } | - | where it comes to rest -- stuck in a block more than stuck_ticks (4), or striking a body (on_entity_hit, true) -- it leaves the entity zone (a zone body, by id) there, owned by its thrower and lasting lasts seconds (the zone's own), gives its thrower back what it carries, ends their move end_move (inactive, on its cooldown, again as the zone goes), and is gone: the trident's whirlpool | |
on_refused_hit | "return" | "discard" | "pass" | - | a body its thrower may not hit is never struck: return turns it home (needs return), discard ends it, pass flies on by; left out, it strikes it as any other | |
recall | true | { beyond?: number, after_ticks?: number, on_lost?: ActionObject[] } | - | a throw out more than after_ticks (55) and more than beyond blocks (32) from its living thrower is lost: it is gone and on_lost runs aimed at the thrower (a thrown hammer re-arming its equip move) | |
catch | true | { pickup?: boolean, on_catch?: ActionObject[] } | - | coming home to its thrower runs on_catch aimed at them (their catch clip): when a return brings it into their hands, and, with pickup (true), when they pick it up themselves | |
hug_ground | true | { depth?: number, max_distance?: number } | - | it runs along the ground instead of flying: each tick it is set depth (0.3) blocks under the top of the terrain beneath it, passes through blocks and bodies, and keeps going level at the speed it was launched at; max_distance (32; 0 for no limit) blocks from its start it is gone. What it does to those it passes is its on_tick's (a buzzsaw: tick_interval 3, a targets around its source). Not with return, tether, chain, orbit, stick or homing |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_impact | onImpact | - | Any impact: after on_entity_hit on a body, after on_block_hit on a block; also when it detonates. | owner: the thrower; source: the thrown entity; hit: what it hit (none for a fuse or a tick); stack: the item it carries (thrown_item); stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
on_entity_hit | onEntityHit | - | It struck a body (not its thrower, unless hits_owner). | owner: the thrower; source: the thrown entity; hit: what it hit (none for a fuse or a tick); stack: the item it carries (thrown_item); stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
on_block_hit | onBlockHit | - | It met a block without detonating. | owner: the thrower; source: the thrown entity; hit: what it hit (none for a fuse or a tick); stack: the item it carries (thrown_item); stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
on_fuse | onFuse | - | Its fuse ran out (fuse_ticks); left out, the fuse runs on_impact. | owner: the thrower; source: the thrown entity; hit: what it hit (none for a fuse or a tick); stack: the item it carries (thrown_item); stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
on_tick | onTick | - | Every tick_interval ticks (or the hook's every) while it flies, or only once landed (tick_only_when_landed). | owner: the thrower; source: the thrown entity; hit: what it hit (none for a fuse or a tick); stack: the item it carries (thrown_item); stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
on_return | onReturn | - | A return brought it home: before the thrower is given back what it carries. | owner: the thrower; source: the thrown entity; hit: what it hit (none for a fuse or a tick); stack: the item it carries (thrown_item); stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
on_release | onRelease | - | A tether let go: its thrower crouched, strayed past max_length, or is gone. | owner: the thrower; source: the thrown entity; hit: what it hit (none for a fuse or a tick); stack: the item it carries (thrown_item); stats: its damage/radius/duration/amplifier, a projectiles.csv row laid over them |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
Traits: free words the engine and kits may ask about (read through ContentTraits)
criminals#
data/<namespace>/criminals/, script global criminal, default type thematic:criminal (registers at startup).
Criminals: data/<namespace>/criminals/<any folders>/<id>.json or .js. Each id registers its own entity type, attributes, spawn rules and spawn egg (<id>spawn_egg) at startup (a restart is needed for a new one, or for new stats); the look, the fight and the hooks reload with /reload. A crew file defines many ids, criminal("<id>", "thematic:criminal", c => c.use("thematic:criminal<role>", { ...crew })).
thematic:criminal#
A hostile human NPC on the criminal brain: it targets whoever the faction rules allow, calls its allies in, chases, punches (or stabs, with a held weapon), breaks and runs when badly hurt, and with a gunner block fights at range instead: aims, fires bursts, reloads in cover and keeps its distance.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
look | { model?: string, texture?: string, renderer?: "basic" | "melee" | "gunner", scale?: number, render_scale?: number } | { model: "criminal", renderer: "basic", scale: 1, render_scale: 1 } | how it is drawn: its GeckoLib model geo/entity/<model>.geo.json and texture textures/entity/<model>.png (texture overrides the second, as a texture id); renderer basic draws the mob beams it may fire, melee the item in its main hand, gunner its gun and the aim pose; scale is its Pehkui size (1.3 for a strong tier); render_scale stretches only the drawing | |
stats | { health?: number, armor?: number, damage_multiplier?: number, speed_multiplier?: number } | { health: 40, armor: 15, damage_multiplier: 1, speed_multiplier: 1 } | yes | its attributes: max health, armor, attack damage 4 times damage_multiplier (which also scales its bullets), movement speed 0.25 times speed_multiplier |
morale | { break_chance?: number } | { break_chance: 0.35 } | the chance, rolled once per criminal, that it breaks and runs when badly hurt | |
chase | { near?: number, far?: number, far_distance?: number } | { near: 1, far: 1.3, far_distance: 12 } | chase speed modifiers: near, and far beyond far_distance blocks (a gunner's is its range) | |
melee | { held_item?: string, anim_ticks?: number, trigger_anim?: string } | { anim_ticks: 10, trigger_anim: "punch" } | its close fight: the item it spawns holding (never dropped), the ticks one swing takes, and the triggerable clip on the Attack controller a swing plays | |
gunner | { range?: number, arm_raise_ticks?: number, first_volley_sighting_ticks?: number, cooldown_ticks?: number, volleys_before_retreat?: number, between_volley_cooldown_ticks?: number, between_volley_aim_ticks?: number, pellets?: number, pellet_damage?: number, pellet_speed?: number, pellet_spread?: number, min_engagement_distance?: number, reaction_ticks?: number, seek_cover?: boolean, strafe?: boolean, hold_position?: boolean, guns?: ({ item: string, weight?: number, sound?: string } | string)[], fire?: { form?: "bullets" | "projectile", round?: string, throwable?: string, explode_on_impact?: boolean, volume?: number, pitch?: number, pitch_jitter?: number }, aoe_safety_radius?: number } | - | fights with a gun: brings it up (arm_raise_ticks, then first_volley_sighting_ticks), fires bursts of volleys_before_retreat volleys, reloads for cooldown_ticks in cover, strafes, sidesteps a blocked lane and backs off inside min_engagement_distance. It rolls one of guns once (saved as GunId); a gun whose mod is missing is none, and a criminal without one never fires. fire: bullets (pellets rounds of round, "thematic:bullet" by default) or one projectile (a round, or a throwable), held while squadmates stand within aoe_safety_radius of the aim point | |
spawn | { egg?: { primary: string | number, secondary: string | number }, natural?: { weight: number, min?: number, max?: number } } | - | yes | its spawn egg's colours ("#rrggbb"), and a natural spawn in the overworld and Gotham (Gotham's weight doubled): its share of the monster pool and its group size |
movement | { type?: "walk" | "fly", hover_height?: number, speed?: number, land_within?: number } | { type: "walk", hover_height: 2, speed: 0.42, land_within: 0 } | how it gets about: walk, or fly under its own power (no fall damage; the move.hover clip while airborne) toward a point hover_height blocks over its target at speed blocks a tick, landing to fight on foot once within land_within blocks (0: never) and whenever it has no target or something grounds it | |
kit | { suit: string, iv?: number, abilities: string[], delay?: number } | { iv: 1, delay: 0 } | the moves it may use: it wears suit (a "boss": true suit, never dropped, its rarity pinned to iv) and may fire only abilities from it, none in the first delay seconds; a mob fires an ability through the ability's mob() part. With no brain.rotation its controller picks among them by range and weight, never while it is panicking | |
brain | { face_target?: boolean, grounded?: { use: string[], within: number }, rotation?: { name: string, move: "close" | "away" | "hold", height?: number, speed?: number, distance?: number, use?: string[], use_within?: number, leave_beyond?: number, seconds: number, next?: string }[] } | { face_target: false } | how it fights with its kit: face_target turns its whole body, head included, at its target every tick; grounded is what it fires when forced down (the first of use that starts, once within blocks); rotation is a fixed order of stances a flier runs (needs movement fly) -- each flies close to height over the target, away to distance off and height up, or holds height over it, at speed; tries use in order while within use_within (0: any distance), and the first that starts ends the stance, as does being leave_beyond off or seconds passing; then next (left out, the stance after it). A move mid-channel pauses the rotation, and landing starts it over |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_melee_hit | onMeleeHit | - | Its swing landed on a living target (after the damage). | owner and source: the criminal; hit: its victim (none for a tick); stats: the kind's defaults |
on_tick | onTick | - | Every server tick it thinks (the hook's every thins it out). | owner and source: the criminal; hit: its victim (none for a tick); stats: the kind's defaults |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
Traits: free words the engine and kits may ask about (read through ContentTraits)
entities#
data/<namespace>/entities/, script global entity (registers at startup).
Entity types: data/<namespace>/entities/<any folders>/<id>.json or .js. "type" names the body (a generic entity: zone, tether, owner_copy, mob, vehicle...) and the file sets its options. Each id registers its own entity type at startup (and a spawn egg <id>_spawn_egg with spawn_egg), so a new one, or a changed size, group, tracking, attributes, egg or boss flag, needs a restart; the render block and the body's options reload with /reload.
Fields every type takes:
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
size | [number, number] | - | yes | its hitbox, [width, height] in blocks; left out, the body sizes it (an empty box until it does) |
resizable | boolean | false | yes | whether the box scales with the entity (vanilla's changing dimensions) instead of staying fixed |
spawn_group | "monster" | "creature" | "ambient" | "axolotls" | "underground_water_creature" | "water_creature" | "water_ambient" | "misc" | "misc" | yes | the mob cap it counts against, and how natural spawning treats it |
spawn_far_from_players | boolean | true for misc and creature, else false | yes | whether it may spawn (and stay) far from every player; misc and creature bodies always may |
track_range | number | 5 | yes | how far away, in chunks, players still see it |
update_rate | number | 3 | yes | ticks between position updates sent to the players who see it |
fire_immune | boolean | false | yes | whether fire and lava leave it unharmed |
attributes | { [attribute: string]: number } | - | yes | base values laid over the body's default attributes, by attribute id ("minecraft:generic.max_health": 40); only a living body has attributes |
spawn_egg | { colors: [string | number, string | number], tab?: string } | - | yes | registers a spawn egg <id>_spawn_egg in these colours ("#rrggbb"), for a mob body; tab names the creative tab it is listed in |
render | { kind?: "geo" | "item" | "player_copy" | "beam" | "line" | "none" | string, model?: string, texture?: string, animation?: string, scale?: number, layers?: string[], procedural_legs?: boolean } | { scale: 1 } | how it is drawn: kind picks the renderer (geo: a GeckoLib model geo/entity/<model>.geo.json with textures/entity/<model>.png and animations/entity/<model>.animation.json, texture and animation overriding those; item: the item it carries, else the item model names; none: nothing), scale sizes the drawing, layers names extra render layers, procedural_legs swings quadruped leg bones with the stride for a model with no walk clip; left out, the body's own renderer | |
boss | boolean | false | yes | a boss: the world-wide loaded-boss cap (maxLoadedThematicBosses) counts it, and entity culling never hides it by distance (it draws a boss bar) |
thematic:thrown#
A thrown thing with an entity type of its own: every entity of the type flies as one throwable definition (data/<ns>/throwables/<id>), with that definition's flight, options (chain, stick, orbit, item_source, pierce, return, bounce, on_land, on_refused_hit...), hooks and look. Throws spawn thematic:thrown itself, so a pack needs its own type only to keep an old entity id loading (a save, a summon command) or to tell its throws apart. The hitbox is the throwable's size; render kind thrown (the default) draws its look.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
throwable | string | this entity's id | the throwable definition id every entity of this type flies as |
thematic:bolt#
An energy bolt with an entity type of its own: every entity of the type is a thematic:bolt (the body a thematic:projectile fires by default), drawn by its look. Moves fire thematic:bolt itself, so a pack needs its own type only to keep an old entity id loading (a save, a summon command), or for a shot Java code fires by entity id (a gunner's round, a flier's gun): that shot flies as projectile says, with the damage and effects its shooter gives it. One made bare (read back from a save with no flight, a summon command) has nothing to run and goes on its first tick. The hitbox is the flight's size; render kind bolt (the default) draws its look.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
projectile | Partial<ProjectileOptions> | - | the flight of a shot fired by entity id: any thematic:projectile field a bolt reads as it flies (size, gravity, max_age, max_distance, direct_hit, effects, pierce, hit_once, hittable_only, trail, hit_sound, look, on_hit, on_block...); left out, the projectile's own defaults | |
max_alive | number | 0 | at most this many shots of this type alive in one world; firing another takes the oldest away (0: no cap) |
thematic:tether#
A line from its owner to a head that takes hold of a block or a body: it hauls its owner in (pull_owner, a grapple), hauls what it holds in (pull_target, a fishing line) or stays on the body it holds (bind_target, a lasso). Fired by a tether_launcher, summoned (a summon's target is bound at once) or thrown like any entity (a move's projectile{body: "entity"} names the move and runs its on_hit / on_block, in the press, as the head takes hold); it lets go when its owner is gone, when it stretches too far, when a pull is done, at the end of its lifetime or when its launcher cuts it, running on_release. Its owner punching while it is out (with the launcher in hand) may start its reel and runs on_owner_swing. Every option is read live, so a /reload retunes lines already out; size, spawn_group, track_range and update_rate are the shared entity fields, and a render.model draws its head as a still GeckoLib model on top of the line.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
mode | "pull_owner" | "pull_target" | "bind_target" | "swing" | "pull_owner" | what it does once it holds something: pull_owner hauls its owner toward it; pull_target hauls the body it holds toward its owner (on a block it lets go at once); bind_target stays on the body it holds, pulling it back when it strays past max_length; swing is a line an ability's tether part moves its owner on (it sits where the move put it for as long as the move keeps it, and of the other options only look applies) | |
body_mode | "pull_owner" | "pull_target" | "bind_target" | mode | what it does while it holds a body rather than a block (a grapple that reels its owner to a wall but only sits on a creature until it reels); left out, mode | |
pull | { base?: number, per_block?: number, max?: number } | - | a spring pull in place of retract_speed: each tick the pulled end's velocity gains, straight at the other end, base + per_block x the distance blocks a tick, at most max (0: no cap), on top of its own movement; left out, the pull sets the end's velocity at retract_speed | |
body_pull | { base?: number, per_block?: number, max?: number } | - | the spring pull while it holds a body; left out, pull | |
pause_on_sneak | boolean | false | while its owner crouches a line that holds something does nothing (no pull, no hang) and a running reel stops counting down | |
hang | number | 0 | a pull_owner line on a block that has brought its owner within release_at holds them there instead of letting go, keeping this share of their speed each tick (0 to 1); crouching there lets go. 0: it lets go on arrival | |
stop_owner | boolean | false | a line that held something stops its owner dead when it lets go or its launcher cuts it | |
reel | { ticks?: number, when?: Guard, mode?: string, body_mode?: string, pull?: { base?: number, per_block?: number, max?: number }, body_pull?: { base?: number, per_block?: number, max?: number }, retract_speed?: number } | - | a burst its owner starts by punching while the line is out and when (a guard on the owner, e.g. {"sneaking": true}; left out, always) passes: for ticks ticks (15; the count runs while the line is out, not while paused) it acts by these hold options, each left out taken from the line's own | |
attach | "any" | "block" | "entity" | "any" | what the flying head takes hold of; the head lets go when it strikes a block it may not hold | |
head | { gravity?: number, drag?: number, max_ticks?: number } | - | the flying head: it falls gravity blocks a tick more each tick (0.03), keeps drag of its speed (0.99) and lets go after max_ticks with nothing held (60) | |
max_length | number | 0 | blocks the line stretches before it lets go (a bind_target line pulls its body back instead); 0 for no limit | |
retract_speed | number | 0.5 | blocks a tick a pull moves the pulled end | |
release_at | number | 1.5 | blocks between the ends at which a pull is done and it lets go; 0 for never | |
release_on_sneak | boolean | false | its owner crouching lets go of a line that holds something | |
lifetime | number | 0 | ticks it lasts at most (20 is one second); 0 for no limit | |
owner_key | string | - | a player-store entity key: it lasts only while its owner's entity stored under this key is this line, so the move that keeps it can replace or drop it by the key; a summoned line takes the key on its owner as it comes, replacing the one kept there before | |
hold_key | string | - | a player-store entity key: once it holds a body, it lasts only while its owner's entity stored under this key is that body (a move's mark_target), so the move that caught it lets go of the line by forgetting the body | |
look | true | "rope" | "streak" | "glow" | "chain" | { style?: "rope" | "streak" | "glow" | "chain", preset?: "line" | "strand" | "snare_line" | "cocoon" | "cocoon_strap" | "ball", from?: "main_hand" | "off_hand" | "eyes" | "feet", ticks?: number, sag?: number, wobble?: number, alpha?: number, width?: number, palette?: "gold" | "silver", by_ability?: { [ability: string]: "gold" | "silver" }, target_height?: number, hand_lift?: number, color?: string, texture?: string } | { "style": "rope", "preset": "line" } | a line from its owner to it: style rope (twisted strands with frayed hairs, shaped by preset; line is the swing line, strand a thin wrist strand), streak (one flat band reaching width blocks to each side of the line, 0.025), chain (textured links of the look's texture, the vanilla chain by default; only a pin draws it) or glow (a thick glowing tube in palette gold or silver, or the palette by_ability names for the move that made it); from where on the owner it starts (main_hand: 0.4 below the eyes, 0.35 in front, 0.4 to that side; hand_lift raises it); ticks it lasts, fading, after the thing it runs to appears (0: for as long as that lasts); sag, blocks the middle hangs; wobble, blocks it ripples near the hand; alpha, its opacity (a rope or streak); target_height, the share of a held body's height it reaches up to (0.6); color, "#RRGGBB": tints a rope or streak, or colours a glow tube (its core paler) in place of the palette |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_attach | onAttach | - | The head took hold of a block or a body (or a summon bound it to one): the actions are aimed at it. | owner: whoever it belongs to (the thrower, the summoner); source: the tether; hit: what it took hold of (a body or a block; none for on_tick and on_release unless it holds a body); stats: the engine defaults (damage 3, radius 3, 6 seconds, amplifier 0), so write the numbers into the actions |
on_release | onRelease | - | It let go, for whatever reason, just before it goes. | owner: whoever it belongs to (the thrower, the summoner); source: the tether; hit: what it took hold of (a body or a block; none for on_tick and on_release unless it holds a body); stats: the engine defaults (damage 3, radius 3, 6 seconds, amplifier 0), so write the numbers into the actions |
on_tick | onTick | - | Every tick it lasts, on the server (use the hook's every to thin it out). | owner: whoever it belongs to (the thrower, the summoner); source: the tether; hit: what it took hold of (a body or a block; none for on_tick and on_release unless it holds a body); stats: the engine defaults (damage 3, radius 3, 6 seconds, amplifier 0), so write the numbers into the actions |
on_owner_swing | onOwnerSwing | - | Its owner punched while it is out, holding the launcher that fired it (after the reel starts, when it does): the actions are about the owner (guard with if), aimed at the body it holds if any. | owner: whoever it belongs to (the thrower, the summoner); source: the tether; hit: what it took hold of (a body or a block; none for on_tick and on_release unless it holds a body); stats: the engine defaults (damage 3, radius 3, 6 seconds, amplifier 0), so write the numbers into the actions |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
thematic:zone#
One entity for a lingering area, a pulse, a wall cell or a decal: it sits where it was put (or follows its owner, or keeps the velocity it was thrown with), lasts its lifetime, does something to the bodies inside it, and is drawn by its visual. Every option is read live, so a /reload retunes zones already out; size, spawn_group, track_range and update_rate are the shared entity fields.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
shape | "box" | "sphere" | "cylinder" | "ring_expanding" | "cone" | "wall" | "line" | "box" | what counts as inside it: box (its own hitbox, the size field); sphere (radius around its middle); cylinder (radius around it, height up from its feet); ring_expanding (a band thickness wide at radius, as tall as height: a shockwave, with grow_per_tick); cone (radius long, angle wide, along the way it faces); wall (radius either side across the way it faces, height tall, thickness deep); line (a thin line radius long out along the way it faces, to the first block, thickness wide: a body whose box crosses it is inside; a tripwire) | |
radius | number | 1 | blocks: the size of every shape but box | |
grow_per_tick | number | 0 | blocks the radius grows each tick it lasts; negative shrinks it (never below 0) | |
height | number | 1 | blocks: how tall a cylinder, ring or wall is | |
thickness | number | 1 | blocks: how wide a ring's band is and how deep a wall is | |
angle | number | 45 | degrees: how wide a cone is, edge to edge | |
lifetime | number | 100 | ticks it lasts before it goes on its own (20 is one second). A summon's lasts, or a saved lifetime under nbt_keys.lifetime, overrides it for one zone | |
sustained_by | string | - | an ability id: while its owner is a player in a suit with that ability running, the zone does not run out | |
stats_from | string | - | an ability id: its hooks' actions read that ability of its owner's tuned numbers (damage, radius, duration, amplifier), so a move's cry or blast hits as hard as the move is tuned; left out, or when the owner wears no such ability, the engine defaults | |
nbt_keys | { lifetime?: string, age?: string } | { "lifetime": "ZoneLifetime", "age": "ZoneAge" } | the keys it saves its lifetime and its age under, so a saved zone comes back with the time it had left; a spawner may hand it a lifetime through the same key | |
follow_owner | boolean | false | it stays at its owner's feet, moving with them | |
velocity | true | { gravity?: number, drag?: number, pierce?: boolean } | - | it moves: each tick by the velocity it was thrown or summoned with, falling gravity blocks a tick more each tick (0) and keeping drag of its speed (1); it runs on_hit on the first body in its path and on_block on the first block, and goes, unless pierce, when it only runs on_hit. Left out, a zone stays where it was put | |
settle | { fall?: number } | - | it sinks fall blocks a tick (0.02) unless it touches a block or another zone of the same id that touches one: cells stick together and to the ground, as honey does | |
solid | boolean | false | it stops hitscan shots and gun beams as a block would, and can be hit by them | |
particles | { particle: string, every?: number, count?: number, spread?: number, velocity?: [x: number, y: number, z: number] } | - | what it gives off: count particles (1) every ticks (20), scattered spread blocks across (0.5) around its middle, drifting at velocity blocks a tick ([0, 0, 0]). Drawn on the client only | |
contact | { margin?: number, once_per_tick_key?: string, while_owner_active?: string, goes_after?: number, push?: { factor?: number, max_speed?: number }, breaks_on?: { speed_above?: number, trait?: string, sound?: string, particles?: number, effects?: string[] } } | - | how it treats the living bodies inside it, each tick on the server: margin widens a box shape by that many blocks; once_per_tick_key lets only one zone act on a body each tick (a cluster of cells shares the key, kept on the body under that name); goes_after is ticks: once on_contact has acted on a body it acts on no other and the zone goes that many ticks later (a tripmine's spring); while_owner_active does nothing unless the owner is a player with that ability running; push speeds a body sliding through it by factor (1.05), never past max_speed blocks a tick (0.45); breaks_on shatters it when a body crosses it faster than speed_above blocks a tick (level speed; 0.5) and, when given, has the wearer trait trait: it plays sound, bursts particles of its block visual, runs on_break and effects (ability effect ids) on that body, and goes | |
gun_hits | { guns: string[], radius?: number, height?: number, fill_depth?: number, max_new?: number, effects?: string[] } | - | guns (item ids) whose shots build this zone as cells: a shot into a block, or into a cell already there, grows a rough dome radius blocks across (2) and height blocks tall at its middle (3), each column reaching down at most fill_depth blocks (4) to meet the ground, at most max_new new cells a shot (16), only where the shooter may build and each new cell touching a block or another cell; the cells already there have their lifetime restarted. A living body the gun hits takes effects (ability effect ids) | |
visual | { kind?: "none" | "block" | "decal" | "trail" | "sonic_ring" | "hull" | "laser" | "molten" | "crystals", block?: string, textures?: { until?: number, texture: string }[], texture?: string, size?: number, light_boost?: number, seen_with_trait?: string, color?: string, length?: number, width?: number, align?: "ground" | "facing", alpha?: number, cracks?: number } | { "kind": "none" } | how it is drawn: none (the default; particles only); block (a block's model filling its box, e.g. "minecraft:blue_ice"); decal (a flat square size blocks wide on the ground under it, texture, or the first of textures whose until, in ticks of its age, it has not reached; light_boost adds to the block light it is drawn in; seen_with_trait shows it only to a viewer with that wearer trait; align "facing" stands it square to the way the zone faces instead, flush on a wall when summoned at: "face"); trail (a ribbon behind a moving zone, length ticks long and width blocks wide at its widest, in color: "#RRGGBB", or "owner_corps" for the colour of its owner's corps, drawing nothing without one); sonic_ring (a sonic-boom ring facing the camera, growing 0.2 blocks a tick up to size blocks across its radius); hull (a translucent faceted shell fitted round the zone's box with bevelled edges and bright frosted rims, texture tiled over it a block to a repeat, tinted color, alpha opaque (1), flashing in as it forms; with cracks, white cracks spread over its faces until it is cracked all over that many seconds in: a body sealed in ice or glass, seen through it); laser (a tripwire laser out of a small emitter pod along the way the zone faces -- out of the wall when summoned at: "face" -- to the first block or size blocks (12): a coloured body that reads at noon, an additive halo width blocks wide (0.08) throbbing three times a second, a white-hot core, a bright dash running its length every half second and flares at the lens and where it ends; in color ("#FF2020"), full bright, kept a few pixels wide however far off); molten (a bubbling puddle of molten goop lying on the ground, size blocks across, in color ("#FF7A10"): a lobed blob white-hot at its heart and crusted at its rim, bubbles swelling and popping, a glow round it, cooling over the last quarter of its lifetime -- keep lifetime equal to the summon's lasts); crystals (a frost patch size blocks across with frost cracks and a cluster of crystal spikes, tinted color ("#BFE9FF"), sprouting over its first ticks and melting over the last third of its lifetime) |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_tick | onTick | - | Every tick it lasts, on the server (use the hook's every to thin it out): once, at the zone. | owner: whoever made it (the thrower, the summoner; none for a zone nothing owns); source: the zone; hit: the body or block the hook is about (none for on_tick); stats: the engine defaults (damage 3, radius 3, 6 seconds, amplifier 0), so write the numbers into the actions |
on_contact | onContact | - | For each living body inside it, each tick (the hook's every thins it out), when contact lets it (see contact). A body its owner may not hit is still inside it: the actions' own checks decide. | owner: whoever made it (the thrower, the summoner; none for a zone nothing owns); source: the zone; hit: the body or block the hook is about (none for on_tick); stats: the engine defaults (damage 3, radius 3, 6 seconds, amplifier 0), so write the numbers into the actions |
on_break | onBreak | - | A body broke it (contact.breaks_on): the actions are aimed at that body, then the zone goes. | owner: whoever made it (the thrower, the summoner; none for a zone nothing owns); source: the zone; hit: the body or block the hook is about (none for on_tick); stats: the engine defaults (damage 3, radius 3, 6 seconds, amplifier 0), so write the numbers into the actions |
on_hit | onHit | - | A moving zone (velocity) ran into a body: the actions are aimed at it; then the zone goes unless velocity.pierce. | owner: whoever made it (the thrower, the summoner; none for a zone nothing owns); source: the zone; hit: the body or block the hook is about (none for on_tick); stats: the engine defaults (damage 3, radius 3, 6 seconds, amplifier 0), so write the numbers into the actions |
on_block | onBlock | - | A moving zone ran into a block: the actions run where it struck; then the zone goes. | owner: whoever made it (the thrower, the summoner; none for a zone nothing owns); source: the zone; hit: the body or block the hook is about (none for on_tick); stats: the engine defaults (damage 3, radius 3, 6 seconds, amplifier 0), so write the numbers into the actions |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
thematic:owner_copy#
A copy of whoever brought it in, wearing their suit: an after-image frozen in the pose it was cast in (copy frozen_pose), a projection that walks near its owner and copies what an onlooker sees of them (live), or a mob in its owner's clothes that picks targets and charges them (ai). Brought in by thematic:summon (its owner, lasts, health, damage, its place in the group, and a mimic's mirror, look and behaviour arrive from the summon) or by Java. It never drops anything and has no name tag. Every option is read live, so a /reload retunes copies already out; size and the attributes (health, speed, attack) are the shared entity fields.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
copy | "frozen_pose" | "live" | "ai" | "frozen_pose" | how it copies its owner: frozen_pose holds the owner's pose, swing and stride from the moment it was cast, sinking to the ground below it and (with animate_as_owner) sliding to a stop on his speed (a move can turn it with look_at and it keeps that facing); live walks on its own legs, keeps loose station near its owner (see station), flies when he flies, swings when he swings and shows his moves' visuals; ai picks the nearest body that is not its owner or another copy, charges it and hits whatever stands beside it (see ai), on its own legs with leap and legs at rest with glide. No copy ever moves its legs with its owner's | |
lifespan | number | 100 for frozen_pose, 400 for live, 800 for ai | ticks it lasts (20 is one second): a frozen_pose or ai copy goes once it is older; a live one counts it down, keeps the count in its save, and fades without a burst when it runs out. A summon's lasts overrides it | |
sustained_by | string | - | an ability id: an ai copy goes as soon as its owner is not running it | |
owner_ability | string | - | an ability id: a live copy goes as soon as its owner no longer has it (the suit came off); a summon hands in the move that brought it in instead | |
hittable | boolean | false for frozen_pose, else true | whether anything can hurt it. A live copy is still spared by the world (falls, walls, fire: only an attacker hurts it), by its owner and by copies of its own id | |
solid | boolean | true | whether blows, bumps, the crosshair and projectiles meet it; false lets them pass through | |
hurts_owner | boolean | number | false | a blow that hurts it hurts its owner (never one the owner struck): true for the same amount, a number for exactly that much (same damage source) whatever the blow | |
die_with_owner | boolean | false | it goes as soon as its owner is dead or gone (logged out, unloaded), in every copy mode | |
suit | boolean | true | whether it is drawn in its owner's suit; false draws the bare figure | |
tint | string | number | - | "#rrggbb": its suit is drawn multiplied by this colour | |
alpha | number | 1 | how solid its suit is drawn, 0 to 1 | |
draw_alpha | number | 0.5 for ai, else 1 | how solid a live or ai copy's whole figure is drawn, 0 to 1 | |
phased | boolean | false | a live copy mirrors its owner's phase: drawn as he is, shrugging and breaking on what he does, and passing through the world when he does | |
mirror_owner | boolean | false | a live copy shows its owner's every move: his clips and poses, his moves' visuals (beams, glows) drawn from its own body, his look while he uses one, and his rise when a move lifts him. Only the look of them: what it deals is still its summon's share | |
shown_to_owner | boolean | false | a frozen copy is drawn for its owner in first person too; false hides it from him while he looks through his own eyes, as an after-image at his back is | |
animate_as_owner | boolean | true | the suit's animation clips play as they do on its owner now (an after-image of a flyer shows his flight); false keeps the copy's own pose, so a body left lying or standing still does not play his moves | |
targetable | boolean | false | whether ability hits and aimed moves may pick it as a target | |
ground_search | number | 2 | blocks a frozen_pose copy looks down for solid ground to stand on | |
fade_by_age | boolean | { ticks?: number, suit_start?: number, suit_step?: number, suit_until?: number } | true for frozen_pose, else false | the copy thins out by age: its suit starting at suit_start (0.8) and losing suit_step (0.15) a tick, gone once older than suit_until ticks (7), and a frozen_pose copy's whole figure from solid to nothing over ticks (20); false draws it solid | |
link_lightning | boolean | false | a frozen_pose copy draws a crackle of lightning to the next copy its owner left (in the order they were cast), the newest to the owner, in the owner's speed-line colour | |
swap_with_owner | { chance?: number, owner_effect?: { effect: string, duration?: number, amplifier?: number } } | - | an ai copy trades places with its owner: each tick, at chance (0.02); the owner then takes owner_effect (a status effect id, for duration ticks at amplifier, hidden). Never while its owner has the ai's still_while_trait | |
ai | { movement?: "glide" | "leap", scan?: [x: number, y: number, z: number], charge?: { speed?: number, range?: number, cooldown?: number, ready_at?: number, min_distance?: number, arrive?: number, lift?: number, keep_on_stop?: number, knockback?: number, prefer_target?: boolean }, touch?: { reach?: number, share?: number, ability_damage?: boolean, swing?: boolean, target_looks?: boolean, knockback?: number, clip?: string, discard_after?: number }, pounce?: number, still_while_trait?: string, jitter?: number, breaks_when_hurt?: boolean, attack_bonus?: number, ability_damage?: boolean, strike_clip?: string } | - | how an ai copy fights. movement glide (weightless, through blocks, charging level and stopping dead) or leap (normal physics, charging straight at the target with a lift of blocks a tick, keeping keep_on_stop of its speed on arrival); movement fills every default below. scan: the box it looks for targets in, blocks each way (25, 10, 25 / 20, 8, 20). charge: when its timer is at or below ready_at (5 / 10) it runs at the first target further than min_distance (3 / 0) and within range (12 / 16) at speed blocks a tick (2.8 / 5.25), resetting the timer to cooldown ticks (15 / 10), and strikes once within arrive blocks (2.24 / 2.45), knocking the target back knockback times harder (1.3 / 1.5); with prefer_target it charges the target a summon handed it first, whenever that is alive and within range. touch: the body right beside it (within reach, 2; 0 turns the touch off) takes share (0.1) of its owner's attack, or with ability_damage the sustained_by move's damage; swing throws a random hand; target_looks turns the target to face it; clip plays on its suit's clip controller; discard_after removes it that many seconds later (glide: swing; leap: target_looks, clip super_sonic_punch, 1 second). pounce: a leap goal at this strength (0: none; leap 0.4). still_while_trait: a wearer trait; while its owner has it the copy cannot be hurt, does not charge, walk or trade places, and jitters jitter blocks (0.045) beside its place in the group. breaks_when_hurt: gone at the first blow, server side too (leap). Its own strike deals the damage a summon handed it, else attack_bonus (0 / 4) plus its attack attribute, or with ability_damage (leap) the sustained_by move's damage; strike_clip plays on its suit's clip controller each time that strike lands. A target a summon handed it is kept while it is alive. What slows or roots its walking (a slow, prone, immobile) slows or stops its charge too | |
station | { leash?: number, regroup?: number, regroup_every?: number, loose?: number, spread?: number, punch_reach?: number, punch_every?: number } | - | how a live copy keeps near its owner: it walks back when further than loose blocks (3), to its place in the group give or take spread (3); put back beside him at once past leash (16), and every regroup_every ticks (60) when past regroup (7). It punches a body within punch_reach (2.5) that its owner may hit, for its share of his hit, at most once every punch_every ticks (20) | |
death_burst | boolean | { radius?: number, knockback?: number, sunlight_scaled?: boolean } | - | a live copy that is destroyed (not one that runs out) bursts: every body within radius (3) its owner may hit takes its share of his hit, scaled by his solar strength when sunlight_scaled, and is thrown knockback (0.45) blocks a tick away and up; with a flash, flames and a bang |
thematic:mob#
A humanoid mob on the criminal brain: it picks a target (whoever hurt it, then anyone its faction may fight), chases and swings at it, opens doors, keeps room from its allies, may break and run at low health and steps around what blocks it. Its brain adds behaviour ids, it can wear a suit and fire its abilities, show a boss bar, fly, and trade. An encounter can lead with it as its boss. Give it attributes (minecraft:generic.max_health, ...), a size such as [0.6, 1.95] and spawn_group monster; its render block's model is drawn unless render.kind names another (worn_suit draws the suit it wears; humanoid draws its model with a turning head, its looks and the shared humanoid clips). With brain.base "none" it runs only the behaviours its brain lists: a brute, a boss or a shopkeeper of its own.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
brain | { base?: "criminal" | "none", core?: (string | { id: string, cooldown?: number, min_range?: number, max_range?: number, on_ground?: boolean, after_age?: number, has_target?: boolean, not_while?: string | string[], animation?: string, of?: unknown[], [option: string]: unknown })[], idle?: (string | { id: string, cooldown?: number, min_range?: number, max_range?: number, on_ground?: boolean, after_age?: number, has_target?: boolean, not_while?: string | string[], animation?: string, of?: unknown[], [option: string]: unknown })[], fight?: (string | { id: string, cooldown?: number, min_range?: number, max_range?: number, on_ground?: boolean, after_age?: number, has_target?: boolean, not_while?: string | string[], animation?: string, of?: unknown[], [option: string]: unknown })[] } | - | behaviours added to its brain: core always runs, idle while it has no target, and of fight the first that can start runs. base "criminal" (the default) starts from the criminal brain (targeting, chase, melee swing, doors, squad spacing, morale, getting unstuck); base "none" starts from nothing but these entries (and, first in fight, forgetting a target its faction may no longer fight). Each is a behaviour id or { id, ...options }: thematic:slam_attack, thematic:shoot_attack, thematic:target_missile_attack, thematic:hover_flight, thematic:open_doors, thematic:squad_spacing, thematic:morale_break, thematic:block_stance, thematic:grab_throw, thematic:area_strike, thematic:heavy_melee, thematic:pounce, thematic:tackle, thematic:ground_slam, thematic:roar, thematic:throw_item, thematic:melee, thematic:walk, thematic:walk_to_target, thematic:strafe_target, thematic:random_walk, thematic:walk_to_block, thematic:float, thematic:target_or_retaliate, thematic:look_at_target, thematic:look_at_player, thematic:random_look, thematic:idle, thematic:first_of, thematic:one_of. first_of and one_of group entries of their own in of: the first that can start runs, or one at random. Every entry also takes cooldown (ticks before it starts again), min_range / max_range (blocks to its target: above the first, at most the second), on_ground, after_age (ticks it must have lived), has_target, not_while (stances it may not start in) and animation (a name from animations, played as it starts). slam_attack: hit_delay 14, radius 6, damage 15, lift 0.75, particle "minecraft:large_smoke", ring_height 6, ring_radius 6, ring_density 35. shoot_attack: delay 10, range 32, duration 120, pulse_every 10, pulse_damage 2.5, half_angle 25, flag "geckolib:beam", sound "heat_vision", taunt (a sound id), taunt_chance 0.2. target_missile_attack: missile (an entity id, required), speed 1.15, delay 20, attack_radius 64, sound "heat_vision", muzzle_eye_factor 1.15, muzzle_forward 1.2, muzzle_right 0.9. hover_flight: ascend_trigger_height 4, ascend_trigger_distance 16, hover_height 6, ascend_acceleration 0.35, ascend_max_speed 0.6, ascend_timeout 40, hover_speed 0.22, hover_lerp 0.25, hover_max 200, descend_trigger_distance 10, descend_height_tolerance 1, descend_acceleration 0.25, land_below_health 0.3, landing_cooldown 100, thump_radius 4, thump_damage 8, thump_knockback 0.4, take_off_animation, controller "actions". block_stance: stance "blocking", hold 60, range_min 8, range_max 32, chance_start 0.3, chance_growth 0.5, chance_over 20, chance_cap 0.8, against_ranged_weapons true, projectile_radius 32, sound. grab_throw: reach 4, duration 21, hit_tick 10, damage 8, push_back 1.8, push_up 1.2, effects, times 1, start_sound, hit_sound. area_strike: radius 5, height 2, needed 2, duration 25, hit_tick 20, damage 20, min_falloff 0.2, knockback 2, knock_lift 0.5, effects, spawn (an entity id), spawn_y 0.5, times 1, start_sound, hit_sound. heavy_melee: hit_tick 10, hold 60, effects, bonus_damage 12, start_sound, hit_sound. pounce: stance "pouncing", speed 2.5, lift 0.8, max_ticks 30, hit_box 1.5, damage 13, knockback 2.5, knock_lift 0.5, effects, self_effects, corps, trail_count 3, needs_sight true, start_sound, land_sound. tackle: stance "tackling", chance 0.3, duration 20, speed 1.8, reach 2, damage 12, carry 1.5, carry_lift 0.5, effects, collateral_box 1, collateral_damage 6, collateral_push 0.5, collateral_lift 0.3, start_sound. ground_slam: radius 6, height 2, damage 15, knockback 1.5, knock_lift 0.8, near 0.5, near_effects, self_lift 0.5, corps, ring_step 20, sound. roar: below_health 0.5, enemies 3, enemy_radius 10, radius 16, effects, player_effects, self_effects, push 0.5, lift 0.2, sound. throw_item: items (required), corps, entity "thematic:thrown_construct", spawn_offset 1.5, speed 2.5, lead 2, lifetime 1200, chance 1, needs_sight true, particle_count 8. melee: delay 10. walk_to_target: speed 1, far_speed, far_distance. strafe_target: distance, speed 1. random_walk: radius 10, height 7, speed 1. walk_to_block: block (required), range 16, height 8, speed 1, distance 4, search_min 200, search_max 400, give_up 1200. float: rise_chance 0.8. target_or_retaliate: alert_allies false. look_at_target: min, max. idle: min 30, max 60. An effects list is [{ id, duration (ticks), amplifier }]; a sound is an id or { id, volume, pitch }; corps is a corps colour ("yellow") | |
suit | string | { id: string, iv?: number } | - | a suit (a boss suit's armor id) it puts on the first time it ticks, pinned to rarity iv (3); it fires the suit's mob-usable abilities its phases unlock | |
phases | { health_below: number, unlock: string | string[] }[] | - | which of its suit's abilities it may use: those of every phase whose health_below (a fraction of its max health) it is at or under. An encounter that leads with it decides instead | |
boss_bar | { color?: string, darken_sky?: boolean } | - | a boss bar shown to the players who see it: color is a boss bar colour's name ("blue"), darken_sky (true). An encounter that leads with it shows its own | |
persistent | boolean | false | it never despawns | |
morale | { break_chance?: number } | { "break_chance": 0.35 } | the chance (0 to 1) that it is the type to break and run at low health; 0 never runs | |
animations | { [name: string]: string } | - | clips (from its animation file) a behaviour's animation or hover_flight's take_off_animation can play, by the name they give; played on its actions controller | |
scale | number | 1 | the size it is drawn and collides at, as a multiple (Pehkui) | |
merchant | { pick?: number, restock?: boolean, trades: { buy: Stack, buy_second?: Stack, sell: Stack, max_uses?: number, xp?: number, price_multiplier?: number, fallback?: object }[] } | - | it trades: right-clicked, it offers pick of its trades (all of them), chosen once and saved. A Stack is an item id, or { item, count } / { suit, alt, count } where count is a number or [min, max] rolled per offer; a trade whose stack cannot be made offers its fallback trade instead. A merchant is an NPC: hostile mobs leave it alone | |
clips | { walk?: string, run?: string, idle?: string, jump?: string, swing?: string, die?: string } | { "walk": "move.walk", "run": "move.run", "idle": "misc.idle", "jump": "move.walk", "swing": "attack.swing" } | the clips (from its animation files) its movement controller plays walking, running, idle and off the ground, its Attack controller plays as it swings, and a Death controller plays as it dies (none without) | |
damage_taken | { attacker_holding?: string, while?: string, damage_type?: string, multiplier: number, sound?: string | { id: string, volume?: number, pitch?: number }, only?: boolean }[] | - | rules, in order, for the damage it takes: each whose stance (while) it holds and whose attacker's main hand holds the held item kind attacker_holding ("gun", "bow"...) and whose hit is of damage_type (an id or #tag, e.g. "#thematic:guns") multiplies the damage by multiplier and plays its sound; an only rule is the last to apply | |
stances | { [stance: string]: { pushable?: boolean, projectiles?: boolean } } | - | what holding a stance (a behaviour's stance: "blocking", "tackling"...) changes: whether it can be pushed and whether projectiles hit it (both true) | |
eye_height | number | - | its eye height in blocks; left out, 0.85 of its height | |
sounds | { spawn?: string | { id: string, volume?: number, pitch?: number }, death?: string | { id: string, volume?: number, pitch?: number }, every?: { ticks: number, sound: string | { id: string, volume?: number, pitch?: number } } } | - | sounds it makes on its own: as it spawns, as it dies, and every ticks of its life | |
melee | { lift?: number } | - | its melee hits: lift is upward speed each landed hit adds (0) | |
looks | { name?: string, model?: string, texture?: string }[] | - | looks it can wear in place of its render block's (the humanoid render kind draws them; saved as Type): a name (literal text, shown unless it has a custom name), a geo model's name and a texture; the first is the one it starts with, and a Java hook may give it another |
thematic:owned_summon#
A pet or minion that works for whoever brought it in: a drone, a jet, a school of fish, a swarm of bats, a mount, a tentacle. base picks what it is built as (a hovering or fixed-wing flier, a swimmer or a prop drawn from the render block's GeckoLib model, or a vanilla bat or horse reskinned), and each base reads its own group of options below; every group defaults to what that base's first user did, so a bare base is a working summon. Brought in by thematic:summon (its owner, its target, lasts, damage, its place in the group and the summon's options block arrive through the summon) or by Java. Every option is read live, so a /reload retunes summons already out, except base, which picks the class and needs a restart. Health, speed, attack and follow range are the shared attributes.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
base | "hover_flier" | "fixed_wing" | "swimmer" | "prop" | "minecraft:bat" | "minecraft:horse" | "squad" | "hover_flier" | yes | what it is built as: hover_flier hangs in the air, hunts the nearest player (attack_nearest) and keeps near its owner (follow_owner); fixed_wing flies like an aircraft, circling its target (orbit), diving on it in strafing passes (strafe) and firing shots (attack.ranged, attack.strafe_fire) -- a summon's options retune one: orbit_radius and orbit_height (a tight circle, e.g. right over the target), strafe: false (no passes), gun_every (ticks between gun shots straight at the target), missile_every, bombs_every with bomb_share, bomb_homing and bomb_shot (bombs dropped onto it), and kamikaze with kamikaze_share, kamikaze_radius and kamikaze_seconds (when its time is up it dives into the target and explodes instead of just going); swimmer chases bodies in the water; prop stands where it was put, plays its clip and goes; minecraft:bat and minecraft:horse are the vanilla animals, owned; squad hovers in a slot of its owner's formation and fights with the moves of the suit it wears (see squad), drawn as the suit it wears, scaled by render.scale (render.model names the suit for one wearing none, e.g. a morph drawing it) |
lifespan | number | 240 for hover_flier, 280 for fixed_wing, 26 for prop, else 0 | ticks it lasts (20 is one second); a summon's lasts overrides it; 0 keeps it until something else sends it away. A hover flier counts its own ticks (and saves the count); the others go once older than it | |
damage | number | 12 for hover_flier, 20 for fixed_wing and prop | what its own hits deal, in raw points (a hover flier's touch, a fixed-wing flier's shots and death explosion); a summon's damage overrides it | |
die_with_owner | boolean | true for hover_flier, else false | it goes as soon as its owner is gone or dead | |
die_with_ability | (string | { ability: string, only_if_held?: boolean })[] | { every?: number, abilities: (string | { ability: string, only_if_held?: boolean })[] } | - | moves its owner must keep running, checked every every ticks (20) while its owner is a player: it goes when he is not running one; with only_if_held, only when he has that move and is not running it. A summon's options.sustained_by (an ability id) adds one | |
weightless | boolean | true for hover_flier and fixed_wing, else false | a summoned one hangs in the air where it was put (no gravity) | |
follow_owner | { distance?: number, height?: number, speed?: number } | - | a hover flier heads for the point height (1.5) blocks above its owner at speed (0.35) while it is farther than distance (3) blocks from it | |
attack_nearest | { range?: number, players_only?: boolean, search_every?: number, speed?: number } | - | a hover flier hunts the nearest body that is not its owner within range (32) blocks, only players unless players_only is false, looking again every search_every (10) ticks while it has none, and flies at it at speed (0.6) | |
attack | { melee?: { reach?: number, sound?: string, particle?: string, particle_count?: number, chase_speed?: number }, ranged?: { shot?: string, count?: number, every?: number, jitter?: number, ahead?: number, speed?: number, lead?: number, homing?: number }, strafe_fire?: boolean | { shot?: string, damage_share?: number, speed?: number, sound?: string }, death_explosion?: boolean | { radius?: number, fire?: boolean, break_blocks?: boolean } } | - | how it fights. melee: a hover flier hits its prey for its damage (magic its owner caused) every tick it is within reach (1.5), with sound (minecraft:entity.iron_golem.hurt) and particle_count (30) of particle (minecraft:electric_spark) at the prey; a swimmer chases at chase_speed (3). ranged: a fixed-wing flier fires count (3; a summon's options.missiles replaces it, options.extra_shots adds to it) shots at its target, one every every (30) ticks and up to jitter (10) more, launched ahead (3) blocks in front of its eyes at speed (10), aimed lead (0.8) of the way to where the target is going and homing at homing (0.9); shot (thematic:missile_entity) is a shot id: one a mod registered (SummonShots), a throwable, or any entity type. strafe_fire: every tick of a strafing pass it fires shot (thematic:laser_entity) for damage_share (0.1) of its damage at speed (4.5), with sound (thematic:m134minigun). death_explosion: shot down, it explodes for its damage over radius (3), with fire and breaking blocks unless told not to (fixed_wing only; the last two default on for it) | |
orbit | { radius?: number, radius_jitter?: number, height?: number, height_jitter?: number, degrees_per_step?: number, slot_degrees?: number, arrive?: number } | - | how a fixed-wing flier circles its target (else the spot it was sent to): radius (60) blocks out plus up to radius_jitter (12), height (20) blocks up give or take half of height_jitter (4), stepping degrees_per_step (4) round each time it comes within arrive (15) blocks of its point; each one brought in together keeps slot_degrees (120) from the last | |
strafe | { first_after?: number, first_jitter?: number, again_after?: number, again_jitter?: number, approach_distance?: number, approach_height?: number, approach_height_jitter?: number, pass_height?: number, overshoot?: number, end_reach?: number, climb_after?: number, climb_jitter?: number } | - | a fixed-wing flier's passes over its target: the first after first_after (20) ticks plus up to first_jitter (20), the next again_after (40) plus up to again_jitter (60) after one ends; it starts approach_distance (48) blocks out on a random bearing and approach_height (20) plus up to approach_height_jitter (10) up, passes pass_height (6) above the target and aims overshoot (30) blocks past it, ending within end_reach (10) of that point, then climbs to circle climb_after (20) plus up to climb_jitter (10) blocks above the ground under its target | |
wall_damage | number | 2 for fixed_wing, else 1 | what a knock into a wall (suffocating, flying into one) is multiplied by | |
trail | false | { particle?: string, dust?: string | number, count?: number, every?: number } | hover_flier: { particle: "minecraft:smoke", dust: "#ff0000", count: 3 }; fixed_wing: { particle: "minecraft:smoke", every: 2 } | particles it leaves every every ticks: a hover flier sprays count round its body, each at random a dust of the dust colour ("#rrggbb") or particle; a fixed-wing flier trails particle behind it (its summon may hand another, or its owner's corps colour with tint_from_owner) | |
ambient | false | { sound: string, every?: number, volume?: number } | hover_flier: { sound: "minecraft:entity.bee.loop" } | a sound it plays every every (5) ticks at volume (0.4), a little off pitch each time | |
separation | boolean | { every?: number, push?: number } | on for hover_flier | hover fliers of one kind nudge apart by push (0.05) when they touch, checked every every (4) ticks | |
sounds | { ambient?: string, hurt?: string, death?: string, volume?: number } | - | a fixed-wing flier's own sounds (the phantom's) and their volume (0.7) | |
tint_from_owner | boolean | false | a summoned fixed-wing flier trails its owner's corps particle, and is drawn in its colour, unless the summon's options.trail names one (a particle id) | |
medium | "water" | "any" | "water" for swimmer | where a swimmer's prey must be: in the water, or anywhere | |
spare_kin | boolean | true | a swimmer never goes for its owner's other summons of its kind | |
never_roosts | boolean | true for minecraft:bat | a bat never hangs up to sleep while it has nothing to chase | |
tame | boolean | true for minecraft:horse | a horse is tame from the start | |
keeps_gear | boolean | true for minecraft:horse | a horse's saddle and barding are the move's: it has no inventory screen and drops nothing | |
dismiss_when_unridden | boolean | true for minecraft:horse | a horse goes as soon as nobody rides it | |
saddled | boolean | true for minecraft:horse | a horse brought in by a summon arrives saddled | |
clip | { controller: string, name: string, animation: string, triggers?: { [name: string]: string }, on_summon?: boolean } | - | a prop's GeckoLib clips: its controller, the default trigger name and animation in the model's animation file; triggers adds more trigger-name to animation pairs, and on_summon (true) plays the default as the prop arrives | |
follow_up | { at?: number, push_y?: number } | - | a prop pushes the bodies it was handed (the ones its move already struck) by push_y (-2, down) when it is at (10) ticks old, once | |
collidable | boolean | true | whether bodies collide with it and push it; false lets mobs and players walk through it, and it neither pushes nor is pushed | |
lasts_after_projectile_hit | number | - | a prop: ticks it has left once a projectile springs it (on_projectile_hit), then it goes by itself, whatever its owner is doing; unset keeps its lifespan | |
squad | { formation?: { kind: "surround" | "escort" | "ring", radius?: number, height?: number, speed?: number, flag?: string, defend_only?: boolean, passes?: boolean, tighten?: number, engage?: "any" | "owner_targets" }[], kit?: string[], focus_flag?: string, spread_radius?: number, engage_range?: number, retreat_below?: number, engage?: "any" | "owner_targets", engage_memory?: number, stand_in?: boolean, suit?: string, face_turn?: number, face_pitch_max?: number, effect_duration_times?: number, expend?: { speed?: number, seconds?: number, reach?: number, damage?: number, turn?: number, homing_range?: number, radius?: number, trail?: { particle: string | object, count?: number, spread?: number, speed?: number }[], launch?: { particle: string | object, count?: number, spread?: number, speed?: number }[], flame?: { core?: string, outer?: string, length?: number, width?: number, flicker?: number }, launch_sound?: string, burst_sound?: string }, offline_on?: { element: string, seconds?: number, sound?: string }, chain?: { element: string, radius?: number }, scout?: { structures: string[], every?: number, chunks?: number } } | - | a squad flier: formation is its owner's patterns, the one whose flag the owner has set (setFlag) else the first with none -- surround keeps the squad on a ring radius (5) round the target, height (1.5) up, alternately higher and lower; escort keeps an arc radius behind the owner and with passes flies passes through the target while the owner is above retreat_below (0.5) of their health; ring keeps a wide ring round the owner; defend_only fights only what hurts the owner or the squad; tighten (0) closes a surround in by up to that share of its radius while the target stays boxed in; speed (0.6) is blocks a tick. A squad falls back round its owner whenever the shared pool (the owner's health) is under retreat_below, whatever the formation. stand_in (false) marks the owner's stand-in body: the rest of the squad forms round it, peels for it and keeps to it instead of the owner while it lives, and it holds where it stands, outside the formation's slots. suit names a boss suit the flier wears instead of a copy of its owner's, so its kit may be moves the owner does not have. Slots are shared out over every squad flier of the owner's by the summon's options.slot. Its target: the owner's locked target, what the owner just hit, what just hit the owner or it, else (engage "any", the default) the nearest monster within engage_range (24) of the owner; engage "owner_targets" picks nothing on its own: only what the owner hurt in the last engage_memory (200) ticks (their own hits, not those their squad landed), what hurt the owner or the squad, and stand-ins (a mimic counts as its owner, and is fought on sight); a formation's own engage overrides the squad's while it is held; with focus_flag set (or none named) the whole squad takes it, else they spread over the enemies within spread_radius (8) of it, one each. kit: the moves of the suit it wears (a copy of its owner's) that it fires at its target, each paced by its own mob() part. expend: what an expend order makes of it -- a homing charge at speed (1.4) blocks a tick that goes off within reach (1.5) of its target, on touching a block or after seconds (6), for damage (60; a summon's damage overrides it) within radius (8), turning onto a body it was sent at by at most turn (24) degrees a tick, following it while it stays within homing_range (64) blocks and falling back to the last place it saw it when it dies or gets that far; trail: particle bursts laid behind it along the path it flew each tick it charges (a fire and smoke streak: a particle is an id or {type: minecraft:dust, color, scale}, count copies scattered by spread blocks at up to speed), launch: bursts thrown once where it takes off; flame: a rendered jet flame cone trailing behind it while it charges (core and outer are "#rrggbb", length (0.9) and width (0.12) in blocks, flicker (0.25) 0..0.9: the same flame a flight profile's jets take; it stretches with speed and is drawn client side); launch_sound and burst_sound: sound ids played as it takes off and where it goes off (the stock rocket whoosh and explosion when left out). effect_duration_times (1): how many times as long a timed status effect lasts on it. offline_on: a hit of that element drops it out of the air for seconds (3) with a power-down sound (sound, default block.beacon.deactivate) and a spark trail on the way down, and one on its owner directly drops the whole squad. chain: a hit of that element on it or its owner jumps to every squad-mate within radius (3), and on from each. scout: in a defend_only pattern the first flier looks every every (100) ticks for the nearest of structures (ids or "#tag"s) within chunks (6) of itself and tells the owner of each new find | |
look | { render_distance?: number, glow?: boolean, tint_from_trail?: boolean, hide_near_viewer?: { distance?: number, while_running: string[] } } | - | how it is drawn beyond the render block: not beyond render_distance blocks (0, the game's own); glow draws the model's texture as a see-through light beam; tint_from_trail colours it by its trail's colour, brightened; hide_near_viewer hides it within distance (1) blocks of a viewer who is running one of while_running (ability ids; "*_suffix" matches any id ending so) |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_projectile_hit | onProjectileHit | - | A prop is struck by a projectile (an arrow, a thrown or fired shot): once, for the first one; the shot then lands as it would have (a display prop turns it away). | owner: whoever brought it in; source and hit: the prop itself, so verbs aimed at the target or searching round the hit (entity_clip, despawn_entity) find it; stats: the engine defaults, so write the numbers into the actions |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
thematic:vehicle#
A vehicle a player drives: a move of type generic_vehicle calls it to its wearer (it drives or flies up and takes them aboard), and only a rider whose suit has that move may climb in. It drives on the ground or flies, burns fuel, hits what it runs into, passes its rider's status effects and fire to them, and a bare-handed attacker next to a slow vehicle pulls its rider out. Its controls take the rider's ability keys in order (the first control the first key). Every option is read live, so a /reload retunes vehicles already out; size (with resizable: true), spawn_group, track_range and update_rate are the shared entity fields, and render names the geo model (render.scale sizes it). A rider's suit layers are hidden while they ride a vehicle in the #thematic:vehicles/hide_rider_layers entity tag.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
movement | "ground" | "flying" | "ground" | ground: it drives, turning toward where its rider looks while it moves; flying: forward input builds thrust, its rider's pitch climbs or dives once it is fast enough, and it sinks slowly while hovering. Each has its own defaults for the numbers below | |
max_speed | number | 3 on the ground, 8 flying | its top speed | |
acceleration | number | 0.05 on the ground, 0.02 flying | speed it gains a tick under throttle | |
deceleration | number | 0.08 on the ground, 0.02 flying | speed it loses a tick coasting | |
braking | number | 0.1 | speed it loses a tick braking | |
turn_rate | number | 3 | degrees a tick it turns under its rider | |
auto_turn_rate | number | 5 | degrees a tick it turns while driving itself to its caller | |
protection | number | 0.1 | the share of an attack on it its rider takes as well | |
max_fuel | number | 100 | the fuel it starts with; it throws its rider out when it runs dry | |
fuel_use | number | 0.1 on the ground, 0.15 flying | fuel it burns a tick | |
mount_distance | number | 8 | blocks around it its caller is taken aboard, and its doors open for a rider who may climb in | |
navigation_interval | number | 5 | ticks between turns toward its caller while it drives itself | |
spawn_distance | number | 12.5 | blocks in front of its caller it arrives (closer, 2.5 at a time, when there is no room) | |
spawn_distance_variation | number | 5 | blocks of random spread on that distance | |
collision_damage | number | 5 | damage per unit of speed to a body it runs into | |
collision_knockback | number | 2 | how hard a body it runs into is thrown, per unit of speed | |
flight | { vertical_sensitivity?: number, hover_descent?: number, max_pitch_angle?: number, pitch_control_speed?: number, air_resistance?: number, vertical_drag?: number, max_pitch_effect?: number, thrust_buildup?: number, banking?: number } | - | a flier's handling: climb per degree of its rider's pitch (0.008), sink a tick while hovering (0.015), the most it tilts (60 degrees), the speed at which pitch takes full effect (3 blocks a second), the share of its speed it keeps a tick sideways (0.995) and up and down (0.98), the most it climbs a tick (0.04), how fast thrust builds (0.02) and how far it banks into turns (0.2) | |
seat_offset | number | - | blocks its rider sits above its feet (negative: below); left out, where the game seats any passenger | |
camera_distance | number | 0 | blocks added to the third-person camera's distance while riding it | |
ride_animation | string | - | a player animation its rider plays while aboard, stopped when they get off | |
rider_stands | boolean | false | its rider stays standing instead of sitting (a board) | |
animation | { speed?: "throttle" | "ground", scale?: number, doors?: boolean } | { "speed": "throttle", "scale": 0.6, "doors": true } | its geo animations: the clip forward loops while its throttle is up and backward otherwise, played at its throttle (or its real ground speed) times scale; with doors, a Door controller plays door_open while a rider who may climb in is near and door_close once one has | |
glow | boolean | false | drawn as translucent full-bright light, like a hard-light construct | |
turret | { pitch?: [number, number], look_pitch?: [number, number], yaw_limit?: number, follow?: number, bones?: { yaw?: string | string[], pitch?: string | string[], look?: string | string[] } } | - | a turret: its heading follows where its rider looks (at most yaw_limit degrees either way of the body, easing follow of the way there a tick, 0.15), and so does its look pitch (within look_pitch, [-22.5, 75]); the aim controls set its aimed pitch (within pitch, [-65, 25]; negative is up). bones names the model bones turned with the heading (yaw), the aimed pitch (pitch) and the heading plus the look pitch (look). A turret vehicle's body steers twice as briskly | |
anchors | { [name: string]: { up?: number, forward?: number, side?: number, frame?: "turret" | "barrel" } } | - | named points its controls fire from: up blocks above its feet, then along the turret's heading (forward ahead, side to the right) or out along the barrel (forward blocks) | |
controls | { key: string, kind?: "aim" | "fire" | "hold_fire" | "eject", passive?: "ram", pitch?: number, throwable?: string, round?: string, from?: string | string[], aim?: "pitch" | "look_pitch", speed?: number, damage?: number, cooldown?: number, every?: number, sound?: string | { id: string, volume?: number, pitch?: number, pitch_spread?: number }, delay?: number, radius?: number, push?: number, lift?: number }[] | - | what its rider's ability keys do, in order: aim (held: tilt the aimed pitch by pitch degrees a tick), fire (a press: throw the throwable from the from anchor along the turret heading and the aim pitch at speed, play sound there, then wait cooldown ticks, 60), hold_fire (held: every every ticks, 2, fire the round (a gunner round id, thematic:bullet) with damage from each from anchor at speed, 4.5, along aim, look_pitch by default, and play sound at the rider), eject (a press: the rider is put out on top and the vehicle is removed after delay seconds, 3, which also restarts the move that called it; cooldown 10 ticks); passive ram hits every body within radius blocks, 1.5, for damage, 22.5, throwing it push along its heading and lift up. key is the control's HUD name (a translation key) and the stem of its saved state |
thematic:seat#
An invisible seat a player rides while sitting on a block: when they get off it stands them on the block above and removes itself. A furniture block's seat option spawns Thematic's own (thematic:chair_entity), so a pack needs its own seat type only to tell its seats apart. Takes no options; give it a small size such as [0.5, 0.6] and spawn_group misc.
thematic:pin#
A wrap round one living body, brought in by thematic:summon with onto: "target": strands reach from the body's middle to every solid block within scan_radius (32 rays), and with hold it pins the body there -- hung off an overhang when a strand reaches above its chest, else feet locked to the ground; AI off, velocity zeroed, Immobile V and Stun each tick -- until its lifetime runs out or the body dies. Without hold it is only drawn (at most anchors strands, never hung). Strands whose block is gone drop every 10 ticks. Drawn by the pin render kind: a cocoon of rope round the body and guy-lines to the anchors, fading over its last second.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifetime | number | 100 | ticks it lasts when the summon gives no lasts (20 is one second) | |
scan_radius | number | 5 | blocks its strands reach out from the body's middle | |
snap_sound | string | - | the sound played at the body when it lets go (a held pin at volume 1, pitch 1; a loose wrap at 0.7, 1.2); left out, none | |
look | { style?: "rope" | "streak" | "glow" | "chain", preset?: "line" | "strand" | "snare_line" | "cocoon" | "cocoon_strap" | "ball", from?: "main_hand" | "off_hand" | "eyes" | "feet", ticks?: number, sag?: number, wobble?: number, alpha?: number, width?: number, palette?: "gold" | "silver", by_ability?: { [ability: string]: "gold" | "silver" }, target_height?: number, hand_lift?: number, color?: string, texture?: string } | - | how the wrap is drawn, a tether look: color ("#RRGGBB") tints the rope strands, and style "chain" draws textured chain links instead (texture, default minecraft:textures/block/chain.png; color then tints the texture) strapped round the body and up from the anchors; left out, the white rope |
thematic:strike#
A lightning strike called down for someone: brought in by thematic:lightning (or thematic:summon, which hands it its owner, damage and hold), it flashes a number of times where it stands, a few ticks apart, with a thunderclap, and each flash hits every living body in a column round it (a block either way, from a block below to three above) that its owner may hit -- for damage, as the owner's attack (or, not credited, a lightning bolt's), holding a body stun seconds (Immobile) and playing victim_animation on a player the first time it holds them. It lights neither blocks nor mobs on fire and charges nothing. One nobody owns goes at once. Drawn by the strike render kind: vanilla's lightning bolt, scaled by render.scale, or with vfx that preset at each flash.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
flashes | number | [number, number] | [1, 3] | [fewest, most] times it flashes, one picked at random when it is made; one number for exactly that many | |
damage | number | 2 | what each flash deals a body it hits, in raw points, unless the spawner says | |
stun | number | 1.5 | seconds a body it hits is held (Immobile), unless the spawner says; 0 holds nobody | |
victim_animation | string | "optic_prone_victim" | the clip played on a player it holds, once per strike; "" for none | |
vfx | string | - | a vfx preset (e.g. a thematic:fractal_bolt one) every flash plays where it lands, sent to every client near it, drawn instead of vanilla's bolt; left out, vanilla's bolt | |
thunder | boolean | true | whether each flash plays its thunderclap | |
sky_flash | boolean | true | whether each flash brightens the sky for everyone who sees it, as vanilla's bolt does |
thematic:arc#
A crackling arc that runs out along the ground from where it is put, the way it was set moving (thematic:summon's velocity): speed blocks a tick, turned a little off its heading at random, jittering zigzag blocks side to side each tick and rising and falling over an arch up to arch_height blocks high (each arc picks its own height, 0.7 to 1.3 of it, and wavelength, 0.5 to 1.5 of arch_frequency cycles a block), through blocks, for lifetime ticks. It hurts nobody: it is a look. Drawn by the arc render kind: a jagged lightning line through the points it has passed, each stretch fading over 20 ticks, in its owner's colour (their suit's; white without one). Never saved.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifetime | number | 15 | ticks it runs when the summon gives no lasts (20 is one second) | |
speed | number | 1 | blocks it runs a tick | |
zigzag | number | 0.4 | blocks it jitters side to side each tick, at most (half of it at least) | |
arch_height | number | 2 | blocks its arch rises at the top | |
arch_frequency | number | 0.15 | arches a block it runs | |
intensity | number | 0.8 | how jagged its line is drawn, 0.1 to 2 |
thematic:mushroom_cloud#
The look of a great blast: from where it is put it rises rise blocks over its lifetime while, on each client, a mushroom cloud boils up round it -- a smoke cap spreading out to radius blocks and climbing, flame and puffs under it, a smoke stem, and at the start a ring of explosions and lava sparks -- over glowing fireball spheres that swell, pulse and fade (the mushroom_cloud render kind). It hurts nobody and burns nothing: pair it with the blast's own damage. thematic:summon's lasts sends it away sooner (the cloud is then cut short, not sped up).
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifetime | number | 70 | ticks the whole cloud takes, rising and fading (20 is one second) | |
radius | number | 16 | blocks the cap spreads out to | |
rise | number | 20 | blocks it climbs over its lifetime |
thematic:perch#
A fixture that hangs over its owner's shoulder, brought in by thematic:summon (its owner must be a player): each tick it eases toward its perch, turns to face its owner's quarry (the nearest body a hunt mark of theirs names, within range) and, while its owner can see that quarry, looses its arrow at it every interval ticks -- the owner's arrow, a full critical draw for damage, led by where the quarry is going. With no quarry it faces the way its owner faces. It is placed, never pushed or hit, goes when its owner dies or its lifetime runs out, and a save never brings it back. A summon's lasts, damage and options range, shots (its lifetime split over that many shots, at least 10 ticks apart) and interval override the definition's. Drawn by the perch render kind: its look's item turned to its aim, full-bright over a halo, kicked back after each shot.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
perch | { up?: number, right?: number, back?: number, bob?: number, ease?: number } | - | where it hangs: up blocks over its owner's head (1.35), right of their body's facing (0.75) and back of it (0.35), bobbing bob blocks (0.06), moving ease of the way there each tick (0.35) | |
lifetime | number | 240 | ticks it stays when the summon gives no lasts | |
interval | number | 30 | ticks between shots when the summon gives neither shots nor interval (at least 5) | |
range | number | 32 | blocks round its owner it looks for their quarry | |
damage | number | 8 | what an arrow hits for when the summon gives no damage | |
arrow | string | "thematic:hunter_arrow" | the arrow it looses (an arrows/ definition id) | |
speed | number | 3.2 | blocks a tick an arrow leaves at | |
spread | number | 0.4 | vanilla's inaccuracy on each shot | |
lead_ticks | number | 6 | ticks of the quarry's motion it aims ahead by | |
aim_height | number | 0.6 | the share of the quarry's height it aims at | |
shot_vfx | string | - | a VFX preset played from it along each shot (16 blocks at most); left out, none | |
shot_sound | { sound: string, volume?: number, pitch?: number } | - | played where it hangs on each shot; left out, none | |
look | { item?: string, item_nbt?: string, halo?: string, scale?: number, recoil_ticks?: number, recoil_distance?: number, arrive_ticks?: number } | - | how the perch render kind draws it: item (an item id, minecraft:crossbow) with item_nbt (SNBT on the drawn stack, e.g. "{Charged:1b}"), laid along its aim at scale (1.1), full-bright; a halo ("#RRGGBB", #FFC24D) facing the camera behind it, brighter as it fires; kicked back recoil_distance blocks (0.25) for recoil_ticks (6) after a shot; swelling in over arrive_ticks (8) and shrinking away over the last tenth of its life |
thematic:strand#
A straight line strung between two world points (the strand verb lays them) that stays after the move ends, until its lifetime runs out, its owner strings one too many, it snaps, or its chunk unloads (it is never saved). A gentle strand is a rail any living body can land and walk on (one-way: from above only); a steep one is climbed like a ladder, holding forward to move along it (looking down goes down). A body that crosses it fast, or with the catching trait, is caught: on_catch and effects run on it, and it may snap. Its owner and anyone its owner may not hit pass freely. Every option is read live; size, spawn_group, track_range and update_rate are the shared entity fields.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
lifetime | number | 600 | ticks it lasts when the verb gives no lasts (20 is one second) | |
max_per_owner | number | 8 | strands of this id one owner may have; stringing one more removes the oldest | |
walk_slope | number | 1 | rise over run up to which it is walked on; steeper, it is climbed | |
footing_width | number | 0.3 | blocks wide its walkable top is | |
climb_speed | number | 0.15 | blocks a tick a climber holding forward moves along it | |
stats_from | string | - | an ability id whose tuned numbers on_catch reads; left out, the move that strung it | |
catches | { speed_above?: number, trait?: string, stop?: boolean, snaps?: boolean, cooldown?: number, sound?: string, effects?: string[] } | - | who it catches: a body crossing it faster than speed_above blocks a tick (level speed; 0.6), or any body with the wearer trait trait, whatever its speed. stop zeroes the caught body's velocity (true); snaps removes the strand after a catch (false); cooldown, ticks before it catches the same body again (20); sound plays at the catch; effects (ability effect ids) land on the body. Left out, it catches nobody | |
look | { style?: "rope" | "streak" | "glow" | "chain", preset?: "line" | "strand" | "snare_line" | "cocoon" | "cocoon_strap" | "ball", from?: "main_hand" | "off_hand" | "eyes" | "feet", ticks?: number, sag?: number, wobble?: number, alpha?: number, width?: number, palette?: "gold" | "silver", by_ability?: { [ability: string]: "gold" | "silver" }, target_height?: number, hand_lift?: number, color?: string, texture?: string } | { "style": "rope", "preset": "line", "sag": 0 } | how it is drawn, a tether look (style, preset, color, alpha, width, sag); only the line's own fields apply, from and the owner are ignored |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_catch | onCatch | - | It caught a body crossing it: the actions are aimed at that body. | owner: whoever strung it; source: the strand; hit: the body it caught; stats: the tuned numbers of the move that strung it (stats_from overrides), else the engine defaults |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
professions#
data/<namespace>/professions/, script global profession, default type thematic:profession (registers at startup).
Villager professions: data/<namespace>/professions/<id>.json. The file name is the profession's id, and an unemployed villager near the workstation block takes the job, restocking there like any villager. Its name is the lang key entity.minecraft.villager.<file name>. A new id or a changed workstation needs a restart; the look and trades reload.
thematic:profession#
A villager profession. It offers pick of its trades at Novice, chosen once, and never levels up.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
workstation | string | required | yes | the block id whose block is the job site, e.g. "thematic:cosmic_treadmill" |
work_sound | string | - | yes | the sound id played while it works at its job site |
render | { model: string, scale?: number } | required | the humanoid model the villager is drawn with (geo/entity/<model>.geo.json, textures/entity/<model>.png) instead of a villager's, at scale (1) | |
looks | { model: string, name?: string, chance: number }[] | - | other models a villager may wear instead, each picked for a share chance of villagers (0.05 is one in twenty, fixed per villager); name replaces the profession's name for that look | |
clips | { walk?: string, idle?: string } | { walk: "brute.walk", idle: "misc.idle" } | the shared humanoid clips it walks and stands with | |
merchant | { pick?: number, trades: { buy: Stack, buy_second?: Stack, sell: Stack, max_uses?: number, xp?: number, price_multiplier?: number, fallback?: object }[] } | required | its trades, as an entities file's merchant: pick of them (all of them), chosen when it takes the job | |
replaces | string | - | an entity id whose mobs become villagers with this job when they load, keeping their name: a mob a pack used to have for the job |
armors#
data/<namespace>/armors/, script global suit, default type thematic:suit (registers at startup).
Suits: data/<namespace>/armors/<collection>/<any folders>/<id>.json or .js. The first folder under armors/ is the suit's collection (data/<namespace>/collections/<collection>.json describes it). A suit's id is always thematic:<file name>, whatever namespace the file is in. A file with "parent", or one under a folder named alt/, is an alt (a skin variant) of its parent. Each id registers its own suit item at startup (a restart is needed for a new one); the kit reloads with /reload. When two packs define one suit id, the higher pack's file is the one /reload applies, whatever folder it sits in, unless the other sets a higher "priority".
thematic:suit#
A suit: one chestpiece item with a kit of abilities, stat bands and a look. Every field is optional. An alt ("parent") inherits every field it leaves out: abilities merge by identifier ("remove": true drops the parent's), stats replace per identifier, tags and attributes are added, and a field left at its default keeps the parent's value.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
wip | boolean | true | work in progress: a WIP tooltip, and the suit bench doesn't offer it; set false for a finished suit | |
tier | number | 1 | power tier, 1 to 10 | |
abilities | { identifier: string, keybind?: string, options?: object, assets?: object, remove?: boolean }[] | [] | the kit: each ability id with the key it is bound to (key.thematic.ability_0..5, ultimate, utility, passive, equip_item); remove (alts) drops the parent's entry with that identifier | |
stats | { identifier: string, minimum: number, maximum: number }[] | [] | stat bands a crafted suit rolls inside (thematic:base_generic_attack, base_generic_speed, base_defense, base_utility; each about 0 to 100) | |
fighting_type | string[] | [] | BRAWLER, DUELIST, UTILITY, MAGIC | |
tags | string[] | [] | suit tags (data/<namespace>/armor_tags) whose kit the suit takes, another suit's id (that suit's whole kit), or plain flags code asks about | |
flight_type | "ONE_HAND_LEFT" | "ONE_HAND_RIGHT" | "BOTH_HANDS" | "NO_HANDS" | "JETPACK" | "WINGED" | "NO_HANDS" | the pose while flying: shorthand for the shipped flight profile of that name | |
flight_profile | string | - | a flight profile (data/<namespace>/flight_profiles): this suit's own hover speed, lean and clips; wins over flight_type | |
jet_groups | "arms" | "legs" | "both" | "both" (all jets) | which limbs the flight jets may hang off; absent keeps every jet | |
suit-recipe | string | "thematic:invalid" (none) | the suit bench recipe that crafts it, thematic:<recipe file name> | |
attributes | { identifier: string, effect: number }[] | [] | size and body scales as multipliers (pehkui:base, pehkui:reach, ...) | |
guns | { id: string, Count?: number }[] | [] | guns the suit comes with | |
cape | { partCount?: number, height?: number, width?: number, thickness?: number, texture?: string, shinyTexture?: string, simulation?: object, remove?: boolean } | - | a cloth cape; texture defaults to <ns>:textures/cape/<suit>_cape.png (<ns>:textures/glider/<suit>_glider.png with simulation.type "glider"), after the suit's id; remove (alts) takes the parent's away | |
glider | { partCount?: number, height?: number, width?: number, thickness?: number, texture?: string, shinyTexture?: string, simulation?: object, remove?: boolean } | - | a glider, drawn like a cape; texture defaults as for cape | |
crafting | { force_rarity?: number, force_shiny?: boolean, chat_message?: string, craft_sound?: string, unique_ownership?: boolean } | - | what crafting it does beyond the recipe: a fixed rarity (0 starter .. 7 unique), a shiny roll, an announcement, a sound, one owner per server | |
sounds | { land_big?: string | string[], land_vehicle?: string | string[], hurt?: string | string[], death?: string | string[], splash?: string | string[], step?: { [blockTag: string]: string | string[] } } | - | what the wearer sounds like at the game's own moments, layered over vanilla's sound (sound ids; a list plays one entry per moment, in turn): land_big after a fall of more than seven blocks, land_vehicle instead when it lands on a boat, minecart or vehicle, hurt when damage lands, death, splash on entering water, and step per block tag ("minecraft:dirt"; the first tag the block is in wins; one entry per step, so write left and right feet interleaved). An alt, or a suit that names this suit as a tag, takes the whole block unless it has its own | |
boss | boolean | false | a boss's suit (internal) | |
creative | boolean | true | whether the suit is listed in the creative suits tab: false for a mob-only variant such as a boss's risen kit | |
model | string | - | a suit id whose geo, texture and clips this suit wears instead of its own ("thematic:myers"): a variant with a different kit and the same look. Not inherited by alts | |
mob_held | { mainhand?: string, offhand?: string } | - | the items a mob wearing this suit holds (item ids): a boss in the suit carries its weapon in its hand, with a zero drop chance. Not inherited by alts | |
mob_tempo | { gap?: number, evaluate?: number } | - | how fast a mob wearing this suit picks its moves, in ticks: gap, the least time between the start of one move and the next (40), and evaluate, how often it looks for a move to start (10). Not inherited by alts | |
mob_body | { attributes?: { [attribute: string]: number }, pushable?: boolean, unstoppable?: boolean, relentless?: boolean, closers?: string[], close_beyond?: number, immune_effects?: string[], prefer_vs_airborne?: string[] } | - | what a mob wearing this suit is built like: attributes, amounts added to its entity's own while the suit is worn ({ "minecraft:generic.knockback_resistance": 1 } for a mob nothing shoves), and pushable, false for one a body walking into it cannot push aside (true), unstoppable, true for one outside velocity (knockback, pushes, launches) never moves (false), and relentless, true for one that only walks straight at its target at walk pace, never strafing, backing off, fleeing or sprinting (false), and closers, ability ids it prefers (best first) while the target is farther than close_beyond blocks (3), so a relentless body keeps closing instead of waiting, prefer_vs_airborne, move ids preferred while the target is more than 2.5 blocks above it (ranged or gap moves), and immune_effects, status effect ids that other bodies can never put on it ("thematic:stun"); its own moves still can. Not inherited by alts | |
mob_dodge | { projectiles?: boolean, beams?: boolean, chance?: number, cooldown?: number, blink_every?: number } | - | how a mob wearing this suit slips what is about to hit it: projectiles on course (true) and beams or hitscan hits already on it (true) with a sidestep, each dodged at the odds chance (1), at most once per cooldown seconds (1.5); every blink_every-th dodge vanishes in smoke and reappears beside the attacker instead (0, never). Not inherited by alts | |
mob_stalk | { every?: [number, number], when_seen_for?: number, out_of_view?: boolean, after_attack?: boolean, distance?: [number, number], behind?: boolean, particle?: string } | - | how a stealthy mob keeps vanishing: every few seconds ([4, 7]), once it has been in its target's view for when_seen_for seconds (2.5, 0 never) or right after an attack lands (after_attack, true), it reappears at a standable spot out of the target's view (out_of_view, true), distance blocks from it ([7, 13]), behind it (behind, false: any angle), in a puff of particle (dark smoke). Shares the dodge's cooldown. Not inherited by alts | |
mob_antiair | { height?: number, after?: number, range?: number, cooldown?: number, pull?: number, damage_times?: number, bleed?: number, clip?: string } | - | how a mob wearing this suit throws down a target hovering above it: once the target has been more than height blocks above it (2.5) and within range blocks across (6) for after seconds (0.75), it reaches, yanks the target down with one downward speed of pull blocks per tick (1.8) and, on landing, slams it for damage_times its attack damage (1) plus bleed seconds of bleed (2), with a ground crack and heavy shake and hitstop for the victim; at most once per cooldown seconds (4); clip is the suit clip it plays reaching. Not inherited by alts | |
mob_watched | { cone?: number, range?: number, fill?: number, drain?: number, calm_drain?: number, calm_ability?: string, steps?: number, damage?: number, speed?: number, speed_cap?: number, pace?: number, finisher?: string, tell?: string, reset?: number, damage_steps?: number[], max_bleed?: { effect?: string, amplifier?: number, seconds?: number }, climb_sound?: string, warn_sound?: string } | - | a meter on a mob that fills (fill per second, 0.22) while its target keeps it within cone degrees (25) of the crosshair in sight and drains (drain 0.4) when they look away; while calm_ability is active it never fills and drains calm_drain (0.12). Each of steps (4) strengthens it by damage (0.12; ignored when damage_steps are given), speed (0.04, up to speed_cap 0.2) and pace (cooldowns shed, 0.1), with climb_sound, a low note and a tightening screen tint for the target. Full, it forces finisher and the meter drops to reset (0.35); tell is the move whose start warns the target to look away, with warn_sound from the mob. damage_steps are the factors on every hit it deals at step 1, 2, ... (the last repeats; none: 1), and max_bleed is an effect (thematic:bleed) at amplifier (1) for seconds (3) its hits add while the meter is at the top step. Not inherited by alts | |
mob_seek | { lost?: number, range?: number, cone?: number, stacks?: number, damage?: number, speed?: number, speed_cap?: number, pace?: number, strike?: string, ring?: string, ring_every?: number, steps?: string, steps_every?: number } | - | a timer that runs after each time a mob vanishes: if its target has not had it in view (cone degrees, within range) after lost seconds (4.5) it gains a stack (up to stacks, 4) of damage, speed and pace like mob_watched and strikes from behind with strike; finding it in time resets the timer and staggers it. ring and steps are sounds played from its position for the target while it hides. Not inherited by alts | |
mob_chain | { hops: string[], layers?: string[], finishers?: string[], min_hops?: number, max_hops?: number, every?: number, range?: number } | - | a mob that strings moves together: every seconds (10) with its target within range (40) it uses min_hops to max_hops (2 to 3) of the hops abilities in turn, a layers ability (a trap) between them, then the first usable finisher. Not inherited by alts | |
template | boolean | false | a template other suits inherit from (internal) | |
priority | number | 0 | when another pack also defines this suit id, the file with the higher priority is the one used, whatever order the packs load in (on a tie, the higher pack's); a pack that replaces a suit another mod ships sets 1 |
thematic:ladder#
A suit that grows: one item whose level picks a rung of its ladder, each rung with its own stats, the abilities it grants and the ones it lets the player choose between, and what the next upgrade costs. Takes every suit field as well; the rungs are laid over them.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
wip | boolean | true | work in progress: a WIP tooltip, and the suit bench doesn't offer it; set false for a finished suit | |
tier | number | 1 | power tier, 1 to 10 | |
abilities | { identifier: string, keybind?: string, options?: object, assets?: object, remove?: boolean }[] | [] | the kit: each ability id with the key it is bound to (key.thematic.ability_0..5, ultimate, utility, passive, equip_item); remove (alts) drops the parent's entry with that identifier | |
stats | { identifier: string, minimum: number, maximum: number }[] | [] | stat bands a crafted suit rolls inside (thematic:base_generic_attack, base_generic_speed, base_defense, base_utility; each about 0 to 100) | |
fighting_type | string[] | [] | BRAWLER, DUELIST, UTILITY, MAGIC | |
tags | string[] | [] | suit tags (data/<namespace>/armor_tags) whose kit the suit takes, another suit's id (that suit's whole kit), or plain flags code asks about | |
flight_type | "ONE_HAND_LEFT" | "ONE_HAND_RIGHT" | "BOTH_HANDS" | "NO_HANDS" | "JETPACK" | "WINGED" | "NO_HANDS" | the pose while flying: shorthand for the shipped flight profile of that name | |
flight_profile | string | - | a flight profile (data/<namespace>/flight_profiles): this suit's own hover speed, lean and clips; wins over flight_type | |
jet_groups | "arms" | "legs" | "both" | "both" (all jets) | which limbs the flight jets may hang off; absent keeps every jet | |
suit-recipe | string | "thematic:invalid" (none) | the suit bench recipe that crafts it, thematic:<recipe file name> | |
attributes | { identifier: string, effect: number }[] | [] | size and body scales as multipliers (pehkui:base, pehkui:reach, ...) | |
guns | { id: string, Count?: number }[] | [] | guns the suit comes with | |
cape | { partCount?: number, height?: number, width?: number, thickness?: number, texture?: string, shinyTexture?: string, simulation?: object, remove?: boolean } | - | a cloth cape; texture defaults to <ns>:textures/cape/<suit>_cape.png (<ns>:textures/glider/<suit>_glider.png with simulation.type "glider"), after the suit's id; remove (alts) takes the parent's away | |
glider | { partCount?: number, height?: number, width?: number, thickness?: number, texture?: string, shinyTexture?: string, simulation?: object, remove?: boolean } | - | a glider, drawn like a cape; texture defaults as for cape | |
crafting | { force_rarity?: number, force_shiny?: boolean, chat_message?: string, craft_sound?: string, unique_ownership?: boolean } | - | what crafting it does beyond the recipe: a fixed rarity (0 starter .. 7 unique), a shiny roll, an announcement, a sound, one owner per server | |
sounds | { land_big?: string | string[], land_vehicle?: string | string[], hurt?: string | string[], death?: string | string[], splash?: string | string[], step?: { [blockTag: string]: string | string[] } } | - | what the wearer sounds like at the game's own moments, layered over vanilla's sound (sound ids; a list plays one entry per moment, in turn): land_big after a fall of more than seven blocks, land_vehicle instead when it lands on a boat, minecart or vehicle, hurt when damage lands, death, splash on entering water, and step per block tag ("minecraft:dirt"; the first tag the block is in wins; one entry per step, so write left and right feet interleaved). An alt, or a suit that names this suit as a tag, takes the whole block unless it has its own | |
boss | boolean | false | a boss's suit (internal) | |
creative | boolean | true | whether the suit is listed in the creative suits tab: false for a mob-only variant such as a boss's risen kit | |
model | string | - | a suit id whose geo, texture and clips this suit wears instead of its own ("thematic:myers"): a variant with a different kit and the same look. Not inherited by alts | |
mob_held | { mainhand?: string, offhand?: string } | - | the items a mob wearing this suit holds (item ids): a boss in the suit carries its weapon in its hand, with a zero drop chance. Not inherited by alts | |
mob_tempo | { gap?: number, evaluate?: number } | - | how fast a mob wearing this suit picks its moves, in ticks: gap, the least time between the start of one move and the next (40), and evaluate, how often it looks for a move to start (10). Not inherited by alts | |
mob_body | { attributes?: { [attribute: string]: number }, pushable?: boolean, unstoppable?: boolean, relentless?: boolean, closers?: string[], close_beyond?: number, immune_effects?: string[], prefer_vs_airborne?: string[] } | - | what a mob wearing this suit is built like: attributes, amounts added to its entity's own while the suit is worn ({ "minecraft:generic.knockback_resistance": 1 } for a mob nothing shoves), and pushable, false for one a body walking into it cannot push aside (true), unstoppable, true for one outside velocity (knockback, pushes, launches) never moves (false), and relentless, true for one that only walks straight at its target at walk pace, never strafing, backing off, fleeing or sprinting (false), and closers, ability ids it prefers (best first) while the target is farther than close_beyond blocks (3), so a relentless body keeps closing instead of waiting, prefer_vs_airborne, move ids preferred while the target is more than 2.5 blocks above it (ranged or gap moves), and immune_effects, status effect ids that other bodies can never put on it ("thematic:stun"); its own moves still can. Not inherited by alts | |
mob_dodge | { projectiles?: boolean, beams?: boolean, chance?: number, cooldown?: number, blink_every?: number } | - | how a mob wearing this suit slips what is about to hit it: projectiles on course (true) and beams or hitscan hits already on it (true) with a sidestep, each dodged at the odds chance (1), at most once per cooldown seconds (1.5); every blink_every-th dodge vanishes in smoke and reappears beside the attacker instead (0, never). Not inherited by alts | |
mob_stalk | { every?: [number, number], when_seen_for?: number, out_of_view?: boolean, after_attack?: boolean, distance?: [number, number], behind?: boolean, particle?: string } | - | how a stealthy mob keeps vanishing: every few seconds ([4, 7]), once it has been in its target's view for when_seen_for seconds (2.5, 0 never) or right after an attack lands (after_attack, true), it reappears at a standable spot out of the target's view (out_of_view, true), distance blocks from it ([7, 13]), behind it (behind, false: any angle), in a puff of particle (dark smoke). Shares the dodge's cooldown. Not inherited by alts | |
mob_antiair | { height?: number, after?: number, range?: number, cooldown?: number, pull?: number, damage_times?: number, bleed?: number, clip?: string } | - | how a mob wearing this suit throws down a target hovering above it: once the target has been more than height blocks above it (2.5) and within range blocks across (6) for after seconds (0.75), it reaches, yanks the target down with one downward speed of pull blocks per tick (1.8) and, on landing, slams it for damage_times its attack damage (1) plus bleed seconds of bleed (2), with a ground crack and heavy shake and hitstop for the victim; at most once per cooldown seconds (4); clip is the suit clip it plays reaching. Not inherited by alts | |
mob_watched | { cone?: number, range?: number, fill?: number, drain?: number, calm_drain?: number, calm_ability?: string, steps?: number, damage?: number, speed?: number, speed_cap?: number, pace?: number, finisher?: string, tell?: string, reset?: number, damage_steps?: number[], max_bleed?: { effect?: string, amplifier?: number, seconds?: number }, climb_sound?: string, warn_sound?: string } | - | a meter on a mob that fills (fill per second, 0.22) while its target keeps it within cone degrees (25) of the crosshair in sight and drains (drain 0.4) when they look away; while calm_ability is active it never fills and drains calm_drain (0.12). Each of steps (4) strengthens it by damage (0.12; ignored when damage_steps are given), speed (0.04, up to speed_cap 0.2) and pace (cooldowns shed, 0.1), with climb_sound, a low note and a tightening screen tint for the target. Full, it forces finisher and the meter drops to reset (0.35); tell is the move whose start warns the target to look away, with warn_sound from the mob. damage_steps are the factors on every hit it deals at step 1, 2, ... (the last repeats; none: 1), and max_bleed is an effect (thematic:bleed) at amplifier (1) for seconds (3) its hits add while the meter is at the top step. Not inherited by alts | |
mob_seek | { lost?: number, range?: number, cone?: number, stacks?: number, damage?: number, speed?: number, speed_cap?: number, pace?: number, strike?: string, ring?: string, ring_every?: number, steps?: string, steps_every?: number } | - | a timer that runs after each time a mob vanishes: if its target has not had it in view (cone degrees, within range) after lost seconds (4.5) it gains a stack (up to stacks, 4) of damage, speed and pace like mob_watched and strikes from behind with strike; finding it in time resets the timer and staggers it. ring and steps are sounds played from its position for the target while it hides. Not inherited by alts | |
mob_chain | { hops: string[], layers?: string[], finishers?: string[], min_hops?: number, max_hops?: number, every?: number, range?: number } | - | a mob that strings moves together: every seconds (10) with its target within range (40) it uses min_hops to max_hops (2 to 3) of the hops abilities in turn, a layers ability (a trap) between them, then the first usable finisher. Not inherited by alts | |
template | boolean | false | a template other suits inherit from (internal) | |
priority | number | 0 | when another pack also defines this suit id, the file with the higher priority is the one used, whatever order the packs load in (on a tie, the higher pack's); a pack that replaces a suit another mod ships sets 1 | |
levels | { level: number, stats?: { preset?: "ramp", favoured?: string | string[], pace?: "normal" | "swift" | "heavy" }, grants?: string[], choices?: string[], cost?: { id: string, Count?: number }[], trial?: string }[] | - | the rungs, each level 1 to 10 once (read once at startup; /reload does not re-read them): the stats the level gives (preset ramp, the only one; favoured names one stat, attack, regen, utility or defense; pace normal, swift or heavy, default normal), the abilities it grants and the abilities the player picks exactly one of (both by identifier, each one an entry of this suit's own abilities, which lists every ability the ladder can ever grant), what the upgrade into it costs at the bench (none for level 1; an unknown item is logged and skipped) and the trial that unlocks it instead of the cost | |
equips | object[] | - | not read: an item the suit hands out is an ordinary abilities entry on the equip move | |
legacy_ids | string[] | - | yes | old per-level item ids (<id>t<level>, the rung's model id) that still load: an old stack turns into this suit at that level, with every rung up to it granted |
roster | string | - | not read: the bound-item roster is the thematic:toolkit ability's own roster list |
ability_effects#
data/<namespace>/ability_effects/, script global abilityEffect, default type thematic:action_list.
Ability effects: data/<namespace>/ability_effects/<any folders>/<id>.json or .js. What a beam, a bolt or a spray carries (an ability's "effects": ["thematic:laser", {"id": "thematic:blindness", "duration": 3.5}]) and does to what it hits. Read before abilities are, and again on /reload.
thematic:action_list#
An effect made of actions: the ability's own hit (damage), then whatever its hooks do. A value written {"$option": "name"} anywhere in a hook is that option's value for the firing; {"$option": "flag", "then": x, "else": y} picks by a true/false option, and without "else" a false flag leaves the field (or list entry) out.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
damage | "ability" | "none" | "ability" | ability: every entity struck takes the ability's hit, the damage it was fired with raised to min_damage, as the wearer's player or mob attack (a player must be allowed to hit the target); none: no hit of its own | |
min_damage | number | 7 | the least an ability hit lands for (7; 0 for none) | |
options | { [name: string]: { default: number | boolean; doc?: string } } | - | what an effects list may write beside the id, each with its default; a boolean default makes a true/false option. Numbers are written as they read (seconds as seconds) | |
doc | string | - | what it does, for the docs and the effects-list autocompletion |
| Hook | Script method | Options | When | Context |
|---|---|---|---|---|
on_entity_hit | onEntityHit | stage contact: the touch every carrier makes, missiles and constructs included; damage: the call that lands the hit, which beams, bolts, sprays and hitscan make (the cold gun and ice walls make only this one). Runs before the ability hit (contact) | It struck a living body. | owner: who fired it; source: the projectile, or the owner for a hitscan beam and for the contact stage; hit: the body struck; stats: damage is what the ability fired it to deal (0 at the contact stage) |
on_block_hit | onBlockHit | - | It met a block. | owner: who fired it (the projectile's owner); source: the projectile, or the owner for a hitscan beam; hit: the block struck |
on_pos | onPos | - | Where a body was struck, before anything else on that hit. | no owner and no source: only the world and the point, the corner of the block the body struck stands in |
Every hook also takes if (a guard), every (ticks) and cooldown (seconds).
Traits: none read
effect_visuals#
data/<namespace>/effect_visuals/, script global effectVisual, default type thematic:effect_visual.
How a status effect shows on a suit: data/<namespace>/effect_visuals/<any folders>/<effect>.json or .js. The file name is the status effect's id (effect_visuals/frozen.json is thematic:frozen), or its effect field names one. Synced to clients and reloaded with /reload; an effect with no file shows nothing on the suit.
thematic:effect_visual#
What a body wearing a suit looks like while it has the effect. Every field is optional; a file with none draws nothing.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
effect | string | the file's id | the status effect it is for, when the file cannot be named after it (an effect of another namespace, e.g. "minecraft:invisibility") | |
suit_visual | { id: "thematic:glow", options?: GlowOptions } | - | a suit visual drawn over the suit while the effect lasts: thematic:glow with its options (bones, model, texture, tint, scroll, scale, shell) and ramp, which follows the effect's remaining ticks; a suit move lending the overlay named after the effect (its path) its model is honoured | |
suit_render | { render_type: "translucent" | "lightning" | "energy_swirl", flicker?: number } | Array<{ render_type: string, flicker?: number }> | - | the layer the suit itself is drawn in while the effect lasts, instead of its own: each entry in order, taken on a frame with chance flicker (1, every frame); the first effect file whose entry is taken wins | |
opacity | { amplifier?: [number, number], hidden: [number, number], hidden_soft?: [number, number] } | - | how see-through the suit is while the effect lasts: 1 minus hidden eased over the amplifier range (amplifier [1, 10]); hidden_soft instead for a wearer with the soft_invisibility trait. A wearer with still_invisible standing still, or fully_invisible, is hidden outright | |
first_person | { model: string, bone?: string, texture: string, scale?: number, offset?: [number, number, number] } | - | drawn over the screen for the local player in first person while the effect lasts: the model's bone (armorBody) in the beacon-beam texture, scaled (1) and moved by offset ([0, 0, 0]) in screen space | |
marker | { frame?: "diamond" | "circle" | "none", glyph?: "chevron" | "triangle" | "dot" | "none", color?: string | number, core?: string | number, size?: number, height?: number, bob?: number, spin?: number, through_walls?: boolean } | - | an emblem facing the camera over the head of every living body with the effect, suit or not, drawn for everyone near (effects are synced to every watcher): a thin frame (diamond) round a glyph (chevron, pointing down at the body) in color ("#FF3A1A") with a core line ("#FFFFFF") through it and a dark edge so it reads on sky and ground alike; size blocks across (0.45, growing a little with distance), height blocks over the head (0.45), bobbing bob blocks (0.06), its frame turning spin degrees a second (0); it fades over the effect's last half second. through_walls draws it over whatever is in front (false) |
anim_controllers#
data/<namespace>/anim_controllers/, script global animController, default type thematic:suit_controllers.
The GeckoLib controllers every suit carries: data/<namespace>/anim_controllers/<any folders>/<id>.json or .js. The engine ships thematic:armor (anim_controllers/armor.js); a pack changes it by shipping the same path, or adds to it with a file of its own id. Every definition is read together, thematic:armor first and the rest in id order: a later one's idle wins, its states are tried before the earlier ones', its while_active controllers and trigger_clips_from are added, and its effect_clips replace the same effect's. What plays reloads with /reload; which controllers a suit has is fixed when the suit is first drawn. Synced to clients.
thematic:suit_controllers#
What a suit's clip controller (ArmorAnimations: the one ability clips are triggered on) plays when nothing is triggered, the extra controllers that hold a clip while something is true, and the player-animator clips status effects put on their target. A condition (when) holds when every key it names holds: riding: the wearer rides an entity of this type, or of this #tag; vehicle_moving: the ride is moving (a Thematic vehicle by its own measure, anything else by the ground vehicles' one: across faster than about 0.6 blocks a second); flag: the wearer's stored ability flag of this key is on; trait: the wearer has this trait; has_ability: the wearer's suit has this ability in its kit; active: the wearer has this ability running; holding: the main hand holds this item, or an item of this #tag; sneaking: the wearer is (or is not) sneaking; looking_at: the first living thing the wearer's look meets within range blocks (32), with no block in between, is there (of this entity type or #tag, if entity names one). Every key is answered on each client from what it sees of the wearer, so every viewer sees the same clip. Nothing but a player wearing the suit (or a mirage of one) matches anything.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
idle | string | "misc.idle" | the looping clip the clip controller plays when no state matches | |
states | { clip: string, play?: "loop" | "once" | "hold", when: { riding?: string, vehicle_moving?: boolean, flag?: string, trait?: string, has_ability?: string, active?: string, holding?: string, sneaking?: boolean, looking_at?: boolean | { range?: number, entity?: string } } }[] | - | clips the clip controller plays in place of idle: the first whose when holds wins (play: loop, the default; once; hold, which stays on its last frame) | |
while_active | { controller: string, clip: string, play?: "loop" | "once" | "hold", when: { riding?: string, vehicle_moving?: boolean, flag?: string, trait?: string, has_ability?: string, active?: string, holding?: string, sneaking?: boolean, looking_at?: boolean | { range?: number, entity?: string } }, transition?: number }[] | - | yes | a controller of its own per entry, named controller, playing the clip while when holds and idle otherwise; it sits after the staff-block controller, so it paints over the flight and parry poses. transition: blend ticks (0) |
walk | { clip: string, play?: "loop" | "once" | "hold", when?: { riding?: string, vehicle_moving?: boolean, flag?: string, trait?: string, has_ability?: string, active?: string, holding?: string, sneaking?: boolean, looking_at?: boolean | { range?: number, entity?: string } }, stride: number, view_bob?: boolean, blend?: number }[] | - | clips the walk controller plays while the wearer walks on the ground (not sprinting, flying, swimming or riding): the first whose when holds wins, a later definition's tried first. The clip plays at the rate that matches the wearer's ground speed: stride is how many blocks one play of the clip carries them, so feet keep pace with the ground. It sits after the clip controller and before flight, and stands aside for ability clips and swings, and in the wearer's own first-person view. blend: ticks to ease in, out and across between walk clips at the same stride phase (4); view_bob: false stops the wearer's camera bobbing | |
trigger_clips_from | string[] | - | yes | every clip in a GeckoLib animation file whose path holds one of these ("armor": animations/armor/...) can be triggered on the clip controller by its name, played as its file says (once, loop or hold) |
effect_clips | { [statusEffect: string]: string } | - | the player-animator clip (an animation id) a status effect plays on the player it is on, by the effect's id |
encounters#
data/<namespace>/encounters/, script global encounter, default type thematic:encounter.
Ready-made missions: data/<namespace>/encounters/<any folders>/<id>.json or .js. The file name is the template's name (/thematic dev encounter template <name>, /thematic dev encounter import <name>, an NPC start). The fields are the wave spawner's own encounter NBT, key for key, so a mission authored in game and exported with /thematic dev encounter export is already a valid file. Read by the server and reloaded with /reload; a file in config/thematic/encounters/ with the same name wins.
thematic:encounter#
One mission: its phases, spawn geometry, boss, rewards and cooldown.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
Version | number | 2 | the NBT shape's version; older files are migrated as they load | |
Id | string | - | the mission's id: what cooldowns and first-clear records are kept under | |
Display | string | - | the name players see | |
Area | string | "" | an opaque area label other mods may read | |
Boss | object | - | the boss: { Entity, Suit, SpawnPoint {X,Y,Z}, BarColor, DarkenSky } | |
SpawnPoints | object[] | [] | named spawn positions: [{ Name, Pos {X,Y,Z} }], or [{ Name, Block, Radius }]: on top of every block of that id within Radius blocks of the anchor (24), nearest first, so a mission held in a placed structure spawns from its own blocks however the structure was turned | |
Objectives | object[] | [] | authored objectives: [{ Id, Pos {X,Y,Z}, Kind, Label }] | |
Phases | object[] | [] | the phases, in order: [{ Type, Name, Announce, Entries, Transition, ... }]; a phase's Suit (a boss suit id) re-equips the boss already on the field when it begins, and its Transition may add { OutClip, InClip, HoldTicks } to hold the boss while the suit swaps (clips alone hold it without a new suit). A phase may also carry Sound (the cue as it begins: a sound event id, or "none"; left out, the engine's own), BossHealTo (a fraction: the boss is healed up to it as the phase begins), BossMinHealth (a fraction: damage cannot take the boss below it while the phase runs, so a BOSS_HP_BELOW gate at that fraction always trips), OnStart (action list, as the phase begins) and OnTransition { Start, Midpoint, End } (action lists at the beats of its held swap). An action list is a JSON array of the same { "type": ... } actions an ability or block runs, run once per participant with the boss as the wearer and that participant as the target ("to": "target" for a screen effect); with no boss on the field the participant is both. An entry with "after": <seconds> runs that long after its beat starts instead of at once, so a beat can be built up in stages. A phase may carry Group (an id: the consecutive phases of one group are a block the mission's Shuffle moves as a whole), Assemble { Seconds, Up, Visual } (when the phase puts the boss on the field it is set Up blocks over the anchor, held still and unhurtable for Seconds, and its client plays the entity visual Visual, "materialize" by default, for that long; in a held swap that is the last Seconds of the hold, the body set down at the anchor at their start, and OnTransition.Midpoint and End are its start and end), Entrance { Mode "from_darkness", Distance, StopAt, Quiet, Walk, Jumpscare, Close, Hold (seconds, blocks), OnVanish, OnEmerge, OnJumpscare, OnEnd (action lists) } (once the boss is out it vanishes to a ring Distance blocks from the participant, stays unseen for Quiet, walks in to StopAt over Walk, then with Jumpscare closes to Close blocks in front of their face at once and is held Hold before the fight begins), Music { sound, loop_every, volume } (a sound id replayed every loop_every seconds, privately for each participant, one instance at a time; it keeps playing into the next phase carrying the same Music and stops when a phase without it begins or the fight ends), DismissBoss (the boss on the field is taken off it as the phase's hold ends) and Dialogue { PHASE_START, BOSS_HP, OBJECTIVE_DONE, ESCALATION, PHASE_END, FIGHT_START: [{ Speaker, Text, Delay, Style, Sound, Duration }] }; a line with a Sound and no Text is a voice line, and in a private run each participant hears theirs one at a time, a line waiting for the one before it to run its Duration seconds (3 when left out) and dropped if it waits longer than 6 seconds | |
CompletionLootTable | string | - | the loot table paid out for every completion | |
FirstClearLootTable | string | - | the loot table each player gets on their first completion | |
Return | object | - | where a finished party is sent: { World, Pos {X,Y,Z}, Yaw, Message }; World "" sends everyone back where they came from; Message is the translation key they are told (left out, the default exit message) | |
Limits | object | - | { MaxConcurrentMobs, MaxPartySize, MinPlayers, MaxSessionMinutes } | |
Arena | object | - | { Memory }: the arena theme (arena_themes/) shown round the fight, to the participants only | |
Anchor | object | - | { World, Pos {X,Y,Z} }: where a mission with no block is pinned | |
Briefing | object[] | [] | what the mission-giver says before you accept: [{ Speaker, Text, Delay, Style, Sound }] | |
Cooldown | object | { "Seconds": 7200, "PerPlayer": true } | { Seconds, PerPlayer } | |
Private | boolean | false | the run is one player's alone: the party is exactly the player who starts it, and the boss and everything it spawns are seen and hit only by them, as are the bar, dialogue, announcements and phase sounds; the boss shows no bar of its own, the phase bar is the one bar; the engine's own chat lines (cooldown, backup, first clear, exit, completion) are left out, and the participants' HUD shows no ability readouts (stack-effect counters such as Terror) while it runs | |
Leash | number | 0 | blocks from the anchor a participant may stray before LeashMode applies (by default the run fails once they have been out for three seconds, warned at the edge); 0 is no leash | |
LeashMode | "fail" | "pull" | "fail" | what straying past the Leash does: "fail" ends the run after three seconds out, "pull" pulls the participant back toward the anchor in short impulses (a soft rumble and thicker fog while they are out, no warning text), never failing for distance; one who gets 12 blocks past the Leash (a teleport out) is put back at the edge. Needs a Leash | |
AutoStart | object | - | { Range }: a block-held mission starts by itself, after the usual countdown, once a survival player who may run it (off its cooldown) comes within Range blocks of the block; left out, it waits to be used | |
FailOnDeath | boolean | false | a participant dying ends the run as FAILED | |
QuietComplete | boolean | false | a win skips the default "Mission complete." line, its sound and the bar's text, for a mission whose OnComplete tells it; the boss shows no bar of its own either, and the engine's own chat lines (cooldown, backup, first clear, exit) are left out, and the participants' HUD shows no ability readouts (stack-effect counters such as Terror) while it runs | |
Shuffle | string[] | [] | phase group ids whose blocks (the consecutive phases carrying that Group) swap places with one another, as wholes, in a random order drawn when each run starts and kept for that run; every other phase stays where it is written | |
ParticipantEffects | object[] | [] | status effects every participant carries for the whole run: [{ id, amplifier (0 is level I, as the effect command takes it), icon (list it on their HUD; default true) }]; put on as it starts, topped up while it lasts and taken off when it ends however it ends | |
DifficultyDamage | object | {} | damage factor per world difficulty, { easy, normal, hard } (Peaceful reads as easy; a missing key is 1), multiplied onto each phase's DamageMultiplier for every mob of the run while it fights, so changing the difficulty mid-run takes effect within a second | |
OnComplete | object[] | [] | an action list run for the party as the run is won, before they are sent out; see Phases for how an action list runs | |
OnFail | object[] | [] | an action list run for the party as the run ends in anything but a win (failed, timed out, abandoned, stopped), while the boss is still there; see Phases |
arena_themes#
data/<namespace>/arena_themes/, script global arenaTheme, default type thematic:arena_theme.
Remembered places shown round a mission: data/<namespace>/arena_themes/<any folders>/<id>.json or .js. An encounter names one in Arena.Memory (a bare name means thematic:). The place is vanilla structure templates, dissolved at their edges and set in a ring beyond the fight, shown only to the participants. Read by the server and reloaded with /reload.
thematic:arena_theme#
One arena theme: its light and the vanilla structure pieces around it.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
light | string | required | the light dropped beside the pieces, standing on the ground, e.g. "minecraft:soul_lantern" | |
piece_y_offset | number | 0 | a vertical nudge for the pieces, for templates that carry their own ground layer | |
centrepieces | string[] | required | vanilla structure template paths, without the minecraft: namespace ("ancient_city/structures/barracks"), one of which stands at the head of the room | |
props | string[] | [] | vanilla structure template paths, without the namespace, scattered round the rest of the edge |
pocket_dimensions#
data/<namespace>/pocket_dimensions/, script global pocketDimension, default type thematic:pocket_dimension.
Pocket dimensions a wearer is sent into for a while and then brought back from: data/<namespace>/pocket_dimensions/<any folders>/<id>.json or .js. The file name is the pocket's id, which the Java that sends someone in names. The dimension itself stays vanilla data (dimension/<id>.json and its dimension_type, whose coordinate_scale scales the walk back out). Read by the server and reloaded with /reload.
thematic:pocket_dimension#
One pocket: where the wearer lands, how long they stay, the corridor built around the landing spot on every entry and the resident waiting down it.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
dimension | string | required | the world the pocket is, e.g. "thematic:speed_force" | |
spawn | [number, number, number] | [0, 64, 0] | where the wearer lands, [x, y, z] | |
stay | { min?: number, max?: number } | { min: 800, max: 1000 } | how long a trip lasts before the wearer is brought back, in ticks: a whole number from min to max (both included), rolled on entry | |
corridor | { length?: number, radius?: number, floor: string, wall: string } | - | a straight corridor along Z through the landing spot, rebuilt on every entry: floor blocks under it, wall blocks for its sides (|x| == radius) and ceiling (y == radius), air inside; it runs from -length to length - 1. length defaults to 512, radius to 6. Leave it out to build nothing | |
resident | { entity: string, name?: string, distance?: number, delay?: number, floor: string, marker: string } | - | someone waiting on a 5 by 3 platform distance blocks down the corridor (+Z; default 32): made fresh delay ticks after each entry (default 30), after anything else living near the platform is removed; invulnerable, AI off, facing the wearer, with name (literal text) shown over its head. floor is the platform's block, marker the block it stands on | |
cells | { shells: string[], membranes?: string[], gap?: number, giant?: { min?: number, max?: number }, core: string, nucleon?: string, electron?: string, orbitals?: { min?: number, max?: number }, seed?: number, size?: number, radius?: number, bubble?: { min?: number, max?: number }, thickness?: number, lumps?: { min?: number, max?: number }, windows?: { min?: number, max?: number }, stones?: { min?: number, max?: number } } | - | a standing world of hollow glass atoms on a grid, built when someone first comes near and never rebuilt. shells are the blocks of an atom's inner layer (one per atom, chosen by grid position); membranes are paler layers outside it, outermost first, each thickness thick with gap (2) blocks of air between. core is the 3x3x3 block at the centre, and the landing spot is two blocks above the home atom's core. nucleon and electron blocks are optional (left out, they build nothing). giant wraps each atom in a larger sphere of the same membranes (radius 30 to 32 is 64 across); cells are then spaced so giants never touch, and lumps are best left at 0. orbitals (2 to 3) sets the pairs of hollow lobes around the nucleus. size (96) is the grid spacing, radius (8) how many cells are built out from the home one, bubble (10 to 22) the main sphere's radius (at least 5 more than the layers), thickness (2) its wall, lumps (2 to 5) the smaller overlapping spheres, windows (1 to 3) the round holes in the wall, stones (2 to 5) the floating spheres. The same seed builds the same world. Entering a pocket with cells removes nobody and returns the wearer to exactly where they left | |
gravity | number | 1 | the pocket's pull as a fraction of the overworld's: 1 is normal, 0.2 floats, 0 is none. The wearer's client applies it, and fall damage is off below 1 | |
look | { shader?: string, pulse?: { period?: number, strength?: number }, motes?: { particle: string, per_second?: number, radius?: number, drift?: number }[], fog?: { colors?: string[], amount?: number, start?: number, scale?: number }, near?: { range?: number, boost?: number } } | - | what the pocket looks like from inside, drawn by the wearer's client only while they are in it. shader is a post pass (shaders/post/<name>.json; a bare name is Thematic's, e.g. "quantum_glow"). pulse swells the pass like a heartbeat every period seconds (1.6) by up to strength (0.4). motes are drifting specks: per_second (8) of a particle id with no options ("minecraft:end_rod") within radius blocks (12), drifting about drift blocks a tick (0.015); the particle setting thins them. fog pulls the world's fog colour amount (0.1) of the way toward a colour that drifts through colors (hex, e.g. ["#0b3f1f", "#0b2a52"]) over patches about scale (160) blocks across, and starts start (0.2) of the way out. near boosts the pass within range (48) blocks of a core, by up to boost (0.35) at the core; a negative boost dims it |
multiblocks#
data/<namespace>/multiblocks/, script global multiblock, default type thematic:multiblock.
Structures built from blocks the player places in a layout: data/<namespace>/multiblocks/<any folders>/<id>.json or .js. Using a placed part runs the thematic:assemble action, which swaps the layout for another set of blocks (a model block and its fillers); breaking any of them runs thematic:disassemble, which swaps the parts back. Read by the server and reloaded with /reload.
thematic:multiblock#
One structure: the layout the player places, the layout it becomes, and the block each character in them stands for.
| Field | Type | Default | Identity | Meaning |
|---|---|---|---|---|
key | { [character: string]: string } | required | the block id each one-character name in the layouts stands for, e.g. { "F": "mypack:frame" }; '.' and '_' are taken (see parts) | |
parts | string[][] | required | what the player places: layers (bottom first) of rows (front first) of text, one character per block, left to right. A key character is that block, '.' must be empty and '_' is not checked. It is matched facing any of the four ways, so the front is where the player stands to use it | |
assembled | string[][] | required | what the parts become, the same size as parts: a key character is placed (a block with a horizontal facing is turned to face the front), '.' and '_' leave the cell alone | |
particle | string | - | a particle sprayed over the structure as it assembles, e.g. "minecraft:end_rod" | |
count | number | 40 | how many of them |