data: fix indentation in markdown

master
an 2019-06-12 23:28:15 -04:00
parent 661bc9082f
commit 475aa64138
1 changed files with 162 additions and 162 deletions

View File

@ -7,12 +7,12 @@ unavailable, the link below:
<http://creativecommons.org/publicdomain/zero/1.0/> <http://creativecommons.org/publicdomain/zero/1.0/>
All of the information in this Document is original research. Marathon and All of the information in this Document is original research. Marathon and Forge
Forge are owned by Bungie, Inc. QuickDraw, QuickTime and Macintosh are owned by are owned by Bungie, Inc. QuickDraw, QuickTime and Macintosh are owned by Apple.
Apple. Aleph One (also referred to as A1 in this Document) is owned by Bungie, Aleph One (also referred to as A1 in this Document) is owned by Bungie, Inc. et
Inc. et al. Igni Ferroque, Ferro, and Atque are owned by Gregory Smith al. Igni Ferroque, Ferro, and Atque are owned by Gregory Smith (treellama.) Any
(treellama.) Any other copyrights not mentioned here belong to their respective other copyrights not mentioned here belong to their respective owners and not
owners and not me. me.
If you need explanation on anything in this document don't hesitate to ask me. If you need explanation on anything in this document don't hesitate to ask me.
Contact information is available at <http://greyserv.net>. Contact information is available at <http://greyserv.net>.
@ -168,9 +168,9 @@ Text commands include:
It displays a picture to the specified alignment and text to the other side. It displays a picture to the specified alignment and text to the other side.
It will: It will:
* Wait for input before proceeding. - Wait for input before proceeding.
* Display 45 characters per line, and display up to 22 lines on one page. - Display 45 characters per line, and display up to 22 lines on one page.
* Display text aligned to the left on the right side of the screen. - Display text aligned to the left on the right side of the screen.
If alignment is specified as RIGHT, text is aligned to the right on the left of If alignment is specified as RIGHT, text is aligned to the right on the left of
the screen. If alignment is specified as CENTER, no text may be displayed, only the screen. If alignment is specified as CENTER, no text may be displayed, only
@ -195,13 +195,13 @@ hellote this is example text from durnadle prettiest ai in ever thank u for read
`#LOGON` and `#LOGOFF` are generally used first and last in a terminal. `#LOGON` and `#LOGOFF` are generally used first and last in a terminal.
These two display a PICT in the middle of the screen and text below the image These two display a PICT in the middle of the screen and text below the image if
if you supply it. They both do things to the screen borders. you supply it. They both do things to the screen borders.
They will: They will:
* Automatically continue, an input will interrupt it. - Automatically continue, an input will interrupt it.
* Only display one line of text, at most 72 characters. - Only display one line of text, at most 72 characters.
* Display text aligned to the center in the middle of the screen. - Display text aligned to the center in the middle of the screen.
Example: Example:
@ -222,9 +222,9 @@ ehhg.431.4122//<PFGR ZNE6 &49c2>
`#INFORMATION` will just display text, and is mostly used in Marathon 1. `#INFORMATION` will just display text, and is mostly used in Marathon 1.
It will: It will:
* Wait for input before proceeding. - Wait for input before proceeding.
* Display 72 characters per line, and display up to 22 lines on one page. - Display 72 characters per line, and display up to 22 lines on one page.
* Display text aligned to the left on the left side of the screen. - Display text aligned to the left on the left side of the screen.
Example: Example:
@ -243,17 +243,17 @@ p.s. if you don't win i'm erasing your home planet from existence
`#CHECKPOINT` may only be used in Marathon 1, unless you're using Aleph One `#CHECKPOINT` may only be used in Marathon 1, unless you're using Aleph One
version 1.1 or higher. version 1.1 or higher.
This shows a map centered on the specified goal point, with the goal circled, This shows a map centered on the specified goal point, with the goal circled, on
on the left of the screen. the left of the screen.
The map will only show polygons connected to the polygon the goal is in, so if The map will only show polygons connected to the polygon the goal is in, so if
you have a separated area where the goal point is, it will only display that. you have a separated area where the goal point is, it will only display that. It
It will also not display secret areas and any polygons proceeding them. will also not display secret areas and any polygons proceeding them.
It will: It will:
* Wait for input before proceeding. - Wait for input before proceeding.
* Display 45 characters per line, and display up to 22 lines on one page. - Display 45 characters per line, and display up to 22 lines on one page.
* Display text aligned to the left on the right side of the screen. - Display text aligned to the left on the right side of the screen.
Example: Example:
@ -338,8 +338,8 @@ Example:
#SOUND sound_number #SOUND sound_number
``` ```
`#SOUND` plays the specified sound from the Sounds file or from the scenario `#SOUND` plays the specified sound from the Sounds file or from the scenario and
and then goes to the next level. then goes to the next level.
Example: Example:
@ -394,12 +394,12 @@ Map tags:
Map files can be identified by the `Minf` chunk. Map files can be identified by the `Minf` chunk.
Maps will always have either a `PNTS` or `EPNT` chunk, depending on what the Maps will always have either a `PNTS` or `EPNT` chunk, depending on what the map
map (and editor) use. `PNTS` are plain and have no more information than the (and editor) use. `PNTS` are plain and have no more information than the actual
actual position, while `EPNT` can be loaded directly into memory by the engine. position, while `EPNT` can be loaded directly into memory by the engine. `EPNT`
`EPNT` also tells the engine that the map is preprocessed and that `iidx` and also tells the engine that the map is preprocessed and that `iidx` and `PLAT`
`PLAT` chunks also exist. With `DataVersion` as `DataM1`, the format must chunks also exist. With `DataVersion` as `DataM1`, the format must always be
always be preprocessed. preprocessed.
Physics tags: Physics tags:
@ -411,9 +411,9 @@ Physics tags:
| `PXpx` | Array of Physics Definition | | `PXpx` | Array of Physics Definition |
| `WPpx` | Array of Weapon Definition | | `WPpx` | Array of Weapon Definition |
Physics definitions may be embedded into a map in Infinity and Aleph One, so Physics definitions may be embedded into a map in Infinity and Aleph One, so the
the only reliable way to check if something is a pure physics file is by only reliable way to check if something is a pure physics file is by checking
checking that there are no chunks other than `**px` chunks. that there are no chunks other than `**px` chunks.
Image tags: Image tags:
@ -484,25 +484,25 @@ The type "`fixed`" refers to a 32-bit fixed point number with the format 15.16s
sign.) sign.)
The type "`angle`" refers to a 16-bit fixed point number with the format 0.9s. The type "`angle`" refers to a 16-bit fixed point number with the format 0.9s.
This is used for all angles. Because they're actually 16-bit, the real format This is used for all angles. Because they're actually 16-bit, the real format is
is 6.9s, but the integral part is ignored. "No angle" is represented by 65510 6.9s, but the integral part is ignored. "No angle" is represented by 65510
(-1.9) for some reason. (-1.9) for some reason.
The type "`unit`" refers to a 16-bit fixed point number with the format 5.10s. The type "`unit`" refers to a 16-bit fixed point number with the format 5.10s.
This is used for all world coordinates. This is used for all world coordinates.
A "`u16opt`" is a 16-bit integer which references something by index. If all A "`u16opt`" is a 16-bit integer which references something by index. If all
bits are set, it is to be interpreted as "none." Traditionally, these are bits are set, it is to be interpreted as "none." Traditionally, these are signed
signed integers, but they can be treated as unsigned with no repercussions. integers, but they can be treated as unsigned with no repercussions.
## Wad ## ## Wad ##
### Wad File ### ### Wad File ###
Wad files are structured like: Wad files are structured like:
* Wad Header - Wad Header
* Entries/Chunks - Entries/Chunks
* Directory - Directory
It *must* be in this order because the engine assumes that the data directly It *must* be in this order because the engine assumes that the data directly
after the 128th byte is entry data. after the 128th byte is entry data.
@ -539,9 +539,9 @@ If `WadVersion` is greater than or equal to `VerDir`:
- `DirOffset` is the offset to the first Directory Entry structure. - `DirOffset` is the offset to the first Directory Entry structure.
- `NumEntries` is the number of entries in this file. - `NumEntries` is the number of entries in this file.
- `AppDataSize` is the number of bytes to skip for each directory entry. - `AppDataSize` is the number of bytes to skip for each directory entry.
- `ChunkSize` and `EntrySize` may be zero, in which case they will default to - `ChunkSize` and `EntrySize` may be zero, in which case they will default to 16
16 and 10 respectively. They exist for forward compatibility with Wad patching, and 10 respectively. They exist for forward compatibility with Wad patching,
but because they were never actually expanded upon, are useless. but because they were never actually expanded upon, are useless.
If `WadVersion` is greater than or equal to `VerOver`: If `WadVersion` is greater than or equal to `VerOver`:
@ -553,8 +553,8 @@ If `WadVersion` is greater than or equal to `VerOver`:
### Directory Entry ### ### Directory Entry ###
Directory Entry is 8 bytes if `WadVersion` is `VerBase`, or else `EntrySize + Directory Entry is 8 bytes if `WadVersion` is `VerBase`, or else `EntrySize
AppData` bytes. Following this structure is `AppData` bytes, supposed to be + AppData` bytes. Following this structure is `AppData` bytes, supposed to be
| Name | Type | Offset | | Name | Type | Offset |
| ---- | ---- | ------ | | ---- | ---- | ------ |
@ -562,7 +562,7 @@ AppData` bytes. Following this structure is `AppData` bytes, supposed to be
| `DataSize` | `u32` | `4` | | `DataSize` | `u32` | `4` |
- `DataOffset` is the offset to the start of this entry's data (from the start - `DataOffset` is the offset to the start of this entry's data (from the start
of the file.) of the file.)
- `DataSize` is the length of this entry's data. - `DataSize` is the length of this entry's data.
If `WadVersion` is greater than or equal to `VerDir`: If `WadVersion` is greater than or equal to `VerDir`:
@ -574,14 +574,14 @@ If `WadVersion` is greater than or equal to `VerDir`:
- `Index` is the index of this entry, for instance the map or PICT number. - `Index` is the index of this entry, for instance the map or PICT number.
- `AppData` is an arbitrary data array used by editor applications, and will be - `AppData` is an arbitrary data array used by editor applications, and will be
ignored by the engine. ignored by the engine.
### Chunk ### ### Chunk ###
Chunk is 12 bytes if `WadVersion` is `VerBase`, or `ChunkSize` bytes otherwise. Chunk is 12 bytes if `WadVersion` is `VerBase`, or `ChunkSize` bytes otherwise.
Most Wad entries are made up of tagged data formats, the engine assumes this Most Wad entries are made up of tagged data formats, the engine assumes this for
for every entry and so every entry has at least one chunk. These are similar to every entry and so every entry has at least one chunk. These are similar to IFF
IFF or PNG chunks. or PNG chunks.
| Name | Type | Offset | | Name | Type | Offset |
| ---- | ---- | ------ | | ---- | ---- | ------ |
@ -638,8 +638,8 @@ Point is 4 bytes. A geometric point.
### Endpoint ### ### Endpoint ###
Endpoint is 16 bytes. A point structure which can be loaded directly into Endpoint is 16 bytes. A point structure which can be loaded directly into memory
memory instead of being calculated at runtime. instead of being calculated at runtime.
| Name | Type | Offset | | Name | Type | Offset |
| ---- | ---- | ------ | | ---- | ---- | ------ |
@ -650,8 +650,8 @@ memory instead of being calculated at runtime.
| `Support` | `u16` | `14` | | `Support` | `u16` | `14` |
- `Flags` is an Endpoint Flags bit field. - `Flags` is an Endpoint Flags bit field.
- `HeightHi` and `HeightLo` are the highest adjacent ceiling and lowest - `HeightHi` and `HeightLo` are the highest adjacent ceiling and lowest adjacent
adjacent floor heights, respectively. floor heights, respectively.
- `Position` is a Point structure. - `Position` is a Point structure.
- `Support` is the index of the highest adjacent polygon. - `Support` is the index of the highest adjacent polygon.
@ -674,8 +674,8 @@ Line is 32 bytes. A geometric line segment.
- `PointBeg` and `PointEnd` are the beginning and terminating endpoints. - `PointBeg` and `PointEnd` are the beginning and terminating endpoints.
- `Flags` is a Line Flags bit field. - `Flags` is a Line Flags bit field.
- `HeightHi` and `HeightLo` are the highest adjacent ceiling and lowest - `HeightHi` and `HeightLo` are the highest adjacent ceiling and lowest adjacent
adjacent floor heights, respectively. floor heights, respectively.
- `SideFrnt` and `SideBack` are indices of the Sides in the front and back. - `SideFrnt` and `SideBack` are indices of the Sides in the front and back.
- `PolyFrnt` and `PolyBack` are indices of the connected Polygons. - `PolyFrnt` and `PolyBack` are indices of the connected Polygons.
@ -704,24 +704,24 @@ Side is 64 bytes. One possibly textured side of a line segment.
- `Type` is a Side Type enumeration. - `Type` is a Side Type enumeration.
- `Flags` is a Side Flags bit field. - `Flags` is a Side Flags bit field.
- `TexPri`, `TexSec` and `TexTra` are Side Texture structures representing the - `TexPri`, `TexSec` and `TexTra` are Side Texture structures representing the
primary, secondary and transparent (middle) textures. Middle textures are not primary, secondary and transparent (middle) textures. Middle textures are not
supported if `DataVersion` is `DataM1` and so `TexTra` must be set to none. supported if `DataVersion` is `DataM1` and so `TexTra` must be set to none.
- `ExTopL`, `ExTopR`, `ExBotL` and `ExBotR` are Point structures representing - `ExTopL`, `ExTopR`, `ExBotL` and `ExBotR` are Point structures representing
the collision bounding rectangle. the collision bounding rectangle.
- `PanelType` is a control panel preset number. - `PanelType` is a control panel preset number.
- `PanelPerm` is the permutation for this control panel (if any.) - `PanelPerm` is the permutation for this control panel (if any.)
- `XferPri`, `XferSec` and `XferTra` are Transfer Mode enumerations for each - `XferPri`, `XferSec` and `XferTra` are Transfer Mode enumerations for each
respective texture. respective texture.
- `Shade` is the ambient shading used primarily for visual contrast. If - `Shade` is the ambient shading used primarily for visual contrast. If
`DataVersion` is `DataM1`, this must be set to 0. `DataVersion` is `DataM1`, this must be set to 0.
### Polygon ### ### Polygon ###
Polygon is 128 bytes. A geometric polygon, essentially Doom's "sector," but Polygon is 128 bytes. A geometric polygon, essentially Doom's "sector," but must
must be convex. More similar to a "subsector" since you have to split it be convex. More similar to a "subsector" since you have to split it yourself and
yourself and the map compiler will not help you with this process. (It is a the map compiler will not help you with this process. (It is a planned feature
planned feature of Maraiah to allow the user to draw polygons of arbitrary of Maraiah to allow the user to draw polygons of arbitrary shape and
shape and automatically split them.) automatically split them.)
Note that `u16opt`s not available with `DataM1` must be set to none. Note that `u16opt`s not available with `DataM1` must be set to none.
@ -765,7 +765,7 @@ If `DataVersion` is not `DataM1`:
| `SoundRandom` | `u16opt` | `124` | | `SoundRandom` | `u16opt` | `124` |
- `Type` is a Polygon Type enumeration, unless `DataVersion` is `DataM1`, where - `Type` is a Polygon Type enumeration, unless `DataVersion` is `DataM1`, where
it is instead an Old Polygon Type enumeration. it is instead an Old Polygon Type enumeration.
- `Flags` is a Polygon Flags bit field. - `Flags` is a Polygon Flags bit field.
- `Area` is the power-of-two area of the polygon. - `Area` is the power-of-two area of the polygon.
- `ObjectFst` must be `65535`. - `ObjectFst` must be `65535`.
@ -797,11 +797,10 @@ Light is 100 bytes. If `DataVersion` is `DataM1` this is an Old Light.
### Old Light ### ### Old Light ###
Old Light is 32 bytes. The old lighting system not only sucked, but there was Old Light is 32 bytes. The old lighting system not only sucked, but there was no
no Media system, so it was even more useless as it couldn't be used as a Media system, so it was even more useless as it couldn't be used as a controller
controller for liquids. So, because of these issues, the new lighting system for liquids. So, because of these issues, the new lighting system was put in
was put in place, but it was incompatible data-wise because it had too many place, but it was incompatible data-wise because it had too many extensions.
extensions.
| Name | Type | Offset | | Name | Type | Offset |
@ -815,15 +814,15 @@ extensions.
| `ValueCur` | `fixed` | `18` | | `ValueCur` | `fixed` | `18` |
- `Type` is an Old Light Type enumeration. To create a new light from this, you - `Type` is an Old Light Type enumeration. To create a new light from this, you
will need to write a lookup table which imitates each light type in the new will need to write a lookup table which imitates each light type in the new
lighting system. This table is tedious to write, so please reference either lighting system. This table is tedious to write, so please reference either
Aleph One or Maraiah for a full table of translations. Aleph One or Maraiah for a full table of translations.
- `Mode` is an Old Light Mode enumeration. - `Mode` is an Old Light Mode enumeration.
- `Phase` is ignored in Aleph One. - `Phase` is ignored in Aleph One.
- If `Type` is `Strobe`, you must set each resulting `Period` to this - If `Type` is `Strobe`, you must set each resulting `Period` to this
definition's `Period` divided by 4 plus one. Otherwise, `Period` is ignored. definition's `Period` divided by 4 plus one. Otherwise, `Period` is ignored.
- For each of the new definition's functions, if the intensity of it is more - For each of the new definition's functions, if the intensity of it is more
than 0, it should be set to `ValueMax`, otherwise `ValueMin`. than 0, it should be set to `ValueMax`, otherwise `ValueMin`.
- `ValueCur` is ignored in Aleph One. - `ValueCur` is ignored in Aleph One.
### Map Annotation ### ### Map Annotation ###
@ -838,7 +837,7 @@ Map Annotation is 72 bytes.
| `Text` | `u8[64]` | `8` | | `Text` | `u8[64]` | `8` |
- `Type` is an index into the annotation type definition, but there's only one, - `Type` is an index into the annotation type definition, but there's only one,
so this will always be `0` anyway. so this will always be `0` anyway.
### Object ### ### Object ###
@ -856,7 +855,7 @@ Object is 16 bytes.
| `Flags` | `u16` | `14` | | `Flags` | `u16` | `14` |
- `Flags` is a Map Object Flags bit field, and the upper 4 bits are the - `Flags` is a Map Object Flags bit field, and the upper 4 bits are the
activation bias for monsters. activation bias for monsters.
### Object Frequency ### ### Object Frequency ###
@ -948,7 +947,7 @@ part of the map in the middle of a wall.
- `Type` is a Media Type enumeration. - `Type` is a Media Type enumeration.
- `Flags` is a Media Flags bit field. - `Flags` is a Media Flags bit field.
- `Control` is the index of a light which is used to control the height of this - `Control` is the index of a light which is used to control the height of this
media. media.
- `XferMode` is a Transfer Mode enumeration. - `XferMode` is a Transfer Mode enumeration.
### Static Map Info ### ### Static Map Info ###
@ -965,40 +964,41 @@ Static Map Info is 88 bytes.
| `Name` | `u8[66]` | `18` | | `Name` | `u8[66]` | `18` |
| `EntryFlags` | `u32` | `84` | | `EntryFlags` | `u32` | `84` |
- `TextureId` is a Texture Collection enumeration. It is a preset number for texture collections and some other things such as media (liquid) presets. - `TextureId` is a Texture Collection enumeration. It is a preset number for
texture collections and some other things such as media (liquid) presets.
- `PhysicsId` used to be used for specifying three physics models: one for the - `PhysicsId` used to be used for specifying three physics models: one for the
Forge editor, one for the game, and one for low-gravity. However, the first one Forge editor, one for the game, and one for low-gravity. However, the first
ended up being useless and the third was made into a map flag instead which one ended up being useless and the third was made into a map flag instead
simply modifies the current physics model. This should always be set to `1` by which simply modifies the current physics model. This should always be set to
new editors. `1` by new editors.
- `LandscapeId` is a Landscape enumeration. is the landscape number to use for - `LandscapeId` is a Landscape enumeration. is the landscape number to use for
the sky. This starts at `0`, since it's an offset into the landscape the sky. This starts at `0`, since it's an offset into the landscape
collections. If `DataVersion` is `DataM1` or the `Music` flag of `EnvFlags` is collections. If `DataVersion` is `DataM1` or the `Music` flag of `EnvFlags` is
set, then this is used as the music index instead. set, then this is used as the music index instead.
- `MissionFlags` is a Mission Flags bit field. - `MissionFlags` is a Mission Flags bit field.
- `EnvFlags` is an Environment Flags bit field. - `EnvFlags` is an Environment Flags bit field.
- `Name` is the level name, intended to be 65 bytes, but one padding byte is - `Name` is the level name, intended to be 65 bytes, but one padding byte is
left over, so the real length is 66. left over, so the real length is 66.
- `EntryFlags` is an Entry Point Flags bit field. It is unknown why this is 32 - `EntryFlags` is an Entry Point Flags bit field. It is unknown why this is 32
bits wide when it could fit in even 8 bits. If `DataVersion` is `DataM1` and bits wide when it could fit in even 8 bits. If `DataVersion` is `DataM1` and
this is `0`, this implies the value is `Solo`. this is `0`, this implies the value is `Solo`.
## Terminal ## ## Terminal ##
### Terminal ### ### Terminal ###
Terminal text can be encoded with some weird xor bullshit for some reason. Terminal text can be encoded with some weird xor bullshit for some reason. You
You can decode it and encode it with the same method: can decode it and encode it with the same method:
```c ```c
for(i = 0; i < len / 4; i++) {p += 2; *p++ ^= 0xFE; *p++ ^= 0xED;} for(i = 0; i < len / 4; i++) {p += 2; *p++ ^= 0xFE; *p++ ^= 0xED;}
for(i = 0; i < len % 4; i++) *p++ ^= 0xFE; for(i = 0; i < len % 4; i++) *p++ ^= 0xFE;
``` ```
* Terminal Header - Terminal Header
* Terminal Groups - Terminal Groups
* Text Faces - Text Faces
* Terminal text (null byte terminated) - Terminal text (null byte terminated)
### Terminal Header ### ### Terminal Header ###
@ -1129,7 +1129,7 @@ Weapon Definition is 134 bytes.
- `WeaponClass` is a Weapon Type enumeration. - `WeaponClass` is a Weapon Type enumeration.
- `Flags` is a Weapon Flags bit field. - `Flags` is a Weapon Flags bit field.
- `TriggerPri` and `TriggerSec` are Trigger Definition structures used for the - `TriggerPri` and `TriggerSec` are Trigger Definition structures used for the
primary and secondary fire buttons. primary and secondary fire buttons.
### Trigger Definition ### ### Trigger Definition ###
@ -1286,10 +1286,11 @@ Attack Definition is 16 bytes.
Pictures are formed with a header and then a variable number of operations. In Pictures are formed with a header and then a variable number of operations. In
other words, a small state machine is used to form an image through effects and other words, a small state machine is used to form an image through effects and
various fill instructions. QuickDraw is horrifying. This is the native image various fill instructions. QuickDraw is horrifying. This is the native image
format. It's a fucking metafile. format. It's a fucking metafile. I suppose this could be worse, considering they
later used PDF files for images.
* Picture Header - Picture Header
* Picture Opcodes - Picture Opcodes
### Picture Header ### ### Picture Header ###
@ -1325,7 +1326,7 @@ Always:
| `Right` | `u16` | | `Right` | `u16` |
- `PitchFl` is the number of bytes per row, and the upper two bits are a - `PitchFl` is the number of bytes per row, and the upper two bits are a
CopyBits Flags bit field. CopyBits Flags bit field.
If PICT2: If PICT2:
@ -1421,14 +1422,14 @@ Header Op is 24 bytes.
## Shapes ## ## Shapes ##
Shapes files start with exactly 32 Collection Headers, followed by everything Shapes files start with exactly 32 Collection Headers, followed by everything
else. Use the offsets provided by these structures to find where all of the else. Use the offsets provided by these structures to find where all of the data
data is. is.
### Collection Header ### ### Collection Header ###
Collection Header is 32 bytes. Each collection may have two versions, lo-res Collection Header is 32 bytes. Each collection may have two versions, lo-res and
and hi-res, which are used according to the user's settings. The main purpose hi-res, which are used according to the user's settings. The main purpose of
of these is for compatibility with older Macs which might not have enough video these is for compatibility with older Macs which might not have enough video
memory for, for instance, the huge two mebibyte sky boxes that Marathon 2 has. memory for, for instance, the huge two mebibyte sky boxes that Marathon 2 has.
| Name | Type | Offset | | Name | Type | Offset |
@ -1440,11 +1441,11 @@ memory for, for instance, the huge two mebibyte sky boxes that Marathon 2 has.
### Collection Definition ### ### Collection Definition ###
Collection Definition is 544 bytes (no, I'm not kidding, there are actually Collection Definition is 544 bytes (no, I'm not kidding, there are actually that
that many unused bytes.) The sequences, frames and bitmaps have their many unused bytes.) The sequences, frames and bitmaps have their individual
individual offsets stored in tables, which themselves are at offsets specified offsets stored in tables, which themselves are at offsets specified by this
by this structure. Note that all offsets (including those in offset tables) are structure. Note that all offsets (including those in offset tables) are relative
relative to the start of this structure. to the start of this structure.
| Name | Type | Offset | | Name | Type | Offset |
| ---- | ---- | ------ | | ---- | ---- | ------ |
@ -1464,11 +1465,11 @@ relative to the start of this structure.
- `Type` is a Collection Type enumeration. - `Type` is a Collection Type enumeration.
- `TabNum` and `TabOfs` are the number of and offset to the color tables. - `TabNum` and `TabOfs` are the number of and offset to the color tables.
- `SeqNum` and `SeqOfs` are the number of sequences and the offset to their - `SeqNum` and `SeqOfs` are the number of sequences and the offset to their
offset table. offset table.
- `FrmNum` and `FrmOfs` are the number of frames and the offset to their offset - `FrmNum` and `FrmOfs` are the number of frames and the offset to their offset
table. table.
- `BmpNum` and `BmpOfs` are the number of bitmaps and the offset to their - `BmpNum` and `BmpOfs` are the number of bitmaps and the offset to their offset
offset table. table.
### Frame ### ### Frame ###
@ -1494,8 +1495,7 @@ Frame is 36 bytes. TODO: document how world transform works.
Sequence is 88 bytes. A sequence, also known as a "high level shape" in the Sequence is 88 bytes. A sequence, also known as a "high level shape" in the
engine, is essentially a potentially animated sequence of frames organized into engine, is essentially a potentially animated sequence of frames organized into
angular views which may loop or play sounds. Each sequence has a "key frame" angular views which may loop or play sounds. Each sequence has a "key frame"
which is used for determining when to run action code or play an attached which is used for determining when to run action code or play an attached sound.
sound.
| Name | Type | Offset | | Name | Type | Offset |
| ---- | ---- | ------ | | ---- | ---- | ------ |
@ -1512,7 +1512,7 @@ sound.
| `FrameLoop` | `u16` | `58` | | `FrameLoop` | `u16` | `58` |
- `Name` is the sequence name, used mainly by editors, supposed to be 33 bytes, - `Name` is the sequence name, used mainly by editors, supposed to be 33 bytes,
but due to padding, the real length is 34. but due to padding, the real length is 34.
- `ViewType` is a View Type enumeration. - `ViewType` is a View Type enumeration.
- `FrameNum` is the number of frames in this sequence. - `FrameNum` is the number of frames in this sequence.
- `FrameTick` is the number of ticks per frame. - `FrameTick` is the number of ticks per frame.
@ -1520,14 +1520,14 @@ but due to padding, the real length is 34.
- `XferMode` is a Transfer Mode enumeration. - `XferMode` is a Transfer Mode enumeration.
- `XferPeriod` is the period for the transfer mode in 1/30ths seconds. - `XferPeriod` is the period for the transfer mode in 1/30ths seconds.
- `SndBeg`, `SndKey` and `SndEnd` are the sounds played at the first, key and - `SndBeg`, `SndKey` and `SndEnd` are the sounds played at the first, key and
last frame of this sequence. last frame of this sequence.
### Bitmap Header ### ### Bitmap Header ###
Bitmap Header is 26 bytes. Bitmap Header is 26 bytes.
Each Bitmap Header is followed by either `Height * 4` or `Width * 4` empty Each Bitmap Header is followed by either `Height * 4` or `Width * 4` empty bytes
bytes which must be skipped. which must be skipped.
| Name | Type | Offset | | Name | Type | Offset |
| ---- | ---- | ------ | | ---- | ---- | ------ |
@ -1540,7 +1540,7 @@ bytes which must be skipped.
- `Width` is the number of pixels on the horizontal axis. - `Width` is the number of pixels on the horizontal axis.
- `Height` is the number of pixels on the vertical axis. - `Height` is the number of pixels on the vertical axis.
- `Pitch` is either the number of pixels per row if row ordered, per column if - `Pitch` is either the number of pixels per row if row ordered, per column if
column ordered, or `65535` if the data is transparency RLE compressed. column ordered, or `65535` if the data is transparency RLE compressed.
- `Flags` is a Bitmap Flags bit field. - `Flags` is a Bitmap Flags bit field.
- `Depth` must always be `8`. - `Depth` must always be `8`.
@ -1566,11 +1566,11 @@ This header is followed by `SrcNum * SndNum` Sound Definitions.
- `Version` is always `1`. - `Version` is always `1`.
- `Magic` is always `"snd2"`. - `Magic` is always `"snd2"`.
- `SrcNum` defines the number of sound formats this file provides, similar to - `SrcNum` defines the number of sound formats this file provides, similar to
Shapes' lo- and hi-res collections, although this applies to the entire file Shapes' lo- and hi-res collections, although this applies to the entire file
and not just parts of it. `0` is invalid for this field, and in the original and not just parts of it. `0` is invalid for this field, and in the original
Marathon 2 engine (on Mac only, not on Windows,) it must be `2` because of Marathon 2 engine (on Mac only, not on Windows,) it must be `2` because of
QuickTime. A value of `1` means "8-bit 22kHz only" and a value of `2` means QuickTime. A value of `1` means "8-bit 22kHz only" and a value of `2` means
"both 8-bit 22kHz and 16-bit 22kHz." "both 8-bit 22kHz and 16-bit 22kHz."
### Sound Definition ### ### Sound Definition ###
@ -1600,7 +1600,7 @@ Sound Definition is 64 bytes.
- `Size` is the sound of an individual sound in the group. - `Size` is the sound of an individual sound in the group.
- `GroupSize` is the total size of all sounds in the group. - `GroupSize` is the total size of all sounds in the group.
- `AddOffset` is the offset added to `GroupOffset` to get an individual sound. - `AddOffset` is the offset added to `GroupOffset` to get an individual sound.
While it is an array of `NumOfs` offsets, it has a fixed size in the format. While it is an array of `NumOfs` offsets, it has a fixed size in the format.
### Carbon Sound Header ### ### Carbon Sound Header ###
@ -1608,11 +1608,11 @@ Carbon Sound Header is 21 bytes.
The sound format is from Carbon's `SoundHeader` structures. It's used primarily The sound format is from Carbon's `SoundHeader` structures. It's used primarily
in System 7 programs as `snd` resources but in OS X it was deprecated in favor in System 7 programs as `snd` resources but in OS X it was deprecated in favor
of QuickTime. HFS still has Resource Forks but they aren't used anymore. I of QuickTime. HFS still has Resource Forks but they aren't used anymore. I don't
don't imagine this format was ever used for anything else, except for Marathon, imagine this format was ever used for anything else, except for Marathon, which
which embeds it in the Sound files directly, instead of using `snd` resources embeds it in the Sound files directly, instead of using `snd` resources (which
(which have a larger structure consisting of a resource header and sound have a larger structure consisting of a resource header and sound commands
commands rather than just the header and sample data.) rather than just the header and sample data.)
| Name | Type | Offset | | Name | Type | Offset |
| ---- | ---- | ------ | | ---- | ---- | ------ |
@ -1623,18 +1623,18 @@ commands rather than just the header and sample data.)
| `Magic` | `u8` | `20` | | `Magic` | `u8` | `20` |
- If `Magic` is `$00` nothing else needs to be done and raw unsigned 8-bit mono - If `Magic` is `$00` nothing else needs to be done and raw unsigned 8-bit mono
PCM sample data starts at byte 22. If it is `$FF` it is followed by a Carbon PCM sample data starts at byte 22. If it is `$FF` it is followed by a Carbon
Extended Sound Header, or if it is `$FE` it is followed by a Carbon Compressed Extended Sound Header, or if it is `$FE` it is followed by a Carbon Compressed
Sound Header. The compressed sound header is not documented because it is not Sound Header. The compressed sound header is not documented because it is not
actually used by Marathon. actually used by Marathon.
### Carbon Extended Sound Header ### ### Carbon Extended Sound Header ###
Carbon Extended Sound Header is 42 bytes. Carbon Extended Sound Header is 42 bytes.
The extended sound header contains more useless information and even several The extended sound header contains more useless information and even several
fields that do absolutely nothing. Wow. At least it can store 16 bit samples. fields that do absolutely nothing. Wow. At least it can store 16 bit samples. It
It also has an 80-bit float in it, which horrifies me greatly. There's only one also has an 80-bit float in it, which horrifies me greatly. There's only one
actually useful field. actually useful field.
| Name | Type | Offset | | Name | Type | Offset |
@ -1643,10 +1643,10 @@ actually useful field.
| `SampleBits` | `u16` | `26` | | `SampleBits` | `u16` | `26` |
- `Frames` is used instead of `Size` for sounds with this header, since it - `Frames` is used instead of `Size` for sounds with this header, since it
represents how many frames there are rather than how many bytes. Even though represents how many frames there are rather than how many bytes. Even though
this is actually a pointless distinction and `Size` is left at `1` anyway. this is actually a pointless distinction and `Size` is left at `1` anyway.
- `SampleBits` must be either `16` or `8`. If it is `16` then the sample data - `SampleBits` must be either `16` or `8`. If it is `16` then the sample data is
is signed 16-bit *little endian* mono PCM. signed 16-bit *little endian* mono PCM.
# ENUMERATIONS ################################################################ # ENUMERATIONS ################################################################
@ -1891,7 +1891,7 @@ Marathon 2 itself acknowledges how redundant this enumeration is.
| `Toggle` | `4` | | `Toggle` | `4` |
- `TurningOn` and `Active` mean the new light created from this should have the - `TurningOn` and `Active` mean the new light created from this should have the
`InitActive` flag. Others do not mean anything. `InitActive` flag. Others do not mean anything.
### Wad Version ### ### Wad Version ###
@ -1970,14 +1970,14 @@ Sound behaviours are used to determine falloff and volume bounds of a sound.
| `Normal` | `1` | | `Normal` | `1` |
| `Loud` | `2` | | `Loud` | `2` |
- `Quiet` sounds will not be heard at all when obstructed, and only play at - `Quiet` sounds will not be heard at all when obstructed, and only play at full
full volume point-blank. They fall off very quickly, with a range of only 5 volume point-blank. They fall off very quickly, with a range of only 5 world
world units. units.
- `Normal` sounds will be heard at at most half volume when obstructed, and - `Normal` sounds will be heard at at most half volume when obstructed, and fall
fall off at 10 world units unobstructed. off at 10 world units unobstructed.
- `Loud` sounds will be heard at 3/4 volume when obstructed and can be heard at - `Loud` sounds will be heard at 3/4 volume when obstructed and can be heard at
full volume for twice the distance as a normal sound, and fall off at 15 units full volume for twice the distance as a normal sound, and fall off at 15 units
unobstructed. unobstructed.
### Light Function ### ### Light Function ###
@ -2105,8 +2105,8 @@ over for editor preset usage.
| `Transparent` | `2` | | `Transparent` | `2` |
- `Solid` means the point belongs to a solid line. - `Solid` means the point belongs to a solid line.
- `SameHeight` means all polygons with this point have the same height, - `SameHeight` means all polygons with this point have the same height, relative
relative to the point's lines to the point's lines
- `Transparent` means the point does not belong to an opaque line. - `Transparent` means the point does not belong to an opaque line.
### Line Flags ### ### Line Flags ###
@ -2188,17 +2188,17 @@ If `DataVersion` is `DataM1`, then `ItemOpt` must be set by the client.
| `M1Repair` | `7` | | `M1Repair` | `7` |
- `Extermination` means you must kill all monsters on the map, with an error - `Extermination` means you must kill all monsters on the map, with an error
threshold of 8 alien enemies maximum. threshold of 8 alien enemies maximum.
- `Exploration` means you must explore marked polygons. - `Exploration` means you must explore marked polygons.
- `Retrieval` means you must grab marked items. - `Retrieval` means you must grab marked items.
- `Repair` means you must flip marked switches. - `Repair` means you must flip marked switches.
- `Rescue` means you must keep 50% of BoBs alive. - `Rescue` means you must keep 50% of BoBs alive.
- `M1Exploration` is the same as `Exploration` except you only need to look at - `M1Exploration` is the same as `Exploration` except you only need to look at
each marked polygon, not actually enter them. each marked polygon, not actually enter them.
- `M1Rescue` is the same as `Rescue`. Since this is an internal flag, all it - `M1Rescue` is the same as `Rescue`. Since this is an internal flag, all it
actually does is change which monster class it checks. actually does is change which monster class it checks.
- `M1Repair` is the same as `Repair`, except it only requires that the last - `M1Repair` is the same as `Repair`, except it only requires that the last
switch (by side index) be switched to succeed. switch (by side index) be switched to succeed.
### Environment Flags ### ### Environment Flags ###
@ -2227,7 +2227,7 @@ switch (by side index) be switched to succeed.
- `TermPause` makes terminals stop time (in Solo only.) - `TermPause` makes terminals stop time (in Solo only.)
- `M1Monster` sets monster activation limits to Marathon 1's. - `M1Monster` sets monster activation limits to Marathon 1's.
- `M1Weps` changes weapon pickups on Total Carnage and makes grenades low - `M1Weps` changes weapon pickups on Total Carnage and makes grenades low
gravity. gravity.
### Light Flags ### ### Light Flags ###
@ -2313,7 +2313,7 @@ gravity.
| `SoundObstruct` | `0` | | `SoundObstruct` | `0` |
- `SoundObstruct` means the media makes no sound when under the floor. This is - `SoundObstruct` means the media makes no sound when under the floor. This is
most sensible for, for instance, lava which can be drained. most sensible for, for instance, lava which can be drained.
### Object Frequency Flags ### ### Object Frequency Flags ###