From 787d932825b055731039284905f5b0aa574aaf3b Mon Sep 17 00:00:00 2001 From: Misha <106913236+MishaProductions@users.noreply.github.com> Date: Mon, 30 Oct 2023 09:15:43 -0400 Subject: [PATCH 1/3] LegoActor implementation (#253) * LegoActor * LegoEntity * Replace float with MxFloat --------- Co-authored-by: Christian Semmler --- LEGO1/legoactor.cpp | 42 ++++++++++++++++++++++++------------------ LEGO1/legoactor.h | 17 ++++++++++------- LEGO1/legoentity.cpp | 5 +++-- LEGO1/legoentity.h | 5 +---- 4 files changed, 38 insertions(+), 31 deletions(-) diff --git a/LEGO1/legoactor.cpp b/LEGO1/legoactor.cpp index ace8a47c..31c6da6f 100644 --- a/LEGO1/legoactor.cpp +++ b/LEGO1/legoactor.cpp @@ -3,43 +3,49 @@ DECOMP_SIZE_ASSERT(LegoActor, 0x78) // Probably in header -// OFFSET: LEGO1 0x10002cc0 STUB -void LegoActor::VTable0x50() +// OFFSET: LEGO1 0x10002cc0 +MxFloat LegoActor::VTable0x50() { - // TODO + return m_unk68; } -// OFFSET: LEGO1 0x10002cd0 STUB -void LegoActor::VTable0x54() +// OFFSET: LEGO1 0x10002cd0 +void LegoActor::VTable0x54(MxFloat p_unk) { - // TODO + m_unk68 = p_unk; } -// OFFSET: LEGO1 0x10002ce0 STUB -void LegoActor::VTable0x58() +// OFFSET: LEGO1 0x10002ce0 +void LegoActor::VTable0x58(MxFloat p_unk) { - // TODO + m_unk70 = p_unk; } -// OFFSET: LEGO1 0x10002cf0 STUB -void LegoActor::VTable0x5c() +// OFFSET: LEGO1 0x10002cf0 +MxFloat LegoActor::VTable0x5c() { - // TODO + return m_unk70; } -// OFFSET: LEGO1 0x10002d00 STUB -void LegoActor::VTable0x60() +// OFFSET: LEGO1 0x10002d00 +undefined LegoActor::VTable0x60() { - // TODO + return m_unk74; } -// OFFSET: LEGO1 0x10002d10 STUB -void LegoActor::VTable0x64() +// OFFSET: LEGO1 0x10002d10 +void LegoActor::VTable0x64(undefined p_unk) { - // TODO + m_unk74 = p_unk; } // End header +// OFFSET: LEGO1 0x1002d110 LegoActor::LegoActor() { + m_unk68 = 0.0f; + m_unk6c = 0; + m_unk70 = 0.0f; + m_unk10 = 0; + m_unk74 = 0; } diff --git a/LEGO1/legoactor.h b/LEGO1/legoactor.h index 4c943cf6..f4096b06 100644 --- a/LEGO1/legoactor.h +++ b/LEGO1/legoactor.h @@ -23,15 +23,18 @@ class LegoActor : public LegoEntity { return !strcmp(name, LegoActor::ClassName()) || LegoEntity::IsA(name); } - virtual void VTable0x50(); // vtable+0x50 - virtual void VTable0x54(); // vtable+0x54 - virtual void VTable0x58(); // vtable+0x58 - virtual void VTable0x5c(); // vtable+0x5c - virtual void VTable0x60(); // vtable+0x60 - virtual void VTable0x64(); // vtable+0x64 + virtual MxFloat VTable0x50(); // vtable+0x50 + virtual void VTable0x54(MxFloat p_unk); // vtable+0x54 + virtual void VTable0x58(MxFloat p_unk); // vtable+0x58 + virtual MxFloat VTable0x5c(); // vtable+0x5c + virtual undefined VTable0x60(); // vtable+0x60 + virtual void VTable0x64(undefined p_unk); // vtable+0x64 private: - undefined unk68[0x10]; + MxFloat m_unk68; + undefined4 m_unk6c; + MxFloat m_unk70; + undefined m_unk74; }; #endif // LEGOACTOR_H diff --git a/LEGO1/legoentity.cpp b/LEGO1/legoentity.cpp index 19820154..2a9b4b76 100644 --- a/LEGO1/legoentity.cpp +++ b/LEGO1/legoentity.cpp @@ -3,6 +3,7 @@ #include "define.h" #include "legoomni.h" #include "legoutil.h" +#include "legoworld.h" DECOMP_SIZE_ASSERT(LegoEntity, 0x68) @@ -60,12 +61,12 @@ void LegoEntity::Destroy(MxBool p_fromDestructor) Init(); } -// OFFSET: LEGO1 0x10010880 STUB +// OFFSET: LEGO1 0x10010880 void LegoEntity::SetWorld() { LegoWorld* world = GetCurrentWorld(); if (world != NULL && world != (LegoWorld*) this) { - // TODO: world->AddEntity(this); + world->VTable0x58(this); } } diff --git a/LEGO1/legoentity.h b/LEGO1/legoentity.h index 1da99f3b..c0a16c32 100644 --- a/LEGO1/legoentity.h +++ b/LEGO1/legoentity.h @@ -13,10 +13,7 @@ class LegoEntity : public MxEntity { public: // Inlined at 0x100853f7 - inline LegoEntity() - { - // TODO - } + inline LegoEntity() { Init(); } __declspec(dllexport) virtual ~LegoEntity() override; // vtable+0x0 From f3b0de06090d55406990b1226a19adaf9d234873 Mon Sep 17 00:00:00 2001 From: Misha <106913236+MishaProductions@users.noreply.github.com> Date: Mon, 30 Oct 2023 09:54:00 -0400 Subject: [PATCH 2/3] more MxDSBuffer functions (#255) * FUN_100c6f80 * AllocateBuffer * Update mxdsbuffer.h * Update mxdsbuffer.cpp * Update mxdsbuffer.cpp * Return reference * Fix delete call * Fix GetWriteOffset * Remove cast --------- Co-authored-by: Christian Semmler --- LEGO1/mxdsbuffer.cpp | 105 +++++++++++++++++++++++++++++--- LEGO1/mxdsbuffer.h | 21 +++++-- LEGO1/mxdssource.cpp | 2 +- LEGO1/mxramstreamcontroller.cpp | 2 +- LEGO1/mxstreamer.h | 7 ++- 5 files changed, 121 insertions(+), 16 deletions(-) diff --git a/LEGO1/mxdsbuffer.cpp b/LEGO1/mxdsbuffer.cpp index 4163e39b..a09bb101 100644 --- a/LEGO1/mxdsbuffer.cpp +++ b/LEGO1/mxdsbuffer.cpp @@ -1,5 +1,8 @@ #include "mxdsbuffer.h" +#include "mxomni.h" +#include "mxstreamer.h" + DECOMP_SIZE_ASSERT(MxDSBuffer, 0x34); // OFFSET: LEGO1 0x100c6470 @@ -14,24 +17,112 @@ MxDSBuffer::MxDSBuffer() m_unk1c = 0; m_writeOffset = 0; m_bytesRemaining = 0; - m_mode = 2; + m_mode = MxDSBufferType_Preallocated; m_unk30 = 0; } // OFFSET: LEGO1 0x100c6530 MxDSBuffer::~MxDSBuffer() { - // TODO + if (m_pBuffer != NULL) { + if (m_mode == MxDSBufferType_Chunk) { + // TODO + } + else if (m_mode == MxDSBufferType_Allocate || m_mode == MxDSBufferType_Unknown) { + delete[] m_pBuffer; + } + } + + m_unk14 = 0; + m_unk1c = 0; +} + +// OFFSET: LEGO1 0x100c6640 +MxResult MxDSBuffer::AllocateBuffer(MxU32 p_bufferSize, MxDSBufferType p_mode) +{ + MxResult result = FAILURE; + MxU32 i = 0; + if (p_mode == MxDSBufferType_Allocate) { + m_pBuffer = new MxU8[p_bufferSize]; + } + else if (p_mode == MxDSBufferType_Chunk) { + MxStreamer* streamer = Streamer(); + // I have no clue as to what this does, or even if its correct. Maybe it's related to storing chunks in + // MxRamStreamController? + if (p_bufferSize >> 10 == 0x40) { + i = 0; + while (i < 22) { + if ((*(MxU32*) ((streamer->GetSubclass1().GetUnk08() + ((i & 0xffffffe7) >> 3)) & 1 << ((MxU8) i & 0x1f) + )) == 0) { + MxU32* ptr = (MxU32*) ((streamer->GetSubclass1().GetUnk08() + ((i & 0xffffffe7) >> 3)) & + 1 << ((MxU8) i & 0x1f)); + + // mark it as used? + *ptr = *ptr ^ 1 << (i & 0x1f); + + m_pBuffer = + (MxU8*) (streamer->GetSubclass1().GetSize() * i * 0x400 + streamer->GetSubclass1().GetBuffer()); + break; + } + i++; + } + + m_pBuffer = NULL; + } + else if (p_bufferSize >> 10 == 0x80) { + i = 0; + // Same thing as above but it uses subclass2 + while (i < 22) { + if ((*(MxU32*) ((streamer->GetSubclass2().GetUnk08() + ((i & 0xffffffe7) >> 3)) & 1 << ((MxU8) i & 0x1f) + )) == 0) { + MxU32* ptr = (MxU32*) ((streamer->GetSubclass2().GetUnk08() + ((i & 0xffffffe7) >> 3)) & + 1 << ((MxU8) i & 0x1f)); + + // mark it as used? + *ptr = *ptr ^ 1 << (i & 0x1f); + + m_pBuffer = + (MxU8*) (streamer->GetSubclass2().GetSize() * i * 0x400 + streamer->GetSubclass2().GetBuffer()); + break; + } + i++; + } + + m_pBuffer = NULL; + } + else { + m_pIntoBuffer = NULL; + } + } + + m_pIntoBuffer = m_pBuffer; + m_pIntoBuffer2 = m_pBuffer; + if (m_pBuffer != NULL) { + m_mode = p_mode; + m_bytesRemaining = p_bufferSize; + m_writeOffset = p_bufferSize; + result = SUCCESS; + } + return result; } // OFFSET: LEGO1 0x100c6780 -MxResult MxDSBuffer::FUN_100c6780(void* p_buffer, MxU32 p_size) +MxResult MxDSBuffer::SetBufferPointer(MxU32* p_buffer, MxU32 p_size) { - m_pBuffer = p_buffer; - m_pIntoBuffer = p_buffer; - m_pIntoBuffer2 = p_buffer; + m_pBuffer = (MxU8*) p_buffer; + m_pIntoBuffer = (MxU8*) p_buffer; + m_pIntoBuffer2 = (MxU8*) p_buffer; m_bytesRemaining = p_size; m_writeOffset = p_size; - m_mode = 2; + m_mode = MxDSBufferType_Preallocated; return SUCCESS; } + +// OFFSET: LEGO1 0x100c6f80 +void MxDSBuffer::FUN_100c6f80(MxU32 p_unk) +{ + if (p_unk < m_writeOffset) { + m_pIntoBuffer2 = m_pBuffer + p_unk; + m_pIntoBuffer = m_pBuffer + p_unk; + } +} diff --git a/LEGO1/mxdsbuffer.h b/LEGO1/mxdsbuffer.h index e521b47f..33706899 100644 --- a/LEGO1/mxdsbuffer.h +++ b/LEGO1/mxdsbuffer.h @@ -4,6 +4,13 @@ #include "decomp.h" #include "mxcore.h" +enum MxDSBufferType { + MxDSBufferType_Chunk = 0, + MxDSBufferType_Allocate = 1, + MxDSBufferType_Preallocated = 2, + MxDSBufferType_Unknown = 3, +}; + // VTABLE 0x100dcca0 // SIZE 0x34 class MxDSBuffer : public MxCore { @@ -18,20 +25,22 @@ class MxDSBuffer : public MxCore { return "MxDSBuffer"; } - MxResult FUN_100c6780(void* p_buffer, MxU32 p_size); + MxResult AllocateBuffer(MxU32 p_bufferSize, MxDSBufferType p_mode); + MxResult SetBufferPointer(MxU32* p_buffer, MxU32 p_size); + void FUN_100c6f80(MxU32 p_unk); - inline void* GetBuffer() { return m_pBuffer; } + inline MxU8* GetBuffer() { return m_pBuffer; } inline MxU32 GetWriteOffset() { return m_writeOffset; } private: - void* m_pBuffer; - void* m_pIntoBuffer; - void* m_pIntoBuffer2; + MxU8* m_pBuffer; + MxU8* m_pIntoBuffer; + MxU8* m_pIntoBuffer2; undefined4 m_unk14; undefined4 m_unk18; undefined4 m_unk1c; undefined2 m_unk20; - undefined4 m_mode; + MxDSBufferType m_mode; MxU32 m_writeOffset; MxU32 m_bytesRemaining; undefined4 m_unk30; diff --git a/LEGO1/mxdssource.cpp b/LEGO1/mxdssource.cpp index f94318d1..7110c9ee 100644 --- a/LEGO1/mxdssource.cpp +++ b/LEGO1/mxdssource.cpp @@ -5,7 +5,7 @@ // OFFSET: LEGO1 0x100bffd0 void MxDSSource::ReadToBuffer(MxDSBuffer* p_buffer) { - Read((unsigned char*) p_buffer->GetBuffer(), p_buffer->GetWriteOffset()); + Read(p_buffer->GetBuffer(), p_buffer->GetWriteOffset()); } // OFFSET: LEGO1 0x100bfff0 diff --git a/LEGO1/mxramstreamcontroller.cpp b/LEGO1/mxramstreamcontroller.cpp index ae3d9634..2e8efc36 100644 --- a/LEGO1/mxramstreamcontroller.cpp +++ b/LEGO1/mxramstreamcontroller.cpp @@ -29,7 +29,7 @@ MxResult MxRAMStreamController::Open(const char* p_filename) ((MxRAMStreamProvider*) m_provider)->GetBufferOfFileSize(), ((MxRAMStreamProvider*) m_provider)->GetFileSize() ); - m_buffer.FUN_100c6780( + m_buffer.SetBufferPointer( ((MxRAMStreamProvider*) m_provider)->GetBufferOfFileSize(), ((MxRAMStreamProvider*) m_provider)->GetFileSize() ); diff --git a/LEGO1/mxstreamer.h b/LEGO1/mxstreamer.h index 6a62146a..f7d1d448 100644 --- a/LEGO1/mxstreamer.h +++ b/LEGO1/mxstreamer.h @@ -18,9 +18,11 @@ class MxStreamerSubClass1 { ~MxStreamerSubClass1() { delete[] m_buffer; } - undefined4 GetSize() { return m_size; } + undefined4 GetSize() const { return m_size; } void SetBuffer(undefined* p_buf) { m_buffer = p_buf; } + inline undefined* GetBuffer() const { return m_buffer; } + inline undefined4 GetUnk08() const { return m_unk08; } private: undefined* m_buffer; @@ -93,6 +95,9 @@ class MxStreamer : public MxCore { MxResult AddStreamControllerToOpenList(MxStreamController* p_stream); MxResult FUN_100b99b0(MxDSAction* p_action); + inline const MxStreamerSubClass2& GetSubclass1() { return m_subclass1; } + inline const MxStreamerSubClass3& GetSubclass2() { return m_subclass2; } + private: list m_openStreams; // 0x8 MxStreamerSubClass2 m_subclass1; // 0x14 From 1db48b3b2c4c56908e629b1108a46bac90cabf8c Mon Sep 17 00:00:00 2001 From: Misha <106913236+MishaProductions@users.noreply.github.com> Date: Mon, 30 Oct 2023 12:46:38 -0400 Subject: [PATCH 3/3] MxSmkPresenter vtables (#254) * implement vtbls * Update smk.h --- LEGO1/mxsmkpresenter.cpp | 46 ++++++++++++++++++++++++++++++++++++++++ LEGO1/mxsmkpresenter.h | 5 +++++ 2 files changed, 51 insertions(+) diff --git a/LEGO1/mxsmkpresenter.cpp b/LEGO1/mxsmkpresenter.cpp index 126c9a7a..c4c2224e 100644 --- a/LEGO1/mxsmkpresenter.cpp +++ b/LEGO1/mxsmkpresenter.cpp @@ -1,6 +1,7 @@ #include "mxsmkpresenter.h" #include "decomp.h" +#include "mxvideomanager.h" DECOMP_SIZE_ASSERT(MxSmkPresenter, 0x720); @@ -65,3 +66,48 @@ void MxSmkPresenter::FUN_100c5d40(MxSmack* p_mxSmack) if (p_mxSmack->m_unk0x6b4) delete p_mxSmack->m_unk0x6b4; } + +// OFFSET: LEGO1 0x100b4300 +void MxSmkPresenter::Destroy() +{ + Destroy(FALSE); +} + +// OFFSET: LEGO1 0x100b3940 STUB +void MxSmkPresenter::VTable0x5c(undefined4 p_unknown1) +{ +} + +// OFFSET: LEGO1 0x100b3a00 STUB +void MxSmkPresenter::VTable0x68(undefined4 p_unknown1) +{ +} + +// OFFSET: LEGO1 0x100b42c0 +void MxSmkPresenter::VTable0x70() +{ + MxPalette* palette = m_bitmap->CreatePalette(); + MVideoManager()->RealizePalette(palette); + delete palette; +} + +// OFFSET: LEGO1 0x100b4260 +MxU32 MxSmkPresenter::VTable0x88() +{ + MxU32 result = m_unk0x71c; + if ((m_mxSmack.m_smack.m_smkType & 1) != 0) { + result = m_unk0x71c / m_mxSmack.m_smack.m_frames; + if (1 < m_unk0x71c && (m_unk0x71c % m_mxSmack.m_smack.m_frames) == 1) { + m_unk0x71c = 1; + } + return result; + } + else { + if (m_mxSmack.m_smack.m_frames == result) { + m_unk0x71c = 0; + result = 0; + memset(m_mxSmack.m_smack.m_palette, 0, sizeof(m_mxSmack.m_smack.m_palette)); + } + return result; + } +} diff --git a/LEGO1/mxsmkpresenter.h b/LEGO1/mxsmkpresenter.h index 29b23afc..39fbba94 100644 --- a/LEGO1/mxsmkpresenter.h +++ b/LEGO1/mxsmkpresenter.h @@ -13,7 +13,12 @@ class MxSmkPresenter : public MxVideoPresenter { MxSmkPresenter(); virtual ~MxSmkPresenter() override; + virtual void Destroy() override; + virtual void VTable0x5c(undefined4 p_unknown1) override; virtual void VTable0x60() override; + virtual void VTable0x68(undefined4 p_unknown1) override; // vtable+0x68 + virtual void VTable0x70() override; + virtual MxU32 VTable0x88(); struct MxSmack { Smack m_smack;