Scriptable Layers (Metroid Prime 2)

This article is for the scriptable layers format from Metroid Prime 2, 3, and Donkey Kong Country Returns. See Scriptable Layers (File Format) for other revisions of this format.

Scriptable layers are a data section found in the MREA format, denoted by the fourCC identifier SCLY. It contains script object instances which are used to set the object layout of each room. Rooms can contain multiple layers, with each being able to be toggled on and off independently, allowing for the layout of a room to be updated after significant ingame events, which is done using a ScriptLayerController object. Each instance has a large number of parameters that can be toggled to customize the appearance and behavior of that instance, and they're capable of sending messages to other objects, allowing for fairly complex interactions between objects to be scripted.

In Echoes, the SCLY format was overhauled. The most notable change is that all properties now have a 32-bit ID and a size value listed, allowing the game to match properties in the file with data members by ID rather than by their position in the file; this was presumably done to avoid breaking cooked data when objects were modified during development, since this change meant the file could still be read correctly if properties were added or removed from an object and the script data hadn't been recooked. Another change is that there's now a separate layer for generated objects (ie objects that are spawned using a Generator or a PickupGenerator), which uses the fourCC SCGN. Aside from minor changes in the header, the SCGN layer is identical to SCLY layers.

In Donkey Kong Country Returns, the format is identical, but the way the data is cooked was slightly modified. In every game starting with Prime 2, the engine assigns an arbitrary default value to every object property before reading in the values from the file. In the Prime series, this didn't have much of an effect, since (almost) every property for every object is written to the file anyway. But starting in Donkey Kong Country Returns, any properties whose value matches the internal default value are left out of the file in order to speed up loading times. This means a full list of properties and their internal default value is required to correctly read/write DKCR files. (This change could also be applied in the Prime series with custom script data.)

Although this format is primarily found in MREA files, it's also occasionally reused in other formats, such as SCAN.

Format

Offset Type Count Name Notes
0x0 char 4 Magic Always SCLY or SCGN
0x4 char 1 Unknown
0x5 u32 1 Unknown Appears to be layer self-index. Not present in SCGN.
0x9 char 1 Version Always 1
0xA u32 1 Instance Count Count of instances in this layer.
0xE Script Instance Instance Count Script Instances Layer instance data.
End of layer

Script Instance

Offset Type Count Name Notes
0x0 char 4 Instance Type FourCC representing the type of object this is.
0x4 u16 1 Instance Size Size of this instance, relative to after the size value.
0x6 u32 1 Instance ID ID used by other objects to reference this instance. The bottom 16 bits is an area-relative instance ID. The next 10 bits up are the world-relative area index. The top 6 bits are the layer index. The layer index isn't technically part of the ID, as the game removes it for ID-based lookups.
0xA u16 1 Connection Count Count of outgoing script connections.
0xC Connection Connection Count Connection Array Array of outgoing script connections.
Property Struct 1 Base Struct This is the instance's base struct, which contains all properties in this instance. The property ID is always 0xFFFFFFFF.
End of instance

Connection

A connection is used to script interactions between objects; when this instance enters the given state, it sends the target instance the given message.

Offset Type Count Name Notes
0x0 char 4 State When the instance enters this state, the connection will activate.
0x4 char 4 Message Message that will be sent to the target instance when the connection activates.
0x8 u32 1 Target Instance ID ID of the target instance.
0xC End of connection

Property Struct

A property struct is a property that contains other properties. These are often modular pieces that are present on multiple objects (for example, the PatternedAI struct that appears on all enemies). Structs can contain other structs as sub-properties.

Offset Type Count Name Notes
0x0 u32 1 Property ID Property ID for this struct property.
0x4 u16 1 Property Size Size of this struct including all sub-properties.
0x6 u16 1 Sub-Property Count Count of sub-properties contained in this struct.
0x8 Property Sub-Property Count Sub-Properties Array of this struct's sub-properties.
End of struct

Property

A property represents a single data value on a script instance. The type of each property varies depending on the ID.

Offset Type Count Name Notes
0x0 u32 1 Property ID ID that uniquely identifies this property.
0x4 u16 1 Property Size Size of this property. This is used by the game to skip over the property if it encounters an unrecognized ID.
0x6 Varies 1 Property Data The actual data for this property. The type and size of this data varies depending on which property it is (ie. depending on the ID).
End of property


Generated Objects

Generated objects are stored on a separate layer, denoted with SCGN. The SCGN layer isn't a real layer; it doesn't store a self-index and instances on the layer still contain the index of their original SCLY script layer in their instance ID. These are the stipulations that cause an instance to be written to SCGN:

  • Any instance that receives a Generate/Activate message (MP2) or a Generate/Attach, Generate0/Attach, or Generate1/Attach message (MP3, DKCR) is written to SCGN instead of SCLY.
  • In DKCR, all GenericCreature instances are written to both SCLY and SCGN. (The generated one is spawned if you scroll the creature offscreen and come back.)