MDB Format

This Wiki describes the MDB file format for Neverwinter Nights 2 as it is currently understood. It is the primary file format for representing 3d objects in the game.

File Header
All MDB files begin with a header that has a unique signature as well as version information and a list of the available packets. The available packet list hold references what kind of data is in the file and where it is located from the start of the file.

MDBHeader
A simple header block which has the version of the file and the available packets.

MDBPacketKey
The packet key holds the type of packet and the location within the file where that packet begins.

Packets
Virtually all of the useful information held in the MDB file is contained in packets or blobs of data. The header of the file contains the version and a list of the available packets and where they are in the file. The packets are identified by a 4 character signature and always hold the size of the packet.

MDBPacket
Packets always begin with a block indication type of packet it is and how large the packet is. The total size does not include the packet signature and size itself.

TRI
The Triangle structure is commonly used in the mesh formats and holds the indices of the vertices that define a face on the mesh.

RIGD
Rigid bodies are the staple of the MDL format and are the primary format for all static objects. These objects cannot change shape in the game.

Any mesh can be exported as a RIGD object which includes the mesh as well as the materials and texture maps. You are limited to 65535 vertices but really should only have between 1000 - 10000 max for good performance. Note: Due to the way textures and normals are exported, meshes may end up with more vertices than the modelling program indicates.

RVERT – Rigid Body Vertex
The Rigid Body vertex holds all of the information related to a specific vertex in a rigid body mesh including its position the normal tangent and binormal directions and the texture position.

Skinned Body
Skinned bodies are rigid bodies that are rigged so that they can deform when the underlying skeleton is moved.

SKIN
Skinned objects like those used for creatures are SKIN objects. These are usually bound to a skeleton and this structure holds the weights as well as the vertices for a mesh. The bones for the skeleton which are what are normally animated are not held in the MDB file but in the GR2 file which is a format from the Granny product from RadTools.

SVERT - Skin Vertex
The Skin vertex structure is similar to the Rigid Body vertex but has additional regarding which bones can deform the mesh and the weight for that bone. The sum of all of the bone weights must be 1.

Collision Mesh
Skinned bodies are rigid bodies that are rigged so that they can deform when the underlying skeleton is moved.

COL2
These seem to be less detailed collision meshes. And do not tightly conform to the model. We dont really know the difference between COL2 and COL3 at this time. The naming convention used by Obsidian is to append _C2 to name to COL2 type meshes. This naming convention makes it convenient for tool authors to export these meshes.

Materials do not really seem to be used and is probably there just to make it easier to share code between RIGD, SKIN, COL2, COL3, and WALK packets.

COL3
These seem to be more detailed collision and conform more closely to the model. We dont really know the difference between COL2 and COL3 at this time. The naming convention used by Obsidian is to append _C2 to name to COL2 type meshes. This naming convention makes it convenient for tool authors to export these meshes.

Materials do not really seem to be used and is probably there just to make it easier to share code between RIGD, SKIN, COL2, COL3, and WALK packets.

CVERT
The collision vertex holds the information for position and normals. Again the Normal and UVW do not really seem to be used at this time.

COLS
The COLS packet appears to be collision spheres for animated objects. Spheres are one of the best objects to use for collision detection due to the simplicity of the tests involving it. This structure appears to reference bones of the skeleton for skinned meshes.

COLSITM
The Collision Sphere item appears to be a bone index to sphere radius map but am not completely certain about it at this time.

Walk Mesh
Walk meshes define where characters may walk and where they cannot. There are parts of the format that are not well understood which probably effect things like material/sounds to be played when walking on meshes.

WALK
Walk meshes seem to control where you can walk and where you cannot.

Some vertices have unusual values like -1,000,000 to indicate a link to other walk meshes or perhaps non-navigable terrain. In 3d Studio Max, you probably want to use Quad/Tri Patches to create these. The Faces on a Walk mesh have a flag that is unknown and we currently default to 0x21 (33). The naming convension for these meshes is to append _W to the name.

WTRI
The Walk mesh triangle structure is used in the walk mesh format to holds the indices of the vertices that define a face on the mesh. It also has unknown value that seems important but is still unknown.

Hook Points
Hook points appear to have a number of purposes within the game. Its primary purpose seems to hold the position for doors and indirectly the direction that the door will swing when opened.

HookPointSize
HookPointSize was found in the .NET assemblies but it ’ s still in question whether it ’ s actually used in the MDB format since this enumeration is not used in the .NET code.

enum HookPointSize : uint16

{

StandardDoor,

LargeDoor,

GateDoor

}

HookPointType
HookPointType was found in the .NET assemblies but it ’ s still in question whether it ’ s actually used in the MDB format since this enumeration is not used in the .NET code.

enum HookPointType : uint16

{

Door,

Accessory,

None

}

HOOK
Hook points are used to attach doors and accessories to a RIGD mesh. For doors, orient the point so that the Z is the hinge axis the door will swing on. Doors swinging inward would rotate from Y to X axis. The naming convension for hook points is that it begins with "hp_" is then is followed by a number starting with 1.

Hair and Helm Points
Hair and Helm points seem to control how helmets and other items cover or don ’ t cover hair when equipped.

MDBHairShorteningBehavior
Flag that controls the shortening behavior of the hair.

enum MDBHairShorteningBehavior : uint32

{

HSB_LOW,

HSB_SHORT,

HSB_PONYTAIL

}

HAIR
Hair obviously represents hair on a character. It ’ s not a mesh but rather a point that holds the hair shortening behavior flag. The Position and Orientation does not seem to matter terribly. The naming convention holds that the name contains "XX?_Hair" within the name. The first two characters are creature specific and the question mark is either M or F for male or female hair.

MDBHelmHairHidingBehavior
enum MDBHelmHairHidingBehavior : uint32

{

HHHB_NONE_HIDDEN,

HHHB_HAIR_HIDDEN,

HHHB_PARTIAL_HAIR,

HHHB_HEAD_HIDDEN

}

HELM
Helm obviously represents helmets on a character. It ’ s not a mesh but rather a point that holds the hair hiding behavior flag. The Position and Orientation does not seem to matter terribly. The naming convention holds that the name contains "XX?_Helm" within the name. The first two characters are item specific and the question mark is either M or F for male or female hair.

Point3
This is a fairly standard structure for holding 3-dimensional coordinates. Could be an array or individual x,y,z float values depending your preference.

Color3
This is a fairly standard structure for holding color information as a float that usually ranges from 0 to 1.

Quat
Quaternions are a fairly compact way to represent rotation of an object and still have good performace. All rotations are assumed to be right-handed.

RHMatrix
RHMatrix represents a right-handed rotation matrix. Scale information can also be saved in the matrix but have not encountered that in the game yet.

Material
The material data type holds information regarding the texture maps, color and shininess of an object. Most of the major mesh types have a material regardless of whether the mesh will be seen (like in collision meshes.)