diff --git a/d2app/initialization.go b/d2app/initialization.go index 0828cfc0..d84d39a3 100644 --- a/d2app/initialization.go +++ b/d2app/initialization.go @@ -6,7 +6,7 @@ import ( "github.com/OpenDiablo2/OpenDiablo2/d2common/d2loader/asset/types" - "github.com/OpenDiablo2/OpenDiablo2/d2common/d2data" + "github.com/OpenDiablo2/OpenDiablo2/d2common/d2fileformats/d2animdata" "github.com/OpenDiablo2/OpenDiablo2/d2common/d2resource" "github.com/OpenDiablo2/OpenDiablo2/d2common/d2util" "github.com/OpenDiablo2/OpenDiablo2/d2core/d2config" @@ -150,12 +150,12 @@ func (a *App) initAnimationData(path string) error { a.Debugf(fmtLoadAnimData, path) - animData, err := d2data.LoadAnimationData(animDataBytes) + animData, err := d2animdata.Load(animDataBytes) if err != nil { a.Error(err.Error()) } - a.Infof("Loaded %d animation data records", len(animData)) + a.Infof("Loaded %d animation data records", animData.GetRecordsCount()) a.asset.Records.Animation.Data = animData diff --git a/d2common/d2data/animation_data.go b/d2common/d2data/animation_data.go deleted file mode 100644 index 2dc73bc2..00000000 --- a/d2common/d2data/animation_data.go +++ /dev/null @@ -1,83 +0,0 @@ -package d2data - -import ( - "strings" - - "github.com/OpenDiablo2/OpenDiablo2/d2common/d2datautils" -) - -const ( - numCofNameBytes = 8 - numFlagBytes = 144 -) - -// AnimationDataRecord represents a single entry in the animation data dictionary file -type AnimationDataRecord struct { - // COFName is the name of the COF file used for this animation - COFName string - // FramesPerDirection specifies how many frames are in each direction - FramesPerDirection int - // AnimationSpeed represents a value of X where the rate is a ration of (x/255) at 25FPS - AnimationSpeed int - // Flags are used in keyframe triggers - Flags []byte -} - -// AnimationData represents all of the animation data records, mapped by the COF index -type AnimationData map[string][]*AnimationDataRecord - -// LoadAnimationData loads the animation data table into the global AnimationData dictionary -func LoadAnimationData(rawData []byte) (AnimationData, error) { - animdata := make(AnimationData) - streamReader := d2datautils.CreateStreamReader(rawData) - - for !streamReader.EOF() { - var dataCount int - - b, err := streamReader.ReadInt32() - if err != nil { - return nil, err - } - - dataCount = int(b) - - for i := 0; i < dataCount; i++ { - cofNameBytes, err := streamReader.ReadBytes(numCofNameBytes) - if err != nil { - return nil, err - } - - fpd, err := streamReader.ReadInt32() - if err != nil { - return nil, err - } - - animSpeed, err := streamReader.ReadInt32() - if err != nil { - return nil, err - } - - data := &AnimationDataRecord{ - COFName: strings.ReplaceAll(string(cofNameBytes), string(byte(0)), ""), - FramesPerDirection: int(fpd), - AnimationSpeed: int(animSpeed), - } - - flagBytes, err := streamReader.ReadBytes(numFlagBytes) - if err != nil { - return nil, err - } - - data.Flags = flagBytes - cofIndex := strings.ToLower(data.COFName) - - if _, found := animdata[cofIndex]; !found { - animdata[cofIndex] = make([]*AnimationDataRecord, 0) - } - - animdata[cofIndex] = append(animdata[cofIndex], data) - } - } - - return animdata, nil -} diff --git a/d2common/d2fileformats/d2animdata/animdata.go b/d2common/d2fileformats/d2animdata/animdata.go index 65b23859..2f74e5de 100644 --- a/d2common/d2fileformats/d2animdata/animdata.go +++ b/d2common/d2fileformats/d2animdata/animdata.go @@ -56,6 +56,10 @@ func (ad *AnimationData) GetRecords(name string) []*AnimationDataRecord { return ad.entries[name] } +func (ad *AnimationData) GetRecordsCount() int { + return len(ad.entries) +} + // Load loads the data into an AnimationData struct //nolint:gocognit,funlen // can't reduce func Load(data []byte) (*AnimationData, error) { diff --git a/d2common/d2fileformats/d2animdata/record.go b/d2common/d2fileformats/d2animdata/record.go index 9d165efa..da7ce0b1 100644 --- a/d2common/d2fileformats/d2animdata/record.go +++ b/d2common/d2fileformats/d2animdata/record.go @@ -8,6 +8,14 @@ type AnimationDataRecord struct { events map[int]AnimationEvent } +func (r *AnimationDataRecord) FramesPerDirection() int { + return int(r.framesPerDirection) +} + +func (r *AnimationDataRecord) Speed() int { + return int(r.speed) +} + // FPS returns the frames per second for this animation record func (r *AnimationDataRecord) FPS() float64 { speedf := float64(r.speed) diff --git a/d2core/d2asset/composite.go b/d2core/d2asset/composite.go index 73ebf663..cd861cef 100644 --- a/d2core/d2asset/composite.go +++ b/d2core/d2asset/composite.go @@ -265,9 +265,9 @@ func (c *Composite) createMode(animationMode animationMode, weaponClass string) return nil, err } - animationKey := strings.ToLower(c.token + animationMode.String() + weaponClass) + animationKey := strings.ToUpper(c.token + animationMode.String() + weaponClass) - animationData := c.Records.Animation.Data[animationKey] + animationData := c.Records.Animation.Data.GetRecords(animationKey) if len(animationData) == 0 { return nil, errors.New("could not find Animation data") } @@ -277,8 +277,8 @@ func (c *Composite) createMode(animationMode animationMode, weaponClass string) animationMode: animationMode, weaponClass: weaponClass, layers: make([]d2interface.Animation, d2enum.CompositeTypeMax), - frameCount: animationData[0].FramesPerDirection, - animationSpeed: 1.0 / (float64(animationData[0].AnimationSpeed) * speedUnit), //nolint:gomnd // taking inverse + frameCount: animationData[0].FramesPerDirection(), + animationSpeed: 1.0 / (float64(animationData[0].Speed()) * speedUnit), //nolint:gomnd // taking inverse } for _, cofLayer := range cof.CofLayers { diff --git a/d2core/d2map/d2mapentity/factory.go b/d2core/d2map/d2mapentity/factory.go index 181b05c2..8e5936bc 100644 --- a/d2core/d2map/d2mapentity/factory.go +++ b/d2core/d2map/d2mapentity/factory.go @@ -108,8 +108,8 @@ func (f *MapEntityFactory) NewPlayer(id, name string, x, y, direction int, heroT result.mapEntity.uuid = id result.SetSpeed(baseWalkSpeed) result.mapEntity.directioner = result.rotate - err = composite.SetMode(d2enum.PlayerAnimationModeTownNeutral, equipment.RightHand.GetWeaponClass()) + err = composite.SetMode(d2enum.PlayerAnimationModeTownNeutral, equipment.RightHand.GetWeaponClass()) if err != nil { panic(err) } diff --git a/d2core/d2records/record_manager.go b/d2core/d2records/record_manager.go index 8afba41c..b24088a6 100644 --- a/d2core/d2records/record_manager.go +++ b/d2core/d2records/record_manager.go @@ -5,9 +5,8 @@ import ( "github.com/OpenDiablo2/OpenDiablo2/d2common/d2util" - "github.com/OpenDiablo2/OpenDiablo2/d2common/d2data" - "github.com/OpenDiablo2/OpenDiablo2/d2common/d2enum" + "github.com/OpenDiablo2/OpenDiablo2/d2common/d2fileformats/d2animdata" "github.com/OpenDiablo2/OpenDiablo2/d2common/d2fileformats/d2txt" "github.com/OpenDiablo2/OpenDiablo2/d2common/d2resource" ) @@ -39,7 +38,7 @@ type RecordManager struct { *d2util.Logger boundLoaders map[string][]recordLoader // there can be more than one loader bound for a file Animation struct { - Data d2data.AnimationData + Data *d2animdata.AnimationData Token struct { Player PlayerTypes Composite CompositeTypes