Difference between revisions of "FF7/Field"
my_wiki>Cyberman (→PSX DAT Format) |
|||
(32 intermediate revisions by 10 users not shown) | |||
Line 27: | Line 27: | ||
* The running of the Field Script to display events and to get user input | * The running of the Field Script to display events and to get user input | ||
* The on-demand loading of other modules when needed | * The on-demand loading of other modules when needed | ||
+ | |||
+ | A list of fields can be found [[FF7/Field/Field_ID|here]]. | ||
The Field module loads modular "Field Files". In the PC version, the Field File is a single file with nine sections. In the PSX version, there are three files with the same name but with different extensions that do the same thing. The three files are MIM (Mutiple Image Maps, or the backgrounds), DAT (Field Script Data), and BSX (3D data). | The Field module loads modular "Field Files". In the PC version, the Field File is a single file with nine sections. In the PSX version, there are three files with the same name but with different extensions that do the same thing. The three files are MIM (Mutiple Image Maps, or the backgrounds), DAT (Field Script Data), and BSX (3D data). | ||
Line 39: | Line 41: | ||
Another last thing to note is in the middle of the bottom texture cache there are a sea of eyes. These blink at random times and reflect the random blinking of the characters in the game. | Another last thing to note is in the middle of the bottom texture cache there are a sea of eyes. These blink at random times and reflect the random blinking of the characters in the game. | ||
− | |||
− | |||
== Field Format (PC) == | == Field Format (PC) == | ||
Line 46: | Line 46: | ||
=== General PC Field File Format === | === General PC Field File Format === | ||
− | Field files are always found in FLEVEL.LGP. They are always [[FF7/LZS format|LZS]] compressed. | + | Field files are always found in FLEVEL.LGP. They are always [[FF7/LZS format|LZS]] compressed. |
The first two bytes of each (decompressed) field file are blank (zero). | The first two bytes of each (decompressed) field file are blank (zero). | ||
Line 85: | Line 85: | ||
|style="background:rgb(255,255,255)" | 4 bytes | |style="background:rgb(255,255,255)" | 4 bytes | ||
|style="background:rgb(255,255,255)" | Pointer to Section 3 | |style="background:rgb(255,255,255)" | Pointer to Section 3 | ||
− | |style="background:rgb(255,255,255)" | Model Loader | + | |style="background:rgb(255,255,255)" | [[FF7/Field/Model Loader|Model Loader]] |
|- | |- | ||
|style="background:rgb(255,255,255)" | 0x12 | |style="background:rgb(255,255,255)" | 0x12 | ||
Line 97: | Line 97: | ||
|style="background:rgb(255,255,255)" | [[FF7/Field/Walkmesh|Walkmesh]] | |style="background:rgb(255,255,255)" | [[FF7/Field/Walkmesh|Walkmesh]] | ||
|- | |- | ||
− | |style="background:rgb(255,255, | + | |style="background:rgb(255,255,255)" | 0x1A |
− | |style="background:rgb(255,255, | + | |style="background:rgb(255,255,255)" | 4 bytes |
− | |style="background:rgb(255,255, | + | |style="background:rgb(255,255,255)" | Pointer to Section 6 |
− | |style="background:rgb(255,255, | + | |style="background:rgb(255,255,255)" | [[FF7/Field_Module/DAT/Tile_Map|TileMap]] (Unused) |
|- | |- | ||
|style="background:rgb(255,255,255)" | 0x1E | |style="background:rgb(255,255,255)" | 0x1E | ||
Line 110: | Line 110: | ||
|style="background:rgb(255,255,255)" | 4 bytes | |style="background:rgb(255,255,255)" | 4 bytes | ||
|style="background:rgb(255,255,255)" | Pointer to Section 8 | |style="background:rgb(255,255,255)" | Pointer to Section 8 | ||
− | |style="background:rgb(255,255,255)" | | + | |style="background:rgb(255,255,255)" | [[FF7/Field/Triggers|Triggers]] |
|- | |- | ||
|style="background:rgb(255,255,255)" | 0x26 | |style="background:rgb(255,255,255)" | 0x26 | ||
Line 130: | Line 130: | ||
Each section generally starts with a four byte integer indicating the length of the section. You could just work this out by comparing offsets (how much space until the next section/end of file, etc) but FF7 stores the length at the start of the section anyway. After that the actual data follows. So the first bit of data for a section is actually 4 bytes after the point given in the section header (since the first four bytes are actually the length marker). | Each section generally starts with a four byte integer indicating the length of the section. You could just work this out by comparing offsets (how much space until the next section/end of file, etc) but FF7 stores the length at the start of the section anyway. After that the actual data follows. So the first bit of data for a section is actually 4 bytes after the point given in the section header (since the first four bytes are actually the length marker). | ||
− | To examine each section, please navigate using the links in the table above. | + | To examine each section, please navigate using the links in the table above. For sections 3 and 8, there is some information on [http://forums.qhimm.com/index.php?topic=4358.msg58674#msg58674 the forum]. |
− | == Field Format ( | + | == Field Format (PS1) == |
=== PSX DAT Format === | === PSX DAT Format === | ||
Line 146: | Line 146: | ||
! style="background:rgb(0,255,0)" align="center" | Section Information | ! style="background:rgb(0,255,0)" align="center" | Section Information | ||
|- | |- | ||
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | [[FF7/Field/Script|Script]] |
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | Contains conversations, save point interaction etc. |
|- | |- | ||
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | [[FF7/Field/Walkmesh|Walkmesh]] |
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | Contains walkmesh triangles and access info. |
|- | |- | ||
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | [[FF7/Field_Module/DAT/Tile_Map|TileMap]] |
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | Contains the information for the background, animation,<BR> and static scene objects. |
|- | |- | ||
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | [[FF7/Field/Camera_Matrix|Camera_Matrix]] |
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | Contains camera info. |
|- | |- | ||
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | [[FF7/Field/Triggers|Triggers]] |
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | Contains triggers, singles, gateways and so on. |
|- | |- | ||
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | [[FF7/Field/Encounter|Encounter]] |
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | Battle Encounter information for location. |
|- | |- | ||
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | [[FF7/Field/Models|Models]] |
− | |style="background:rgb( | + | |style="background:rgb(200,255,200)" | Some info about field models. |
|} | |} | ||
=== PSX MIM Format === | === PSX MIM Format === | ||
− | Part of the PSX background data is contained in the MIM file, it is compressed with [[FF7/LZS format|LZS compression]]. It consists of palettes (256 color ones) and screen blocks. No data for locating the blocks on the screen is in this file. The MIM file is a truncated TIM file and contains the normal clut location height and width information. This information is directly loaded into the PSX video ram to be decoded by the field module | + | Part of the PSX background data is contained in the [[FF7/Field/MIMfile|MIM file]], it is compressed with [[FF7/LZS format|LZS compression]]. It consists of palettes (256 color ones) and screen blocks. No data for locating the blocks on the screen is in this file. The MIM file is a truncated TIM file and contains the normal clut location height and width information. This information is directly loaded into the PSX video ram to be decoded by the field module. |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
=== PSX BSX Format === | === PSX BSX Format === | ||
− | The Field models are contained | + | The Field models are contained in the [[FF7/Field/BSX|BSX file]], it is compressed with [[FF7/LZS format|LZS compression]]. [[FF7/Field/FIELD.TDB|FIELD.TDB]] contains the textures for these models. |
=== PSX BCX Format === | === PSX BCX Format === | ||
− | The individual characters field models are stored in BCX files | + | The individual characters' field models are stored in [[FF7/Field/BCX|BCX files]]. Their textures are also in [[FF7/Field/FIELD.TDB|FIELD.TDB]]; they are compressed with [[FF7/LZS format|LZS compression]]. |
== Event Scripting == | == Event Scripting == | ||
+ | Event scripting is handled via a series of script commands and entities spawned for the event. The exception to this is the battle event scripting. This is actually a little bit different. Please refer to the [[FF7/Field/Script|Field Script]] for more information. | ||
== Script commands == | == Script commands == | ||
Line 212: | Line 185: | ||
== Movies == | == Movies == | ||
+ | Movies in FF7 are actually triggered from the [[FF7/Field/Script|Field Script]]. The [[FF7/Field/Script/Opcodes/F8 PMVIE|F8 PMVIE]] opcode is first used to set the movie for which the [[FF7/Field/Script/Opcodes/F9 MOVIE|F9 MOVIE]] opcode is used to play. It is important to remember the MOVIE ID may vary in the PS1 versionn depending on what disc you are on. | ||
+ | The PC movies were encoded using the DUCK (goose?) format and are AVI video files. | ||
+ | |||
+ | The PS1 movies were encoded using FMV Motion JPEG video files, for the playstation. These files cannot be decode or read directly from the CD disc media because of the Mode 2 format of the files. The files are encoded using ISO Mode 2 which means the sectors are 2302 bytes in length instead of 2048. The video files have interleaved audio (ADPCM format), between video frames and are 320x224 15fps. Video files that have no audio with it actually has empty sectors of space between video frames to prevent the extremely timing sensitive MDEC decoder in the playstation from locking up. | ||
+ | |||
+ | [[User:Cyberman|Cyberman]] 14:18, 30 Dec 2006 (CST) | ||
== The 3D Overlay == | == The 3D Overlay == | ||
Line 217: | Line 196: | ||
== Data Organization == | == Data Organization == | ||
− | == "A" Field Animation Files for PC by [[User:Mirex|Mirex]] == | + | == "A" Field Animation Files for PC by [[User:Mirex|Mirex]] (Edits by [[User:Aali|Aali]]) == |
Each animation file holds one character animation ( run, walk or some other). Some characters have more animation files. Animation is set of frames, in each frame are stored bone rotations. | Each animation file holds one character animation ( run, walk or some other). Some characters have more animation files. Animation is set of frames, in each frame are stored bone rotations. | ||
Line 228: | Line 207: | ||
|- | |- | ||
|style="background:rgb(255,255,255)" | header | |style="background:rgb(255,255,255)" | header | ||
− | |style="background:rgb(255,255,255)" align="center" | | + | |style="background:rgb(255,255,255)" align="center" | 36 |
− | |||
− | |||
− | |||
|- | |- | ||
|style="background:rgb(255,255,255)" | frames | |style="background:rgb(255,255,255)" | frames | ||
Line 237: | Line 213: | ||
|} | |} | ||
− | -- one frame, size is (bones * 12 + | + | -- one frame, size is (bones * 12 + 12 + 12) -- |
− | |||
− | |||
− | |||
{| border="0" cellspacing="1" cellpadding="3" style="background: rgb(0,0,0)" align="center" | {| border="0" cellspacing="1" cellpadding="3" style="background: rgb(0,0,0)" align="center" | ||
Line 246: | Line 219: | ||
! style="background:rgb(204,204,204)" align="center" | Size | ! style="background:rgb(204,204,204)" align="center" | Size | ||
|- | |- | ||
− | |style="background:rgb(255,255,255)" | | + | |style="background:rgb(255,255,255)" | root rotation |
− | |style="background:rgb(255,255,255)" align="center" | | + | |style="background:rgb(255,255,255)" align="center" | 12 = 3 floats |
+ | |- | ||
+ | |style="background:rgb(255,255,255)" | root translation | ||
+ | |style="background:rgb(255,255,255)" align="center" | 12 = 3 floats | ||
|- | |- | ||
|style="background:rgb(255,255,255)" | rotations | |style="background:rgb(255,255,255)" | rotations | ||
Line 253: | Line 229: | ||
|} | |} | ||
− | header structure, | + | header structure, 36 bytes |
struct { | struct { | ||
− | unsigned | + | unsigned int32 version; |
− | unsigned | + | unsigned int32 frames_count; |
− | unsigned | + | unsigned int32 bones_count; |
− | unsigned | + | unsigned char rotation_order[3]; |
+ | unsigned char unused; | ||
+ | unsigned int32 runtime_data[5]; | ||
} anim_head; | } anim_head; | ||
I understand only two values from the header, 'frames_count' which is number of animation frames and 'bones_count' which is suprisingly number of animated bones. | I understand only two values from the header, 'frames_count' which is number of animation frames and 'bones_count' which is suprisingly number of animated bones. | ||
+ | |||
+ | ''version should always be 1 or FF7 will not load the file'' | ||
+ | |||
+ | ''rotation order determines in which order rotations are applied, 0 means alpha rotation, 1 beta rotation and 2 gamma rotation.'' | ||
+ | |||
+ | ''runtime data has no meaning in the animation file and is discarded on load'' | ||
If you want to load all possible animations for the model (even animations of different models) then check if animation file has same number of bones as current model. | If you want to load all possible animations for the model (even animations of different models) then check if animation file has same number of bones as current model. | ||
− | + | Frame starts with the root rotations and root translations, followed by rotations for each bone. Rotations are stored as 3 floats (float is 4byte floating-point number). | |
− | |||
− | Frame starts with |
Latest revision as of 02:49, 13 July 2019
Contents
Important Files
PSX Version | PC Version |
---|---|
/FIELD/*.DAT | /DATA/FIELD/FLEVEL.LGP |
/FIELD/*.MIM | /DATA/FIELD/FLEVEL.LGP |
/FIELD/*.BSX | |
/FIELD/*.BCX | /DATA/FIELD/CHAR.LGP |
Field Overview
The field module is the core of the game to which everything else is spawned. It is tied very closely with the kernel and contains many low-level calls to it. The field system also contains a self-contained bytecode language called commonly called "Field Script". The field module is responsible for the following:
- The loading and parsing of the field files
- The display of the 2D background ands related special effects
- The display of 3D elements in the field such as the camera, perspective and and entities
- The running of the Field Script to display events and to get user input
- The on-demand loading of other modules when needed
A list of fields can be found here.
The Field module loads modular "Field Files". In the PC version, the Field File is a single file with nine sections. In the PSX version, there are three files with the same name but with different extensions that do the same thing. The three files are MIM (Mutiple Image Maps, or the backgrounds), DAT (Field Script Data), and BSX (3D data).
The backgrounds are actually 16x16 blocks that are loaded into VRAM and then assembled into the video buffer every frame. The system allows for layers to obscure the 3D entities using a simple painter's algorithm.
In this particular field file, there are six cached sections of background data. Also notice the bright green patches that don't show up in in the video buffer. This was to show where a lower layer of 2D data was to be covered by a higher layer. The bright green is for debug purposes. During development, if any bright green showed up, it meant that your upper layer had a "hole" in it that a 3D entity could be seen through.
When the PSX version of FF7 is ran in higher resolutions via emulation with texture filtering on, often the lower layers will "bleed" outside the upper layer and make artifacts. This was also the reason why the field files were not re-rendered for the PC version of the game. It would of required "re-cutting" the layers again in the higher resolution.
Another last thing to note is in the middle of the bottom texture cache there are a sea of eyes. These blink at random times and reflect the random blinking of the characters in the game.
Field Format (PC)
General PC Field File Format
Field files are always found in FLEVEL.LGP. They are always LZS compressed.
The first two bytes of each (decompressed) field file are blank (zero). The next four bytes is an integer indicating how many sections are present in the file. Then a number of 4-byte integers follow, giving the starting offset for each section.
All field files should contain 9 sections; it's what FF7 expects.
PC Field File Header
Offset | Size | Description | Section Data |
---|---|---|---|
0x00 | 2 bytes | Blank | Always 0x00 |
0x02 | 4 bytes | Number of Sections | Always 0x0009 |
0x06 | 4 bytes | Pointer to Section 1 | Field Script & Dialog |
0x0A | 4 bytes | Pointer to Section 2 | Camera Matrix |
0x0E | 4 bytes | Pointer to Section 3 | Model Loader |
0x12 | 4 bytes | Pointer to Section 4 | Palette |
0x16 | 4 bytes | Pointer to Section 5 | Walkmesh |
0x1A | 4 bytes | Pointer to Section 6 | TileMap (Unused) |
0x1E | 4 bytes | Pointer to Section 7 | Encounter |
0x22 | 4 bytes | Pointer to Section 8 | Triggers |
0x26 | 4 bytes | Pointer to Section 9 | Background |
0x2A | 4 bytes | Where Pointer to Section 1 points to | Length of Section 1 |
0x2E | Varies | Start of Section 1 data. Continues for the number of bytes specified in Section Length |
See links above |
Each section generally starts with a four byte integer indicating the length of the section. You could just work this out by comparing offsets (how much space until the next section/end of file, etc) but FF7 stores the length at the start of the section anyway. After that the actual data follows. So the first bit of data for a section is actually 4 bytes after the point given in the section header (since the first four bytes are actually the length marker).
To examine each section, please navigate using the links in the table above. For sections 3 and 8, there is some information on the forum.
Field Format (PS1)
PSX DAT Format
The PSX script is contained in the DAT file, it is compressed with LZS compression.
The header for the DAT file (after it is decompressed), is 28 bytes in size (they are used in the PSX, it's a list of 7 long word values which point to locations in PSX RAM). So for each of these sections are addressable by taking the first memory location subtracting it and adding 28.
There are 7 sections each coresponding to the first 7 memory locations at the begining of the file.
Section Name | Section Information |
---|---|
Script | Contains conversations, save point interaction etc. |
Walkmesh | Contains walkmesh triangles and access info. |
TileMap | Contains the information for the background, animation, and static scene objects. |
Camera_Matrix | Contains camera info. |
Triggers | Contains triggers, singles, gateways and so on. |
Encounter | Battle Encounter information for location. |
Models | Some info about field models. |
PSX MIM Format
Part of the PSX background data is contained in the MIM file, it is compressed with LZS compression. It consists of palettes (256 color ones) and screen blocks. No data for locating the blocks on the screen is in this file. The MIM file is a truncated TIM file and contains the normal clut location height and width information. This information is directly loaded into the PSX video ram to be decoded by the field module.
PSX BSX Format
The Field models are contained in the BSX file, it is compressed with LZS compression. FIELD.TDB contains the textures for these models.
PSX BCX Format
The individual characters' field models are stored in BCX files. Their textures are also in FIELD.TDB; they are compressed with LZS compression.
Event Scripting
Event scripting is handled via a series of script commands and entities spawned for the event. The exception to this is the battle event scripting. This is actually a little bit different. Please refer to the Field Script for more information.
Script commands
The event scripting language for FF7 has 246 commands that have a wide array of functions. For a complete listing of the commands, opcodes, arguments and descriptions, please refer to the opcodes section.
Movies
Movies in FF7 are actually triggered from the Field Script. The F8 PMVIE opcode is first used to set the movie for which the F9 MOVIE opcode is used to play. It is important to remember the MOVIE ID may vary in the PS1 versionn depending on what disc you are on. The PC movies were encoded using the DUCK (goose?) format and are AVI video files.
The PS1 movies were encoded using FMV Motion JPEG video files, for the playstation. These files cannot be decode or read directly from the CD disc media because of the Mode 2 format of the files. The files are encoded using ISO Mode 2 which means the sectors are 2302 bytes in length instead of 2048. The video files have interleaved audio (ADPCM format), between video frames and are 320x224 15fps. Video files that have no audio with it actually has empty sectors of space between video frames to prevent the extremely timing sensitive MDEC decoder in the playstation from locking up.
Cyberman 14:18, 30 Dec 2006 (CST)
The 3D Overlay
Data Organization
"A" Field Animation Files for PC by Mirex (Edits by Aali)
Each animation file holds one character animation ( run, walk or some other). Some characters have more animation files. Animation is set of frames, in each frame are stored bone rotations.
-- animation file contents --
Name | Size in bytes |
---|---|
header | 36 |
frames | frames_count * frame |
-- one frame, size is (bones * 12 + 12 + 12) --
Name | Size |
---|---|
root rotation | 12 = 3 floats |
root translation | 12 = 3 floats |
rotations | bones * 12 bytes = bones * 3 floats |
header structure, 36 bytes
struct { unsigned int32 version; unsigned int32 frames_count; unsigned int32 bones_count; unsigned char rotation_order[3]; unsigned char unused; unsigned int32 runtime_data[5]; } anim_head;
I understand only two values from the header, 'frames_count' which is number of animation frames and 'bones_count' which is suprisingly number of animated bones.
version should always be 1 or FF7 will not load the file
rotation order determines in which order rotations are applied, 0 means alpha rotation, 1 beta rotation and 2 gamma rotation.
runtime data has no meaning in the animation file and is discarded on load
If you want to load all possible animations for the model (even animations of different models) then check if animation file has same number of bones as current model.
Frame starts with the root rotations and root translations, followed by rotations for each bone. Rotations are stored as 3 floats (float is 4byte floating-point number).