-
Notifications
You must be signed in to change notification settings - Fork 0
Game Objects Ships and Combat
The world is a fixed array of 400 pointers at DAT_00587CE0; each points to a separately
heap-allocated GO record of 0xB98 (2968) bytes (allocated in gameobj.cpp).
| Item | Value |
|---|---|
| pointer-table base | 0x00587CE0 |
| capacity | 400 (table end 0x00588320) |
| record size |
0xB98 bytes |
| high-water index | DAT_00539AA0 |
| player/AI count boundary | DAT_0058832C |
| MP/arcade-mode flag | DAT_00582E8C |
Confirmed record offsets:
| Offset | Field |
|---|---|
+0x00 |
object type id (< 0x100 = ships/weapons, geometry-backed; ≥ 0x100 = lightweight) |
+0x04 |
self index |
+0x08 |
flags (bit 0x20 = free slot, bit 0x400 = inactive) |
+0x10 |
→ per-type geometry/stat template &DAT_004FC670 (stride 0x30) |
+0x14 |
→ per-type template &DAT_004F9E70 (stride 0x28) |
+0x84 |
position (vec3) |
+0x59C |
bounding-sphere radius (float) |
+0x5E8 |
hull / health |
+0x640 / +0x644
|
AI vtable / behaviour id |
+0x684 |
current-AI pointer |
+0xB94 |
alive/in-use byte |
Lifecycle: FUN_00466630 initialises the table (marks all slots free); FUN_00475DD0 is the
constructor (gameobj.cpp); FUN_00466C10 is the factory (Create.cpp) — guards
"create object: Overrun in GO arr" (index ≤ 399) and "Trying to create object %s twice"
(+0xB94). Objects are destroyed by slot reuse (set free flag), not freed; iteration/collision
skip slots with flags & 0x420.
FUN_00441AA0 (loadout preloader) loads model assets in batches: each is a 0x14-byte
"OBJECT FILE" handle with the parsed .SHP at +0x0C, produced by the .SHP loader
FUN_004A44D0. It walks fixed-width name tables (ships USLF.prd.SHP stride 0x22C; missiles
stride 0x110; guns) and SetCurrentDirectorys into each asset folder. Assets are read as loose
files by name after install; the .HOG (EA BIGF) is the distribution container. Weapon meshes are
bound per weapon-type in FUN_0047D9A0.
All four loaders read with fread(buf, 0x160, 1, file) in a loop → 352-byte records, with a
64-byte name at +0x00 and stat fields beginning at +0x40. The 15 stat dwords are a mix
of float32 and __ftol-converted int32 (so "15 floats" is only partly right). The trailing
0x7C..0x160 is not read by the loaders (preserved tail).
| File | Loader | Fills |
|---|---|---|
shipstats.bin |
0x00466500 |
&DAT_004F9E74 (stride 10 dw) + &DAT_004FC678 (stride 0xC dw) — the same per-type templates the GO factory reads via +0x10/+0x14
|
gunstats.bin |
0x004788F0 |
&DAT_00500CE8 (stride 0xB dw) |
missilestats.bin |
0x00494BC0 |
&DAT_005035E8 (stride 0x28 B) |
pilotstats.bin |
0x0049CAE0 |
&DAT_0058A968 (stride 0x12 dw) |
The ship-stat → per-type-template → GO-factory link is now established: a record at table index
type is reached by type * 0x30 / type * 0x28.
| Addr | Role |
|---|---|
0x00468FA0 |
collision — sweep-and-prune on an axis, then narrow-phase squared-distance vs (r_a + r_b)² using position +0x84 and radius +0x59C; owner ids +0x618/+0x61C exclude self/parent. |
0x0049F790 |
shields (shield.cpp) — "Capshield mesh"; capital-ship shields are an 8-section mesh-mapped HP grid (per-slot table 0x58FB70, stride 0x3C). |
0x004A0310 |
shield-impact FX (shieldfx.cpp) — 12-byte hit-flash effect. |
0x0046BF20 / 0x0046D090
|
explosions (explode.cpp) — debris burst + named subsystem-debris meshes (e.g. Kras_l_eng_block) for component-level destruction. |
0x0040CA50 |
per-ship AI attach/detach — dispatch table &PTR_DAT_004E06E0 (stride 0x18: callback +8, priority +0x14, name +0x10); current AI at GO +0x684. |
0x0041FE60 / 0x0041DD70
|
jump/warp gates (wgate.cpp) — 0x88-byte gate record in a 32-slot table 0x51D1A4; procedurally generates the ring/tunnel mesh with sin/cos. |