Difference between revisions of "Skin PLG (RW Section)"

From GTAMods Wiki
Jump to navigation Jump to search
m
Line 31: Line 31:
 
Next, a list of transformation matrices for each bone is provided:
 
Next, a list of transformation matrices for each bone is provided:
  
  Xb - RpBone[numBones]      - Bone transformations
+
  Xb - Bone[numBones]      - Bone transformations
  
Where RpBone is defined as follows:
+
Where <code>Bone</code> is defined as follows:
  
 
<source lang="c">
 
<source lang="c">
struct RpBone {
+
struct Bone {
 
     DWORD unused;            // Only stored if version < 0x37000 && maxVertexWeights == 0
 
     DWORD unused;            // Only stored if version < 0x37000 && maxVertexWeights == 0
 
     FLOAT transform[4][4];  // Skin-to-Bone transform.
 
     FLOAT transform[4][4];  // Skin-to-Bone transform.
Line 42: Line 42:
 
</source>
 
</source>
  
=== Run-Length Encoding (RLE) ===
+
=== Bone Group Remapping ===
  
The skin skin may be followed by a [https://en.wikipedia.org/wiki/Run-length_encoding run-length encoded] list of index mappings:
+
As indicated above by the <code>usedBones</code> counter, a mesh (stored within the parent [[Geometry (RW Section)|geometry]]) may not affected by all bones in the skeleton. Some platforms only support a certain number of bones at once. Thus RenderWare can split up a skeleton into groups, where group-indices must be mapped to the actual bone indices. Those groups are stored in a [https://en.wikipedia.org/wiki/Run-length_encoding run-length encoded] fashion.
  
// Split data
+
For all RenderWare-based GTA games, this feature is typically unused. Thus the following values are usually set to zero.
UINT32  boneLimit
 
UINT32  numMeshes
 
UINT32  numRLE
 
  
  #if numMeshes > 0
+
  4b - DWORD  - boneLimit: the maximum number of bones per group. (?)
  UINT8  meshBoneRemapIndices[numBones]
+
4b - DWORD  - numGroups: the number of bone groups.
  UINT16  meshBoneRLECount[numMeshes]
+
4b - DWORD  - numRemaps: the number of bone remappings.
  UINT16  meshBoneRLE[numRLE]
+
 
#endif
+
If there are any groups (<code>numGroups > 0</code>), the counters are followed by three arrays:
 +
 
 +
  Xb - BYTE[numBones]           - boneRemapIndices: an array of all bone indices where each element identifies a bone of the skeleton
 +
  Xb - BoneGroup[numMeshes]     - boneGroups (see below)
 +
  Xb - BoneRemap[numBoneRemaps] - boneRemaps (see below)
 +
 
 +
Where <code>BoneGroup</code> and <code>BoneRemap</code> is defined as follows:
 +
 
 +
<source lang="c">
 +
struct BoneGroup {
 +
    BYTE firstBone;            // Index of first bone in boneRemaps array.
 +
    BYTE numBones;            // Number of bones in boneRemaps that define the mesh (starting from firstBone).
 +
};
 +
 
 +
struct BoneRemap {
 +
    BYTE boneIndex;            // Index of the bone in boneRemapIndices.
 +
    BYTE indices;              // The number of elements of the boneRemapIndices that are included by the group in boneRemapIndices.
 +
};
 +
</source>
  
 
== See also ==
 
== See also ==

Revision as of 10:35, 13 September 2020

40px-Ambox rewrite orange.svg.png This article may need to be rewritten.
Please help improve this article. The discussion page may contain suggestions.
Skin PLG
RenderWare Stream Section
Vendor Criterion Games
Module Toolkit
Module ID 0x000001
Identifier 0x16
Chunk ID 0x00000116
Versions All
Hierarchy
Parents:
Geometry (Extension)
Children:
None
Extensions:
None
File Format

Skin is an additional RenderWare plugin for geometry section. It is used to hold information about skinned model.

Structure

The structure starts with a 4-byte value, where each individual byte contains a counter and the last byte being used for padding.

1b - BYTE - numBones: Overall number of bones in the skeleton.
1b - BYTE - usedBones: Number of bones affected by the skin.
1b - BYTE - maxVertexWeights: Maximum number of non-zero weights per vertex.
1b - BYTE - Padding

The third counter can be any value from 0 to 4. If it equals zero, the engine attempts to figure out this number by looking into each weight array (see below) and counting the non-zero weights. It then takes the largest number from the results.

The counters are followed by multiple arrays that contain information about how vertices of a mesh relate to bones. The number of vertices is obtained from the parent geometry section.

Xb - BYTE[usedBones]       - A list of bone indices, that are affected by the skin.
Xb - BYTE[numVertices][4]  - A list that maps all vertices to (up to) four bones of the skeleton.
Xb - FLOAT[numVertices]    - A list that weights each vertex-bone mapping.

Next, a list of transformation matrices for each bone is provided:

Xb - Bone[numBones]      - Bone transformations

Where Bone is defined as follows:

struct Bone {
    DWORD unused;            // Only stored if version < 0x37000 && maxVertexWeights == 0
    FLOAT transform[4][4];   // Skin-to-Bone transform.
};

Bone Group Remapping

As indicated above by the usedBones counter, a mesh (stored within the parent geometry) may not affected by all bones in the skeleton. Some platforms only support a certain number of bones at once. Thus RenderWare can split up a skeleton into groups, where group-indices must be mapped to the actual bone indices. Those groups are stored in a run-length encoded fashion.

For all RenderWare-based GTA games, this feature is typically unused. Thus the following values are usually set to zero.

4b - DWORD  - boneLimit: the maximum number of bones per group. (?)
4b - DWORD  - numGroups: the number of bone groups.
4b - DWORD  - numRemaps: the number of bone remappings.

If there are any groups (numGroups > 0), the counters are followed by three arrays:

Xb - BYTE[numBones]           - boneRemapIndices: an array of all bone indices where each element identifies a bone of the skeleton
Xb - BoneGroup[numMeshes]     - boneGroups (see below)
Xb - BoneRemap[numBoneRemaps] - boneRemaps (see below)

Where BoneGroup and BoneRemap is defined as follows:

struct BoneGroup {
    BYTE firstBone;            // Index of first bone in boneRemaps array.
    BYTE numBones;             // Number of bones in boneRemaps that define the mesh (starting from firstBone).
};

struct BoneRemap {
    BYTE boneIndex;            // Index of the bone in boneRemapIndices.
    BYTE indices;              // The number of elements of the boneRemapIndices that are included by the group in boneRemapIndices.
};

See also