Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 8 additions & 8 deletions data/file_list.yml
Original file line number Diff line number Diff line change
Expand Up @@ -288853,37 +288853,37 @@ Project/Anim/AnimInfo.o:
label:
- _ZN2al11AnimResInfoC1Ev
- _ZN2al11AnimResInfoC2Ev
status: NotDecompiled
status: Matching
- offset: 0xa3b85c
size: 12
label: _ZNK2al11AnimResInfo11getFrameMaxEv
status: NotDecompiled
status: Matching
- offset: 0xa3b868
size: 8
label: _ZNK2al11AnimResInfo6isLoopEv
status: NotDecompiled
status: Matching
- offset: 0xa3b870
size: 116
label:
- _ZN2al13AnimInfoTableC1Ei
- _ZN2al13AnimInfoTableC2Ei
status: NotDecompiled
status: Matching
- offset: 0xa3b8e4
size: 116
label: _ZN2al13AnimInfoTable3addEPKcPvfb
status: NotDecompiled
status: Matching
- offset: 0xa3b958
size: 224
label: _ZNK2al13AnimInfoTable12findAnimInfoEPKc
status: NotDecompiled
status: Matching
- offset: 0xa3ba38
size: 224
label: _ZNK2al13AnimInfoTable15tryFindAnimInfoEPKc
status: NotDecompiled
status: NonMatchingMajor
- offset: 0xa3bb18
size: 564
label: _ZN2al13AnimInfoTable4sortEv
status: NotDecompiled
status: Matching
Project/Anim/AnimPlayerSimple.o:
'.text':
- offset: 0xa3bd4c
Expand Down
15 changes: 7 additions & 8 deletions lib/al/Project/Action/InitResourceDataActionAnim.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -123,17 +123,16 @@ const al::AnimInfoTable* createAnimInfoTableIfNeed(const al::AnimInfoTable* tabl
if (table1 == table2 || !table2)
return table1;

al::AnimInfoTable* newTable =
new al::AnimInfoTable(table1->getInfoCount() + table2->getInfoCount());
al::AnimInfoTable* newTable = new al::AnimInfoTable(table1->getSize() + table2->getSize());

for (s32 i = 0; i < table1->getInfoCount(); i++) {
const al::AnimResInfo& entry = table1->getResInfo(i);
newTable->add(entry.name, entry.resMaterialAnim, entry.frameMax, entry.isLoop);
for (s32 i = 0; i < table1->getSize(); i++) {
const al::AnimResInfo& entry = table1->getAnimInfo(i);
newTable->add(entry.name, entry.buffer, entry.frameMax, entry.isLooping);
}

for (s32 i = 0; i < table2->getInfoCount(); i++) {
const al::AnimResInfo& entry = table2->getResInfo(i);
newTable->add(entry.name, entry.resMaterialAnim, entry.frameMax, entry.isLoop);
for (s32 i = 0; i < table2->getSize(); i++) {
const al::AnimResInfo& entry = table2->getAnimInfo(i);
newTable->add(entry.name, entry.buffer, entry.frameMax, entry.isLooping);
}

newTable->sort();
Expand Down
121 changes: 121 additions & 0 deletions lib/al/Project/Anim/AnimInfo.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,121 @@
#include "Project/Anim/AnimInfo.h"

#include "Library/Base/StringUtil.h"

namespace al {

AnimResInfo::AnimResInfo() = default;

s32 AnimResInfo::getFrameMax() const {
return static_cast<s32>(frameMax);
}

bool AnimResInfo::isLoop() const {
return isLooping;
}

AnimInfoTable::AnimInfoTable(s32 capacity) {
mInfoEntries = new AnimResInfo[capacity];
}

void AnimInfoTable::add(const char* name, void* buffer, f32 frameMax, bool isLoop) {
// BUG: Is sorted flag is not cleared and no bounds check
AnimResInfo* info = &mInfoEntries[mSize];
info->name = createStringIfInStack(name);
info->buffer = buffer;
info->frameMax = frameMax;
info->isLooping = isLoop;
mSize++;
}

AnimResInfo* AnimInfoTable::findAnimInfo(const char* name) const {
if (mIsSorted) {
s32 low = 0;
s32 high = mSize;
while (low < high) {
s32 mid = (high + low - 1) >> 1;
AnimResInfo* info = &mInfoEntries[mid];
s32 cmp = strcmp(info->name, name);

if (cmp > 0) {
high = mid;
continue;
}

if (cmp == 0)
return info;

low = mid + 1;
}
return nullptr;
}

for (s32 i = 0; i < mSize; i++) {
AnimResInfo* info = &mInfoEntries[i];
if (isEqualString(info->name, name))
return info;
}
return nullptr;
}

// NON-MATCHING: Different register somehow https://decomp.me/scratch/ZxdNk
AnimResInfo* AnimInfoTable::tryFindAnimInfo(const char* name) const {
return findAnimInfo(name);
}

inline void heapify(AnimResInfo* entries, s32 n, const AnimResInfo& temp, s32 parent) {
s32 child = parent * 2;
while (child <= n) {
if (child < n && strcmp(entries[child - 1].name, entries[child].name) < 0)
child++;

if (strcmp(temp.name, entries[child - 1].name) >= 0)
break;

entries[parent - 1] = entries[child - 1];
parent = child;
child = parent * 2;
}
entries[parent - 1] = temp;
}

void AnimInfoTable::sort() {
s32 n = mSize;
AnimResInfo* entries = mInfoEntries;

if (n < 2 || !entries) {
mIsSorted = true;
return;
}

AnimResInfo temp;

for (s32 i = n / 2; i >= 1; i--) {
temp = entries[i - 1];
heapify(entries, n, temp, i);
}

// TODO: Figure out how to apply heapify here as well
for (s32 i = n; i >= 2; i--) {
temp = entries[i - 1];
entries[i - 1] = entries[0];
s32 parent = 1;
s32 child = parent * 2;
while (child < i) {
if (child < i - 1 && strcmp(entries[child - 1].name, entries[child].name) < 0)
child++;

if (strcmp(temp.name, entries[child - 1].name) >= 0)
break;

entries[parent - 1] = entries[child - 1];
parent = child;
child = parent * 2;
}
entries[parent - 1] = temp;
}

mIsSorted = true;
}

} // namespace al
39 changes: 24 additions & 15 deletions lib/al/Project/Anim/AnimInfo.h
Original file line number Diff line number Diff line change
Expand Up @@ -3,30 +3,39 @@
#include <basis/seadTypes.h>

namespace al {

struct AnimResInfo {
const char* name;
void* resMaterialAnim;
f32 frameMax;
bool isLoop;
AnimResInfo();

s32 getFrameMax() const;
bool isLoop() const;

const char* name = nullptr;
void* buffer = nullptr;
f32 frameMax = 0.0f;
bool isLooping = false;
};

static_assert(sizeof(AnimResInfo) == 0x18);

class AnimInfoTable {
public:
AnimInfoTable(u32);

const AnimResInfo& findAnimInfo(const char* name) const;
bool tryFindAnimInfo(const char* name) const;

void add(const char* name, void*, f32 frameMax, bool isLoop);
AnimInfoTable(s32 capacity);
void add(const char* name, void* buffer, f32 frameMax, bool isLoop);
AnimResInfo* findAnimInfo(const char* name) const;
AnimResInfo* tryFindAnimInfo(const char* name) const;
void sort();

s32 getInfoCount() const { return mInfoCount; }
s32 getSize() const { return mSize; }

const AnimResInfo& getResInfo(s32 index) const { return mResInfos[index]; }
const AnimResInfo& getAnimInfo(s32 index) const { return mInfoEntries[index]; }

private:
s32 mInfoCount;
AnimResInfo* mResInfos;
bool mIsSorted;
s32 mSize = 0;
AnimResInfo* mInfoEntries = nullptr;
bool mIsSorted = false;
};

static_assert(sizeof(AnimInfoTable) == 0x18);

} // namespace al
Loading