Add some start for Evp Data.

This commit is contained in:
Ottermandias 2022-09-02 18:36:34 +02:00
parent 8aec63d0be
commit 2010e02034
4 changed files with 128 additions and 60 deletions

View file

@ -1,4 +1,3 @@
using System;
using System.IO; using System.IO;
using System.Linq; using System.Linq;
using System.Text; using System.Text;

View file

@ -9,23 +9,23 @@ namespace Penumbra.GameData.Structs;
[Flags] [Flags]
public enum EqpEntry : ulong public enum EqpEntry : ulong
{ {
BodyEnabled = 0x00_01ul, BodyEnabled = 0x00_01ul,
BodyHideWaist = 0x00_02ul, BodyHideWaist = 0x00_02ul,
BodyHideThighs = 0x00_04ul, BodyHideThighs = 0x00_04ul,
BodyHideGlovesS = 0x00_08ul, BodyHideGlovesS = 0x00_08ul,
_4 = 0x00_10ul, _4 = 0x00_10ul,
BodyHideGlovesM = 0x00_20ul, BodyHideGlovesM = 0x00_20ul,
BodyHideGlovesL = 0x00_40ul, BodyHideGlovesL = 0x00_40ul,
BodyHideGorget = 0x00_80ul, BodyHideGorget = 0x00_80ul,
BodyShowLeg = 0x01_00ul, BodyShowLeg = 0x01_00ul,
BodyShowHand = 0x02_00ul, BodyShowHand = 0x02_00ul,
BodyShowHead = 0x04_00ul, BodyShowHead = 0x04_00ul,
BodyShowNecklace = 0x08_00ul, BodyShowNecklace = 0x08_00ul,
BodyShowBracelet = 0x10_00ul, BodyShowBracelet = 0x10_00ul,
BodyShowTail = 0x20_00ul, BodyShowTail = 0x20_00ul,
DisableBreastPhysics = 0x40_00ul, BodyDisableBreastPhysics = 0x40_00ul,
_15 = 0x80_00ul, BodyHasVfxObject = 0x80_00ul,
BodyMask = 0xFF_FFul, BodyMask = 0xFF_FFul,
LegsEnabled = 0x01ul << 16, LegsEnabled = 0x01ul << 16,
LegsHideKneePads = 0x02ul << 16, LegsHideKneePads = 0x02ul << 16,
@ -75,7 +75,7 @@ public enum EqpEntry : ulong
_55 = 0x00_80_00ul << 40, _55 = 0x00_80_00ul << 40,
HeadShowHrothgarHat = 0x01_00_00ul << 40, HeadShowHrothgarHat = 0x01_00_00ul << 40,
HeadShowVieraHat = 0x02_00_00ul << 40, HeadShowVieraHat = 0x02_00_00ul << 40,
_58 = 0x04_00_00ul << 40, HeadHasVfxObject = 0x04_00_00ul << 40,
_59 = 0x08_00_00ul << 40, _59 = 0x08_00_00ul << 40,
_60 = 0x10_00_00ul << 40, _60 = 0x10_00_00ul << 40,
_61 = 0x20_00_00ul << 40, _61 = 0x20_00_00ul << 40,
@ -136,22 +136,22 @@ public static class Eqp
{ {
return entry switch return entry switch
{ {
EqpEntry.BodyEnabled => EquipSlot.Body, EqpEntry.BodyEnabled => EquipSlot.Body,
EqpEntry.BodyHideWaist => EquipSlot.Body, EqpEntry.BodyHideWaist => EquipSlot.Body,
EqpEntry.BodyHideThighs => EquipSlot.Body, EqpEntry.BodyHideThighs => EquipSlot.Body,
EqpEntry.BodyHideGlovesS => EquipSlot.Body, EqpEntry.BodyHideGlovesS => EquipSlot.Body,
EqpEntry._4 => EquipSlot.Body, EqpEntry._4 => EquipSlot.Body,
EqpEntry.BodyHideGlovesM => EquipSlot.Body, EqpEntry.BodyHideGlovesM => EquipSlot.Body,
EqpEntry.BodyHideGlovesL => EquipSlot.Body, EqpEntry.BodyHideGlovesL => EquipSlot.Body,
EqpEntry.BodyHideGorget => EquipSlot.Body, EqpEntry.BodyHideGorget => EquipSlot.Body,
EqpEntry.BodyShowLeg => EquipSlot.Body, EqpEntry.BodyShowLeg => EquipSlot.Body,
EqpEntry.BodyShowHand => EquipSlot.Body, EqpEntry.BodyShowHand => EquipSlot.Body,
EqpEntry.BodyShowHead => EquipSlot.Body, EqpEntry.BodyShowHead => EquipSlot.Body,
EqpEntry.BodyShowNecklace => EquipSlot.Body, EqpEntry.BodyShowNecklace => EquipSlot.Body,
EqpEntry.BodyShowBracelet => EquipSlot.Body, EqpEntry.BodyShowBracelet => EquipSlot.Body,
EqpEntry.BodyShowTail => EquipSlot.Body, EqpEntry.BodyShowTail => EquipSlot.Body,
EqpEntry.DisableBreastPhysics => EquipSlot.Body, EqpEntry.BodyDisableBreastPhysics => EquipSlot.Body,
EqpEntry._15 => EquipSlot.Body, EqpEntry.BodyHasVfxObject => EquipSlot.Body,
EqpEntry.LegsEnabled => EquipSlot.Legs, EqpEntry.LegsEnabled => EquipSlot.Legs,
EqpEntry.LegsHideKneePads => EquipSlot.Legs, EqpEntry.LegsHideKneePads => EquipSlot.Legs,
@ -198,9 +198,9 @@ public static class Eqp
EqpEntry._55 => EquipSlot.Head, EqpEntry._55 => EquipSlot.Head,
EqpEntry.HeadShowHrothgarHat => EquipSlot.Head, EqpEntry.HeadShowHrothgarHat => EquipSlot.Head,
EqpEntry.HeadShowVieraHat => EquipSlot.Head, EqpEntry.HeadShowVieraHat => EquipSlot.Head,
EqpEntry.HeadHasVfxObject => EquipSlot.Head,
// Currently unused. // currently unused
EqpEntry._58 => EquipSlot.Unknown,
EqpEntry._59 => EquipSlot.Unknown, EqpEntry._59 => EquipSlot.Unknown,
EqpEntry._60 => EquipSlot.Unknown, EqpEntry._60 => EquipSlot.Unknown,
EqpEntry._61 => EquipSlot.Unknown, EqpEntry._61 => EquipSlot.Unknown,
@ -215,22 +215,22 @@ public static class Eqp
{ {
return entry switch return entry switch
{ {
EqpEntry.BodyEnabled => "Enabled", EqpEntry.BodyEnabled => "Enabled",
EqpEntry.BodyHideWaist => "Hide Waist", EqpEntry.BodyHideWaist => "Hide Waist",
EqpEntry.BodyHideThighs => "Hide Thigh Pads", EqpEntry.BodyHideThighs => "Hide Thigh Pads",
EqpEntry.BodyHideGlovesS => "Hide Small Gloves", EqpEntry.BodyHideGlovesS => "Hide Small Gloves",
EqpEntry._4 => "Unknown 4", EqpEntry._4 => "Unknown 4",
EqpEntry.BodyHideGlovesM => "Hide Medium Gloves", EqpEntry.BodyHideGlovesM => "Hide Medium Gloves",
EqpEntry.BodyHideGlovesL => "Hide Large Gloves", EqpEntry.BodyHideGlovesL => "Hide Large Gloves",
EqpEntry.BodyHideGorget => "Hide Gorget", EqpEntry.BodyHideGorget => "Hide Gorget",
EqpEntry.BodyShowLeg => "Show Legs", EqpEntry.BodyShowLeg => "Show Legs",
EqpEntry.BodyShowHand => "Show Hands", EqpEntry.BodyShowHand => "Show Hands",
EqpEntry.BodyShowHead => "Show Head", EqpEntry.BodyShowHead => "Show Head",
EqpEntry.BodyShowNecklace => "Show Necklace", EqpEntry.BodyShowNecklace => "Show Necklace",
EqpEntry.BodyShowBracelet => "Show Bracelet", EqpEntry.BodyShowBracelet => "Show Bracelet",
EqpEntry.BodyShowTail => "Show Tail", EqpEntry.BodyShowTail => "Show Tail",
EqpEntry.DisableBreastPhysics => "Disable Breast Physics", EqpEntry.BodyDisableBreastPhysics => "Disable Breast Physics",
EqpEntry._15 => "Unknown 15", EqpEntry.BodyHasVfxObject => "Has Special Effects",
EqpEntry.LegsEnabled => "Enabled", EqpEntry.LegsEnabled => "Enabled",
EqpEntry.LegsHideKneePads => "Hide Knee Pads", EqpEntry.LegsHideKneePads => "Hide Knee Pads",
@ -277,12 +277,13 @@ public static class Eqp
EqpEntry._55 => "Unknown 55", EqpEntry._55 => "Unknown 55",
EqpEntry.HeadShowHrothgarHat => "Show on Hrothgar", EqpEntry.HeadShowHrothgarHat => "Show on Hrothgar",
EqpEntry.HeadShowVieraHat => "Show on Viera", EqpEntry.HeadShowVieraHat => "Show on Viera",
EqpEntry._58 => "Unknown 58", EqpEntry.HeadHasVfxObject => "Has Special Effects",
EqpEntry._59 => "Unknown 59",
EqpEntry._60 => "Unknown 60", EqpEntry._59 => "Unknown 59",
EqpEntry._61 => "Unknown 61", EqpEntry._60 => "Unknown 60",
EqpEntry._62 => "Unknown 62", EqpEntry._61 => "Unknown 61",
EqpEntry._63 => "Unknown 63", EqpEntry._62 => "Unknown 62",
EqpEntry._63 => "Unknown 63",
_ => throw new InvalidEnumArgumentException(), _ => throw new InvalidEnumArgumentException(),
}; };

View file

@ -0,0 +1,68 @@
using System;
namespace Penumbra.Meta.Files;
// EVP file structure:
// [Identifier:3 bytes, EVP]
// [NumModels:ushort]
// NumModels x [ModelId:ushort]
// Containing the relevant model IDs. Seems to be sorted.
// NumModels x [DataArray]:512 Byte]
// Containing Flags in each byte, 0x01 set for Body, 0x02 set for Helmet. Unsure where the index into this array comes from.
public unsafe class EvpFile : MetaBaseFile
{
public const int FlagArraySize = 512;
[Flags]
public enum EvpFlag : byte
{
None = 0x00,
Body = 0x01,
Head = 0x02,
Both = Body | Head,
}
public int NumModels
=> Data[ 3 ];
public ReadOnlySpan< ushort > ModelSetIds
=> new(Data + 4, NumModels);
public ushort ModelSetId( int idx )
=> idx >= 0 && idx < NumModels ? ( ( ushort* )( Data + 4 ) )[ idx ] : ushort.MaxValue;
public ReadOnlySpan< EvpFlag > Flags( int idx )
=> new(Data + 4 + idx * FlagArraySize, FlagArraySize);
public EvpFlag Flag( ushort modelSet, int arrayIndex )
{
if( arrayIndex is >= FlagArraySize or < 0 )
{
return EvpFlag.None;
}
var ids = ModelSetIds;
for( var i = 0; i < ids.Length; ++i )
{
var model = ids[ i ];
if( model < modelSet )
{
continue;
}
if( model > modelSet )
{
break;
}
return Flags( i )[ arrayIndex ];
}
return EvpFlag.None;
}
public EvpFile()
: base( ( Interop.Structs.CharacterUtility.Index )1 ) // TODO: Name
{ }
}

View file

@ -12,7 +12,7 @@ public unsafe class MetaBaseFile : IDisposable
public CharacterUtility.InternalIndex Index { get; } public CharacterUtility.InternalIndex Index { get; }
public MetaBaseFile( Interop.Structs.CharacterUtility.Index idx ) public MetaBaseFile( Interop.Structs.CharacterUtility.Index idx )
=> Index = CharacterUtility.ReverseIndices[(int) idx]; => Index = CharacterUtility.ReverseIndices[ ( int )idx ];
protected (IntPtr Data, int Length) DefaultData protected (IntPtr Data, int Length) DefaultData
=> Penumbra.CharacterUtility.DefaultResource( Index ); => Penumbra.CharacterUtility.DefaultResource( Index );