diff options
author | Paul Gilbert | 2012-05-03 22:49:30 +1000 |
---|---|---|
committer | Paul Gilbert | 2012-05-03 22:49:30 +1000 |
commit | a2982a0b20027f658c9b47266a8ddbec74a15878 (patch) | |
tree | c324455bc893fbc48ffb6b13fa4b153e30b93a7d | |
parent | ba2711b5e39e495c4cfb1187710605bb9fbf10b1 (diff) | |
download | scummvm-rg350-a2982a0b20027f658c9b47266a8ddbec74a15878.tar.gz scummvm-rg350-a2982a0b20027f658c9b47266a8ddbec74a15878.tar.bz2 scummvm-rg350-a2982a0b20027f658c9b47266a8ddbec74a15878.zip |
TONY: Engine is now compiling and linking again
-rw-r--r-- | engines/tony/adv.h | 2 | ||||
-rw-r--r-- | engines/tony/font.cpp | 27 | ||||
-rw-r--r-- | engines/tony/game.cpp | 2 | ||||
-rw-r--r-- | engines/tony/gfxcore.cpp | 46 | ||||
-rw-r--r-- | engines/tony/gfxengine.cpp | 14 | ||||
-rw-r--r-- | engines/tony/module.mk | 1 | ||||
-rw-r--r-- | engines/tony/sound.cpp | 38 | ||||
-rw-r--r-- | engines/tony/tony.cpp | 79 | ||||
-rw-r--r-- | engines/tony/tony.h | 4 | ||||
-rw-r--r-- | engines/tony/utils.cpp | 130 | ||||
-rw-r--r-- | engines/tony/utils.h | 4 | ||||
-rw-r--r-- | engines/tony/window.cpp | 1255 | ||||
-rw-r--r-- | engines/tony/window.h | 27 |
13 files changed, 1570 insertions, 59 deletions
diff --git a/engines/tony/adv.h b/engines/tony/adv.h index aab7df24af..9a5ecd5072 100644 --- a/engines/tony/adv.h +++ b/engines/tony/adv.h @@ -92,7 +92,7 @@ void MainShowMouse(void); void MainHideMouse(void); void MainEnableInput(void); void MainDisableInput(void); -void MainPlayMusic(int nChannel, const char *fn, int nFX, bool bLoop, int nSync); +void MainPlayMusic(int nChannel, const char *filename, int nFX, bool bLoop, int nSync); void MainInitWipe(int type); void MainCloseWipe(void); void MainWaitWipeEnd(void); diff --git a/engines/tony/font.cpp b/engines/tony/font.cpp index 2996b30f04..a0500047b6 100644 --- a/engines/tony/font.cpp +++ b/engines/tony/font.cpp @@ -125,6 +125,14 @@ void RMFont::Load(const byte *buf, int nChars, int dimx, int dimy, uint32 palRes nLetters=nChars; } +void RMFont::Load(uint32 resID, int nChars, int dimx, int dimy, uint32 palResID) { + RMRes res(resID); + + if ((int)res.Size() < nChars * (dimy * dimx + 8)) + nChars = res.Size() / (dimy * dimx + 8); + + Load(res, nChars, dimx, dimy, palResID); +} void RMFont::Unload(void) { if (m_letter != NULL) { @@ -2273,6 +2281,25 @@ void RMTextItemName::Draw(RMGfxTargetBuffer &bigBuf, RMGfxPrimitive *prim) { RMText::Draw(bigBuf,prim); } +RMPoint RMTextItemName::GetHotspot() { + if (m_item == NULL) + return m_mpos + m_curscroll; + else + return m_item->Hotspot(); +} + +RMItem *RMTextItemName::GetSelectedItem() { + return m_item; +} + +bool RMTextItemName::IsItemSelected() { + return m_item != NULL; +} + +bool RMTextItemName::IsNormalItemSelected() { + return m_item != NULL && m_itemName.Length() > 0; +} + /****************************************************************************\ * Metodi di RMDialogChoice diff --git a/engines/tony/game.cpp b/engines/tony/game.cpp index d5047766bb..00bb81dcf4 100644 --- a/engines/tony/game.cpp +++ b/engines/tony/game.cpp @@ -130,7 +130,7 @@ void MainHideMouse(void) { _vm->GetEngine()->DisableMouse(); } -void MainPlayMusic(int nChannel, char* filename, int nFX, bool bLoop, int nSync) { +void MainPlayMusic(int nChannel, const char *filename, int nFX, bool bLoop, int nSync) { _vm->PlayMusic(nChannel, filename, nFX, bLoop, nSync); } diff --git a/engines/tony/gfxcore.cpp b/engines/tony/gfxcore.cpp index 4842126c59..1d289fbecc 100644 --- a/engines/tony/gfxcore.cpp +++ b/engines/tony/gfxcore.cpp @@ -138,15 +138,15 @@ void RMGfxBuffer::OffsetY(int nLines, int nBpp) { } -inline RMGfxBuffer::operator byte *() { +RMGfxBuffer::operator byte *() { return m_buf; } -inline RMGfxBuffer::operator void *() { +RMGfxBuffer::operator void *() { return (void *)m_buf; } -inline RMGfxBuffer::RMGfxBuffer(int dimx, int dimy, int nBpp, bool bUseDDraw) { +RMGfxBuffer::RMGfxBuffer(int dimx, int dimy, int nBpp, bool bUseDDraw) { Create(dimx, dimy, nBpp, bUseDDraw); } @@ -255,7 +255,7 @@ bool RMGfxSourceBuffer::Clip2D(int &x1, int &y1, int &u, int &v, int &width, int * \****************************************************************************/ -inline int RMGfxSourceBuffer::Init(uint32 resID, int dimx, int dimy, bool bLoadPalette) { +int RMGfxSourceBuffer::Init(uint32 resID, int dimx, int dimy, bool bLoadPalette) { return Init(RMRes(resID), dimx, dimy, bLoadPalette); } @@ -275,11 +275,11 @@ void RMGfxWoodyBuffer::Draw(RMGfxTargetBuffer &bigBuf, RMGfxPrimitive *prim) { RMGfxSourceBuffer16::Draw(bigBuf, prim); } -inline RMGfxWoodyBuffer::RMGfxWoodyBuffer() { +RMGfxWoodyBuffer::RMGfxWoodyBuffer() { } -inline RMGfxWoodyBuffer::RMGfxWoodyBuffer(int dimx, int dimy, bool bUseDDraw) +RMGfxWoodyBuffer::RMGfxWoodyBuffer(int dimx, int dimy, bool bUseDDraw) : RMGfxBuffer(dimx,dimy,16,bUseDDraw) { } @@ -407,7 +407,7 @@ void RMGfxTargetBuffer::AddPrim(RMGfxPrimitive *prim) { g_system->unlockMutex(csModifyingOT); } -inline void RMGfxTargetBuffer::AddClearTask(void) { +void RMGfxTargetBuffer::AddClearTask(void) { AddPrim(new RMGfxPrimitive(&taskClear)); } @@ -486,11 +486,11 @@ void RMGfxSourceBufferPal::Init(RMDataStream &ds, int dimx, int dimy, bool bLoad } } -inline int RMGfxSourceBufferPal::LoadPalette(uint32 resID) { +int RMGfxSourceBufferPal::LoadPalette(uint32 resID) { return LoadPalette(RMRes(resID)); } -inline int RMGfxSourceBufferPal::LoadPaletteWA(uint32 resID, bool bSwapped) { +int RMGfxSourceBufferPal::LoadPaletteWA(uint32 resID, bool bSwapped) { return LoadPaletteWA(RMRes(resID), bSwapped); } @@ -501,7 +501,7 @@ inline int RMGfxSourceBufferPal::LoadPaletteWA(uint32 resID, bool bSwapped) { void RMGfxSourceBuffer4::Draw(RMGfxTargetBuffer &bigBuf, RMGfxPrimitive *prim) { } -inline RMGfxSourceBuffer4::RMGfxSourceBuffer4(int dimx, int dimy, bool bUseDDraw) +RMGfxSourceBuffer4::RMGfxSourceBuffer4(int dimx, int dimy, bool bUseDDraw) : RMGfxBuffer(dimx,dimy,4,bUseDDraw) { SetPriority(0); } @@ -516,11 +516,11 @@ inline RMGfxSourceBuffer4::RMGfxSourceBuffer4(int dimx, int dimy, bool bUseDDraw * \****************************************************************************/ -inline int RMGfxSourceBuffer4::Bpp() { +int RMGfxSourceBuffer4::Bpp() { return 4; } -inline void RMGfxSourceBuffer4::Create(int dimx, int dimy, bool bUseDDraw) { +void RMGfxSourceBuffer4::Create(int dimx, int dimy, bool bUseDDraw) { RMGfxBuffer::Create(dimx,dimy,4,bUseDDraw); } @@ -589,12 +589,12 @@ void RMGfxSourceBuffer8::Draw(RMGfxTargetBuffer &bigBuf, RMGfxPrimitive *prim) { } } -inline RMGfxSourceBuffer8::RMGfxSourceBuffer8(int dimx, int dimy, bool bUseDDraw) +RMGfxSourceBuffer8::RMGfxSourceBuffer8(int dimx, int dimy, bool bUseDDraw) : RMGfxBuffer(dimx,dimy,8,bUseDDraw) { SetPriority(0); } -inline RMGfxSourceBuffer8::RMGfxSourceBuffer8(bool bTrasp0) { +RMGfxSourceBuffer8::RMGfxSourceBuffer8(bool bTrasp0) { m_bTrasp0=bTrasp0; } @@ -609,11 +609,11 @@ inline RMGfxSourceBuffer8::RMGfxSourceBuffer8(bool bTrasp0) { * \****************************************************************************/ -inline int RMGfxSourceBuffer8::Bpp() { +int RMGfxSourceBuffer8::Bpp() { return 8; } -inline void RMGfxSourceBuffer8::Create(int dimx, int dimy, bool bUseDDraw) { +void RMGfxSourceBuffer8::Create(int dimx, int dimy, bool bUseDDraw) { RMGfxBuffer::Create(dimx, dimy, 8, bUseDDraw); } @@ -630,7 +630,7 @@ RMGfxSourceBuffer8AB::~RMGfxSourceBuffer8AB() { } -inline int RMGfxSourceBuffer8AB::CalcTrasp(int fore, int back) +int RMGfxSourceBuffer8AB::CalcTrasp(int fore, int back) { int r,g,b; @@ -1919,7 +1919,7 @@ void RMGfxSourceBuffer16::PrepareImage(void) { } -inline RMGfxSourceBuffer16::RMGfxSourceBuffer16(int dimx, int dimy, bool bUseDDraw) +RMGfxSourceBuffer16::RMGfxSourceBuffer16(int dimx, int dimy, bool bUseDDraw) : RMGfxBuffer(dimx,dimy,16,bUseDDraw) { SetPriority(0); } @@ -1934,11 +1934,11 @@ inline RMGfxSourceBuffer16::RMGfxSourceBuffer16(int dimx, int dimy, bool bUseDDr * \****************************************************************************/ -inline int RMGfxSourceBuffer16::Bpp() { +int RMGfxSourceBuffer16::Bpp() { return 16; } -inline void RMGfxSourceBuffer16::Create(int dimx, int dimy, bool bUseDDraw) { +void RMGfxSourceBuffer16::Create(int dimx, int dimy, bool bUseDDraw) { RMGfxBuffer::Create(dimx,dimy,16,bUseDDraw); } @@ -1980,17 +1980,17 @@ void RMGfxBox::Draw(RMGfxTargetBuffer &bigBuf, RMGfxPrimitive *prim) { * Metodi di RMGfxClearTask \****************************************************************************/ -inline int RMGfxClearTask::Priority() { +int RMGfxClearTask::Priority() { // Priorita' massima (deve essere fatto per primo) return 1; } -inline void RMGfxClearTask::Draw(RMGfxTargetBuffer &bigBuf, RMGfxPrimitive *) { +void RMGfxClearTask::Draw(RMGfxTargetBuffer &bigBuf, RMGfxPrimitive *) { // Pulisce tutto il target buffer Common::fill((byte *)bigBuf, (byte *)bigBuf + (bigBuf.Dimx() * bigBuf.Dimy() * 2), 0x0); } -inline bool RMGfxClearTask::RemoveThis() { +bool RMGfxClearTask::RemoveThis() { // Il task di clear si disattiva sempre return true; } diff --git a/engines/tony/gfxengine.cpp b/engines/tony/gfxengine.cpp index b8accda7c6..d4ea8ee821 100644 --- a/engines/tony/gfxengine.cpp +++ b/engines/tony/gfxengine.cpp @@ -58,15 +58,25 @@ extern bool bIdleExited; extern bool bPatIrqFreeze; extern bool bSkipSfxNoLoop; -extern void ExitAllIdles(int nCurLoc); /****************************************************************************\ * Metodi di RMGfxEngine \****************************************************************************/ +bool bIdleExited; + +void ExitAllIdles(int nCurLoc) { + // Chiude le idle + bSkipSfxNoLoop = true; + mpalEndIdlePoll(nCurLoc); + bIdleExited = true; + bSkipSfxNoLoop = false; + ExitThread(0); +} + RMGfxEngine::RMGfxEngine() { // Crea il big buffer dove verranno disegnati i frame - m_bigBuf.Create(RM_BBX,RM_BBY,16); + m_bigBuf.Create(RM_BBX, RM_BBY, 16); m_bigBuf.OffsetY(RM_SKIPY); } diff --git a/engines/tony/module.mk b/engines/tony/module.mk index 690b1f4713..af0b3acd2c 100644 --- a/engines/tony/module.mk +++ b/engines/tony/module.mk @@ -14,6 +14,7 @@ MODULE_OBJS := \ tony.o \ tonychar.o \ utils.o \ + window.o \ mpal/expr.o \ mpal/loadmpc.o \ mpal/memory.o \ diff --git a/engines/tony/sound.cpp b/engines/tony/sound.cpp index e757ac4115..a5293eecb2 100644 --- a/engines/tony/sound.cpp +++ b/engines/tony/sound.cpp @@ -505,7 +505,7 @@ uint32 CODECADPCMMONO::Decompress(Common::File &fp, void *buf, uint32 dwSize) { uint16 *lpBuf = (uint16 *)buf; byte *inp; int bufferstep; - int cache; + int cache = 0; int delta; int sign; int vpdiff; @@ -545,12 +545,12 @@ uint32 CODECADPCMMONO::Decompress(Common::File &fp, void *buf, uint32 dwSize) { cache = *inp++; delta = (cache>>4)&0xF; } else - delta=cache&0xF; + delta = cache & 0xF; /* Trova il nuovo indice */ index += indexTable[delta]; if (index < 0) index = 0; - if (index > 88) index=88; + if (index > 88) index = 88; /* Legge il segno e lo separa dall'ampliamento */ sign = delta&8; @@ -558,9 +558,9 @@ uint32 CODECADPCMMONO::Decompress(Common::File &fp, void *buf, uint32 dwSize) { /* Trova la differenza dal valore precedente */ vpdiff = step >> 3; - if (delta&4) vpdiff+=step; - if (delta&2) vpdiff+=step >> 1; - if (delta&1) vpdiff+=step >> 2; + if (delta&4) vpdiff += step; + if (delta&2) vpdiff += step >> 1; + if (delta&1) vpdiff += step >> 2; if (sign) valpred -= vpdiff; @@ -1551,12 +1551,10 @@ void FPSFX::GetVolume(int *lpdwVolume) { *lpdwVolume -= (DSBVOLUME_MIN); *lpdwVolume *= 64; *lpdwVolume /= (DSBVOLUME_MAX - DSBVOLUME_MIN); -#endregion +#endif } - - /****************************************************************************\ * Metodi di FPSTREAM \****************************************************************************/ @@ -1571,6 +1569,7 @@ void FPSFX::GetVolume(int *lpdwVolume) { \****************************************************************************/ FPSTREAM::FPSTREAM(LPDIRECTSOUND LPDS, HWND hWnd, bool bSoundOn) { +#ifdef REFACTOR_ME //hwnd=hWnd; lpDS=LPDS; bSoundSupported = bSoundOn; @@ -1581,6 +1580,7 @@ FPSTREAM::FPSTREAM(LPDIRECTSOUND LPDS, HWND hWnd, bool bSoundOn) { lpDSBuffer = NULL; lpDSNotify = NULL; hHot1 = hHot2 = hHot3 = hPlayThread_PlayFast = hPlayThread_PlayNormal = NULL; +#endif } bool FPSTREAM::CreateBuffer(int nBufSize) { @@ -1661,6 +1661,8 @@ bool FPSTREAM::CreateBuffer(int nBufSize) { \****************************************************************************/ FPSTREAM::~FPSTREAM() { +#ifdef REFACTOR_ME + if (!bSoundSupported) return; @@ -1695,6 +1697,7 @@ FPSTREAM::~FPSTREAM() { RELEASE(lpDSNotify); RELEASE(lpDSBuffer); +#endif } @@ -1711,9 +1714,9 @@ FPSTREAM::~FPSTREAM() { * \****************************************************************************/ -FPSTREAM::Release() { +void FPSTREAM::Release() { delete this; - return NULL; +// return NULL; } @@ -1780,6 +1783,8 @@ bool FPSTREAM::LoadFile(const char *lpszFileName, uint32 dwCodType, int nBufSize \****************************************************************************/ bool FPSTREAM::UnloadFile() { +#ifdef REFACTOR_ME + if (!bSoundSupported || !bFileLoaded) return true; @@ -1791,7 +1796,7 @@ bool FPSTREAM::UnloadFile() { /* Si ricorda che non c'e' piu' nessun file in memoria */ bFileLoaded = false; - +#endif return true; } @@ -1985,6 +1990,8 @@ bool FPSTREAM::Play() { \****************************************************************************/ bool FPSTREAM::Stop(bool bSync) { +#ifdef REFACTOR_ME + if (!bSoundSupported) return true; @@ -2018,7 +2025,7 @@ bool FPSTREAM::Stop(bool bSync) { bIsPlaying = false; bPaused = false; } - +#endif return true; } @@ -2199,6 +2206,8 @@ void FPSTREAM::SetLoop(bool loop) { void FPSTREAM::Pause(bool bPause) { +#ifdef REFACTOR_ME + if (bFileLoaded) { if (bPause && bIsPlaying) { lpDSBuffer->Stop(); @@ -2227,6 +2236,7 @@ void FPSTREAM::Pause(bool bPause) { SetVolume(lastVolume); } } +#endif } @@ -2278,7 +2288,7 @@ void FPSTREAM::GetVolume(int *lpdwVolume) { *lpdwVolume -= (DSBVOLUME_MIN); *lpdwVolume *= 64; *lpdwVolume /= (DSBVOLUME_MAX - DSBVOLUME_MIN); -#endregion +#endif } } // End of namespace Tony diff --git a/engines/tony/tony.cpp b/engines/tony/tony.cpp index ea555972d0..0a2143ba8b 100644 --- a/engines/tony/tony.cpp +++ b/engines/tony/tony.cpp @@ -139,7 +139,7 @@ int flipflop=0; OSystem::MutexRef csMusic; -void TonyEngine::PlayMusic(int nChannel, char* fn, int nFX, bool bLoop, int nSync) { +void TonyEngine::PlayMusic(int nChannel, const char *fn, int nFX, bool bLoop, int nSync) { warning("TonyEngine::PlayMusic"); } @@ -202,6 +202,46 @@ int TonyEngine::GetMusicVolume(int nChannel) { return 255; } + +void TonyEngine::GetSaveStateFileName(int n, char *buf) { + RMString name; + + if (n > 0) + name.Format("%02d", n); + else + name.Format("autosave"); + + name += ".sav"; +} + +void TonyEngine::AutoSave(void) { + char buf[256]; + + GrabThumbnail(); + MainWaitFrame(); + MainWaitFrame(); + MainFreeze(); + GetSaveStateFileName(0,buf); + _theEngine.SaveState(buf, (byte *)m_curThumbnail, "Autosave", true); + MainUnfreeze(); +} + + +void TonyEngine::SaveState(int n, const char *name) { + char buf[256]; + + GetSaveStateFileName(n, buf); + _theEngine.SaveState(buf,(byte *)m_curThumbnail, name); +} + + +void TonyEngine::LoadState(int n) { + char buf[256]; + + GetSaveStateFileName(n, buf); + _theEngine.LoadState(buf); +} + bool TonyEngine::OpenVoiceDatabase() { char id[4]; uint32 numfiles; @@ -251,6 +291,21 @@ void TonyEngine::GrabThumbnail(void) { warning("TODO: TonyEngine::GrabThumbnail"); } +void TonyEngine::OptionScreen(void) { +} + +void TonyEngine::OpenInitLoadMenu(void) { + _theEngine.OpenOptionScreen(1); +} + +void TonyEngine::OpenInitOptions(void) { + _theEngine.OpenOptionScreen(2); +} + +void TonyEngine::Abort(void) { + m_bQuitNow = true; +} + void TonyEngine::Play(void) { warning("TODO TonyEngine::Play"); @@ -314,14 +369,14 @@ void TonyEngine::PauseLoop(void) { MSG msg; int st,et; - st = timeGetTime(); + st = GetTime(); while (m_bPaused && GetMessage(&msg,m_wnd,0,0)) { TranslateMessage(&msg); DispatchMessage(&msg); } - et = timeGetTime(); + et = GetTime(); m_startTime += et - st; #endif @@ -345,4 +400,22 @@ warning("TODO: TonyEninge::Pause"); */ } +void TonyEngine::FreezeTime(void) { + m_bTimeFreezed = true; + m_nTimeFreezed = GetTime() - m_startTime; +} + +void TonyEngine::UnfreezeTime(void) +{ + m_bTimeFreezed = false; +} + + +/** + * Returns the millisecond timer + */ +uint32 TonyEngine::GetTime() { + return g_system->getMillis(); +} + } // End of namespace Tony diff --git a/engines/tony/tony.h b/engines/tony/tony.h index dd7e558820..06fe357c0d 100644 --- a/engines/tony/tony.h +++ b/engines/tony/tony.h @@ -158,7 +158,7 @@ public: // Music // ****** - void PlayMusic(int nChannel, char *fn, int nFX, bool bLoop, int nSync); + void PlayMusic(int nChannel, const char *fn, int nFX, bool bLoop, int nSync); void StopMusic(int nChannel); void PlaySFX(int nSfx, int nFX = 0); @@ -183,7 +183,7 @@ public: // Salvataggio void AutoSave(void); - void SaveState(int n, char *name); + void SaveState(int n, const char *name); void LoadState(int n); void GetSaveStateFileName(int n, char* buf); diff --git a/engines/tony/utils.cpp b/engines/tony/utils.cpp index 43a129b92a..69ad5633d7 100644 --- a/engines/tony/utils.cpp +++ b/engines/tony/utils.cpp @@ -292,8 +292,8 @@ RMString::operator char*() const { /** * Resize a string as necessary * @param size New size necessary (in bytes) - * @param bMaintain If TRUE we must keep the original string, - if FALSE we can destroy. + * @param bMaintain If true we must keep the original string, + if false we can destroy. */ void RMString::Resize(int size, bool bMantain) { if (m_realLength == 0) { @@ -407,6 +407,122 @@ void RMString::Format(char* str, ...) { } /****************************************************************************\ +* Metodi di RMFileStreamSlow +\****************************************************************************/ + +RMFileStreamSlow::RMFileStreamSlow() : RMDataStream() { + _stream = NULL; +} + +RMFileStreamSlow::~RMFileStreamSlow() { + Close(); +} + +void RMFileStreamSlow::Close() { + delete _stream; +} + +bool RMFileStreamSlow::OpenFile(Common::File &file) { + _stream = file.readStream(file.size()); + + m_length = _stream->pos(); + + return true; +} + + +bool RMFileStreamSlow::OpenFile(const char *lpFN) { + // Apre il file in lettura + Common::File f; + if (!f.open(lpFN)) + return false; + + m_length = f.size(); + _stream = f.readStream(f.size()); + + return true; +} + + +RMDataStream& RMFileStreamSlow::operator+=(int nBytes) { + Seek(nBytes); + return *this; +} + +int RMFileStreamSlow::Pos() { + return _stream->pos(); +} + +bool RMFileStreamSlow::IsEOF() { + return (Pos() >= m_length); +} + + +int RMFileStreamSlow::Seek(int nBytes, RMDSPos where) { + switch (where) { + case START: + return _stream->seek(nBytes); + + case END: + return _stream->seek(nBytes, SEEK_END); + + case CUR: + return _stream->seek(nBytes, SEEK_CUR); + + default: + return 0; + } +} + + +bool RMFileStreamSlow::Read(void *buf, int size) { + uint32 dwRead; + + dwRead = _stream->read(buf, size); + return ((int)dwRead == size); +} + + +RMFileStreamSlow &operator>>(RMFileStreamSlow &df, char &var) { + df.Read(&var, 1); + return df; +} + +RMFileStreamSlow &operator>>(RMFileStreamSlow &df, byte &var) { + df.Read(&var,1); + return df; +} + +RMFileStreamSlow &operator>>(RMFileStreamSlow &df, uint16 &var) { + uint16 v; + df.Read(&v, 2); + v = FROM_LE_16(v); + return df; +} + +RMFileStreamSlow &operator>>(RMFileStreamSlow &df, int16 &var) { + uint16 v; + df.Read(&v, 2); + var = (int16)FROM_LE_16(v); + return df; +} + +RMFileStreamSlow &operator>>(RMFileStreamSlow &df, int &var) { + int v; + df.Read(&v,4); + var = FROM_LE_32(v); + return df; +} + +RMFileStreamSlow &operator>>(RMFileStreamSlow &df, uint32 &var) { + uint32 v; + df.Read(&v, 4); + var = FROM_LE_32(v); + return df; +} + + +/****************************************************************************\ * RMDataStream methods \****************************************************************************/ @@ -458,7 +574,7 @@ int RMDataStream::Length() { /** * Determines if the end of the stream has been reached - * @returns TRUE if end of stream reached, FALSE if not + * @returns true if end of stream reached, false if not */ bool RMDataStream::IsEOF() { return (m_pos >= m_length); @@ -546,7 +662,7 @@ RMDataStream &operator>>(RMDataStream &df, uint32 &var) { * Reads a series of data from the stream in a buffer * @param lpBuf Data buffer * @param size Size of the buffer - * @returns TRUE if we have reached the end, FALSE if not + * @returns true if we have reached the end, false if not */ bool RMDataStream::Read(void *lpBuf, int size) { byte *dest = (byte *)lpBuf; @@ -609,7 +725,7 @@ int RMDataStream::Pos() { /** * Check if an error occurred during reading the stream - * @returns TRUE if there was an error, false otherwise + * @returns true if there was an error, false otherwise */ bool RMDataStream::IsError() { return m_bError; @@ -714,7 +830,7 @@ RMPoint &RMPoint::operator+=(RMPoint p) { /** * Subtract (offset) of a point */ -RMPoint& RMPoint::operator-=(RMPoint p) { +RMPoint &RMPoint::operator-=(RMPoint p) { Offset(-p); return *this; } @@ -807,7 +923,7 @@ RMPoint &RMRect::TopLeft() { return *((RMPoint *)this); } -RMPoint& RMRect::BottomRight() { +RMPoint &RMRect::BottomRight() { // FIXME: This seems very bad return *((RMPoint*)this + 1); } diff --git a/engines/tony/utils.h b/engines/tony/utils.h index f9c9e614ac..0ce4e83f27 100644 --- a/engines/tony/utils.h +++ b/engines/tony/utils.h @@ -140,9 +140,7 @@ public: class RMFileStreamSlow : public RMDataStream { private: - Common::File f; - bool bMustClose; - + Common::SeekableReadStream *_stream; public: RMFileStreamSlow(); virtual ~RMFileStreamSlow(); diff --git a/engines/tony/window.cpp b/engines/tony/window.cpp new file mode 100644 index 0000000000..ab68030b90 --- /dev/null +++ b/engines/tony/window.cpp @@ -0,0 +1,1255 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ +/************************************************************************** + * ÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍ * + * Nayma Software srl * + * e -= We create much MORE than ALL =- * + * u- z$$$c '. ÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍ * + * .d" d$$$$$b "b. * + * .z$* d$$$$$$$L ^*$c. * + * #$$$. $$$$$$$$$ .$$$" Project: Roasted Moths........ * + * ^*$b 4$$$$$$$$$F .d$*" * + * ^$$. 4$$$$$$$$$F .$P" Module: Window.HPP........... * + * *$. '$$$$$$$$$ 4$P 4 * + * J *$ "$$$$$$$" $P r Author: Giovanni Bajo........ * + * z$ '$$$P*4c.*$$$*.z@*R$$$ $. * + * z$" "" #$F^ "" '$c Desc: Classi per la gestione * + * z$$beu .ue=" $ "=e.. .zed$$c di una finestra Direct + * "#$e z$*" . `. ^*Nc e$"" Draw................. * + * "$$". .r" ^4. .^$$" ..................... * + * ^.@*"6L=\ebu^+C$"*b." * + * "**$. "c 4$$$ J" J$P*" OS: [ ] DOS [X] WIN95 [ ] PORT * + * ^"--.^ 9$" .--"" COMP: [ ] WATCOM [X] VISUAL C++ * + * " [ ] EIFFEL [ ] GCC/GXX/DJGPP * + * * + * This source code is Copyright (C) Nayma Software. ALL RIGHTS RESERVED * + * * + **************************************************************************/ + +#include "tony/window.h" +#include "tony/game.h" +#include "tony/tony.h" + +namespace Tony { + +#define DDRELEASE(x) if (x) { (x)->Release(); (x)=NULL; } + +// Tabella per il b&w. Globale per accederci dalla roba ASM +static uint16 m_wPrecalcTable[0x10000]; + +/****************************************************************************\ +* Metodi di RMWindow +\****************************************************************************/ + +#ifdef REFACTOR_ME +LRESULT CALLBACK GlobalWindowProc(HWND hWnd, uint32 msg, uint16 wParam, int32 lParam) { + if ((HWND)theGame.m_wnd == NULL) + return DefWindowProc(hWnd, msg, wParam, lParam); + + switch (msg) { + case WM_CREATE: + return 0; + + case WM_CLOSE: + PostQuitMessage(0); + return 0; + + default: + return theGame.m_wnd.WindowProc(msg, wParam, lParam); + } +} +#endif + +#ifdef REFACTOR_ME +LRESULT RMWindow::WindowProc(uint32 msg, uint16 wParam, int32 lParam) { + switch (msg) { + case WM_ACTIVATE: + if (LOWORD(wParam)!=WA_INACTIVE) + theGame.Pause(false); + else + theGame.Pause(true); + return 0; + + case WM_ENTERMENULOOP: + case WM_ENTERSIZEMOVE: + if (!m_bFullscreen) + theGame.Pause(true); + return 0; + + case WM_EXITMENULOOP: + case WM_EXITSIZEMOVE: + if (!m_bFullscreen) + theGame.Pause(false); + return 0; +/* + case WM_KEYDOWN: + switch (wParam) + { + case '0': + case '1': + case '2': + case '3': + case '4': + case '5': + case '6': + case '7': + case '8': + case '9': + if (GetAsyncKeyState(VK_CONTROL)&0x8000) + theGame.SaveState(wParam-'0'); + else if (GetAsyncKeyState(VK_SHIFT)&0x8000) + theGame.LoadState(wParam-'0'); + return 0; + } + return 0; +*/ + + case WM_PAINT: +// Repaint(); + ValidateRect(m_hWnd, NULL); + return 0; + + case WM_COMMAND: + switch LOWORD(wParam) { +/* + case ID_OPTIONS: + theGame.OptionScreen(); + break; +*/ + + case ID_FULLSCREEN: + theGame.SwitchFullscreen(!m_bFullscreen); + break; +/* + case ID_ENABLEINPUT: + theGame.GetEngine()->EnableInput(); + break; +*/ + case ID_SCREENSHOT: + m_bGrabScreenshot = true; +// m_bGrabMovie = !m_bGrabMovie; + break; + + case ID_MOVIE: +// m_bGrabMovie = !m_bGrabMovie; + break; +/* + case ID_BLACKWHITE: + m_bBlackWhite = !m_bBlackWhite; + break; +*/ + default: + return DefWindowProc(m_hWnd, msg, wParam, lParam); + } + return 0; + + case WM_SYSKEYDOWN: + if (m_bFullscreen) + return 0; + else + return DefWindowProc(m_hWnd ,msg, wParam, lParam); + + default: + if (m_hWnd != NULL) // Fix del bug visto da BoundsChecker + return DefWindowProc(m_hWnd, msg, wParam, lParam); + return 0; + } +} +#endif + +/* +HANDLE hWaitFlip; +bool bExitThread; + +void DoFlipThread(LPDIRECTDRAWSURFACE lpDDSPrimary) +{ + bExitThread=false; + + while (1) + { + WaitForSingleObject(hWaitFlip,INFINITE); + if (bExitThread) _endthread(); + lpDDSPrimary->Flip(NULL,DDFLIP_WAIT); + } +} +*/ + +void RMWindow::InitDirectDraw(void) { +#ifdef REFACTOR_ME + DDInit(); + + ShowCursor(false); + ShowWindow(m_hWnd, SW_SHOW); + UpdateWindow(m_hWnd); +#endif +} + +void RMWindow::Init(/*HINSTANCE hInst*/) { +#ifdef REFACTOR_ME + WNDCLASS wc; + + // Registra la classe di finestra + wc.style = CS_HREDRAW|CS_VREDRAW; + wc.lpfnWndProc = GlobalWindowProc; + wc.cbClsExtra = 0; + wc.cbWndExtra = 0; + wc.hInstance = hInst; + wc.hIcon = LoadIcon(hInst,MAKEINTRESOURCE(IDI_ICON1)); + wc.hCursor = LoadCursor(NULL,IDC_ARROW); + wc.hbrBackground = NULL; + wc.lpszMenuName = NULL; + wc.lpszClassName = "RMClass"; + RegisterClass(&wc); + + m_hWnd = CreateWindow( + "RMClass", + "Tony Tough and the night of Roasted Moths", + WS_OVERLAPPEDWINDOW & (~WS_THICKFRAME) & (~WS_BORDER) & (~WS_MAXIMIZEBOX), + 50, 50, + RM_SX + GetSystemMetrics(SM_CXDLGFRAME) * 2, + RM_SY + GetSystemMetrics(SM_CYDLGFRAME) * 2 + GetSystemMetrics(SM_CYMENU) + GetSystemMetrics(SM_CYCAPTION), + NULL, + NULL, + hInst, + NULL + ); + + if (m_hWnd == NULL) { + int err = GetLastError(); + RMString str; + + str.Format("error: %u",err); + MessageBox(NULL,str,"sux",MB_OK); + + assert(0); + } + + // Inizializza la finestra directdraw + //DDInit(); + + // Inizializza i conteggi degli FPS + fps = lastfcount = fcount = lastsecond = 0; + + m_bGrabScreenshot = false; + m_bGrabThumbnail = false; + m_bGrabMovie = false; + + //hWaitFlip = CreateEvent(NULL,false,false, NULL); +#endif +}; + +void RMWindow::Close(void) { + DDClose(); +#ifdef REFACTOR_ME + DestroyWindow(m_hWnd); +#endif +} + +void RMWindow::GrabThumbnail(uint16 *thumbmem) { + m_bGrabThumbnail = true; + m_wThumbBuf = thumbmem; +} + +float RGB_to_HSL(float r,float g, float b, float *h, float *s, float *l) { + float v; + float m; + float vm; + float r2, g2, b2; + + if (r > g) v = r; else v = g; + if (v > b) v = v; else v = b; + if (r < b) m = r; else m = b; + if (m < b) m = m; else m = b; + + if ((*l = (m + v) / 2.0f) <= 0.0f) return *l; + if ((*s = vm = v - m) > 0.0f) { + *s /= (*l <= 0.5f) ? (v + m) : (2.0f - v - m) ; + } else + return *l; + + r2 = (v - r) / vm; + g2 = (v - g) / vm; + b2 = (v - b) / vm; + + if (r == v) + *h = (g == m ? 5.0f + b2 : 1.0f - g2); + else if (g == v) + *h = (b == m ? 1.0f + r2 : 3.0f - b2); + else + *h = (r == m ? 3.0f + g2 : 5.0f - r2); + + *h /= 6; + + return *l; +} + +#define ITOF(val) (float)((float)(val) / 31.0f) +#define FTOI(val) (int)(((float)(val) * 31.0f + 0.5f)) + +void RMWindow::CreateBWPrecalcTable(void) { +#define CLAMP(var, min, max) var = (var < min ? min : (var > max ? max : var)); + + int i; + int r, g, b; + int min, max; + int shiftR, shiftG, shiftB; + + // Calcola i valori di shift in base alle maschere + for (shiftR = 15; (mskRed & (1 << shiftR)) == 0; shiftR--) + ; + for (shiftG = 15; (mskGreen & (1 << shiftG)) == 0; shiftG--) + ; + for (shiftB = 15; (mskBlue & (1 << shiftB)) == 0; shiftB--) + ; + + shiftR -= 4; + shiftG -= 4; + shiftB -= 4; + + // @@@ CLAMP inutile (in teoria) + CLAMP(shiftR, 0, 15); + CLAMP(shiftG, 0, 15); + CLAMP(shiftB, 0, 15); + + for (i = 0;i<0x10000;i++) + { + r=(i >> shiftR) & 0x1F; + g=(i >> shiftG) & 0x1F; + b=(i >> shiftB) & 0x1F; + +#if 1 + if (r < g) min=r; else min = g; + if (b < min) min = b; + if (r > g) max = r; else max = g; + if (b > max) max = b; + min = (min + max) / 2; +#else + // Nuova formula B&W. L'immagine è più fedele all'originale, ma l'effetto è peggiore + float fr, fg, fb; + + fr = (float)r / 63.0f; + fg = (float)g / 63.0f; + fb = (float)b / 63.0f; + + min = (int)((fr*0.11f + fg*0.69f + fb*0.33f)*63.f); +#endif + + /* + RGB_to_HSL(ITOF(r), ITOF(g), ITOF(b), &h, &s, &l); + min = FTOI(l); + */ + + r = min + 8 - 8; + g = min + 5 - 8; + b = min + 0 - 8; + + CLAMP(r, 0, 31); + CLAMP(g, 0, 31); + CLAMP(b, 0, 31); + + m_wPrecalcTable[i] = (b << shiftB) | (g << shiftG) | (r << shiftR); + } +} + + +void RMWindow::DDClose(void) { +#ifdef REFACTOR_ME + DDRELEASE(m_Back); + DDRELEASE(m_Primary); + DDRELEASE(m_MainClipper); + DDRELEASE(m_BackClipper); + DDRELEASE(m_DD); +#endif +} + +void RMWindow::DDInit(void) { +#ifdef REFACTOR_ME + HRESULT err; + + // Crea DirectDraw + err = DirectDrawCreate(NULL, &m_DD, NULL); + assert(err == DD_OK); + + // Crea il clipper + err = DirectDrawCreateClipper(0, &m_MainClipper, NULL); + err=DirectDrawCreateClipper(0, &m_BackClipper, NULL); + + // Lo associa alla finestra + m_MainClipper->SetHWnd(0, m_hWnd); + + // Setta la cooperazione a normal + m_DD->SetCooperativeLevel(m_hWnd, DDSCL_NORMAL); + +#ifdef STARTFULLSCREEN + // Di default in fullscreen + m_bFullscreen=false; // Fa finta, per obbligarlo a cambiare + m_Primary=m_Back=NULL; + SwitchFullscreen(true); +#else + // Di default in finestra + m_bFullscreen = true; // Fa finta, per obbligarlo a cambiare + m_Primary = m_Back = NULL; + SwitchFullscreen(false); +#endif + +/* + if (!ISMODE1() && !ISMODE2() && !ISMODE3() && !ISMODE4()) + { + RMString str; + str.Format("Graphic mode not supported: %04x %04x %04x",mskRed,mskGreen,mskBlue); + MessageBox(m_hWnd,str,"Debug",MB_OK); + } +*/ +#endif +} + + +void RMWindow::SwitchFullscreen(bool bFull) { +#ifdef REFACTOR_ME + HRESULT err; + DDSURFACEDESC ddsd; + DDSCAPS ddscaps; + DDBLTFX ddbltfx; + Common::Rect rcWin; + + // Se non c'e' niente da fare, esci + if (bFull == m_bFullscreen) + return; + + // Termina il thread di flipping + //bExitThread = true; + + // Rilascia le superfici create in precedenza (se ce n'erano) + DDRELEASE(m_Back); + DDRELEASE(m_Primary); + + // Legge le coordinate della finestra + if (m_bFullscreen) { + rcWin.left = 50; + rcWin.top = 50; + } else { + GetWindowRect(m_hWnd, &rcWin); + } + + if (bFull) { + // Setta la risoluzione + m_DD->SetCooperativeLevel(m_hWnd, DDSCL_EXCLUSIVE | DDSCL_FULLSCREEN | DDSCL_ALLOWREBOOT); + m_DD->SetDisplayMode(RM_SX, RM_SY, 16); + + // A tutto schermo, possiamo creare una catena di flipping + ZeroMemory(&ddsd, sizeof(ddsd)); + ddsd.dwSize = sizeof(ddsd); + ddsd.dwFlags = DDSD_CAPS|DDSD_BACKBUFFERCOUNT; + ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE | DDSCAPS_COMPLEX | DDSCAPS_FLIP; + ddsd.dwBackBufferCount = 1; + if ((err=m_DD->CreateSurface(&ddsd, &m_Primary, NULL)) != DD_OK) { + //wsprintf(errbuf,"Error creating primary surface2 (%lx)",err); + //MessageBox(hWnd,errbuf,"grSwitchFullscreen()",MB_OK); + assert(0); + } + + ddscaps.dwCaps = DDSCAPS_BACKBUFFER; + if ((err=m_Primary->GetAttachedSurface(&ddscaps, &m_Back)) != DD_OK) { + //wsprintf(errbuf,"Error getting attached surface2 (%lx)",err); + //MessageBox(hWnd,errbuf,"grSwitchFullscreen()",MB_OK); + assert(0); + } + + // Pulisce i buffer + ddbltfx.dwSize = sizeof(ddbltfx); + ddbltfx.dwFillColor = 0; + m_Back->Blt(NULL, NULL, NULL,DDBLT_COLORFILL | DDBLT_WAIT, &ddbltfx); + + ddbltfx.dwSize=sizeof(ddbltfx); + ddbltfx.dwFillColor = 0; + m_Primary->Blt(NULL, NULL, NULL, DDBLT_COLORFILL | DDBLT_WAIT, &ddbltfx); + + // Inizializza il thread + //_beginthread((void (*)(void*))DoFlipThread,10240,(void*)m_Primary); + } else { + // In windowed, non possiamo fare flipping (purtroppo) + m_DD->RestoreDisplayMode(); + m_DD->SetCooperativeLevel(m_hWnd,DDSCL_NORMAL); + + ZeroMemory(&ddsd,sizeof(ddsd)); + ddsd.dwSize=sizeof(ddsd); + ddsd.dwFlags=DDSD_CAPS; + ddsd.ddsCaps.dwCaps=DDSCAPS_PRIMARYSURFACE; + if ((err=m_DD->CreateSurface(&ddsd,&m_Primary, NULL)) != DD_OK) { + //wsprintf(errbuf,"Error creating primary surface (%lx)",err); + //MessageBox(hWnd,errbuf,"ChangeResolution()",MB_OK); + assert(0); + } + + ZeroMemory(&ddsd,sizeof(ddsd)); + ddsd.dwSize=sizeof(ddsd); + ddsd.dwFlags=DDSD_CAPS|DDSD_WIDTH|DDSD_HEIGHT; + ddsd.ddsCaps.dwCaps=DDSCAPS_OFFSCREENPLAIN; // se puo', in video memory + ddsd.dwWidth=RM_SX; + ddsd.dwHeight=RM_SY; + if ((err=m_DD->CreateSurface(&ddsd,&m_Back, NULL)) != DD_OK) { + //wsprintf(errbuf,"Error creating backbuffer surface (%lx)",err); + //MessageBox(hWnd,errbuf,"ChangeResolution()",MB_OK); + assert(0); + } + + // Pulizia per favore + ddbltfx.dwSize = sizeof(ddbltfx); + ddbltfx.dwFillColor = 0; + m_Back->Blt(NULL, NULL, NULL, DDBLT_COLORFILL | DDBLT_WAIT, &ddbltfx); + } + + // Posiziona e ridimensiona la finestra + if (bFull) { + SetWindowPos(m_hWnd, HWND_TOP, 0, 0, RM_SX, RM_SY, 0); + + // Disabilita il clipper (non necessario) + m_Primary->SetClipper(NULL); + } else { + SetWindowPos(m_hWnd, HWND_TOP, rcWin.left, rcWin.top, RM_SX + GetSystemMetrics(SM_CXDLGFRAME) * 2, + RM_SY + GetSystemMetrics(SM_CYDLGFRAME) * 2 + GetSystemMetrics(SM_CYCAPTION), 0); + + m_Primary->SetClipper(m_MainClipper); + //m_Primary->SetClipper(NULL); + } + + // Si ricorda il nuovo stato + m_bFullscreen = bFull; + InvalidateRect(m_hWnd, NULL, false); + + // Legge il nuovo pixel format + UpdatePixelFormat(); +#endif +} + +void RMWindow::UpdatePixelFormat(void) { +#ifdef REFACTOR_ME + DDPIXELFORMAT ddpf; + + // Si fa ridare il nuovo pixel format + ddpf.dwSize = sizeof(ddpf); + m_Primary->GetPixelFormat(&ddpf); + + // Copia le componenti dei colori + mskRed = ddpf.dwRBitMask; + mskGreen = ddpf.dwGBitMask; + mskBlue = ddpf.dwBBitMask; + + // Ricalcola la tabella per l'effetto b&w + CreateBWPrecalcTable(); +#endif +} + + +void RMWindow::Repaint(void) { +#ifdef REFACTOR_ME + Common::Rect rcWin; + HRESULT err; + + if (m_Primary==NULL) + return; + + // Se siamo a tutto schermo, basta un flip + if (m_bFullscreen) { + m_DD->WaitForVerticalBlank(DDWAITVB_BLOCKBEGIN, NULL); + + // Flippa flappa + while (1) { + //err=m_Primary->Flip(NULL,DDFLIP_WAIT); + err = m_Primary->BltFast(0, 0, m_Back, NULL, DDBLTFAST_WAIT); + + if (err==DD_OK) + break; + else if (err == DDERR_SURFACELOST) { + //MessageBox(NULL,"Primary lost!","RMWindow::Repaint()",MB_OK); + m_Primary->Restore(); + return; + } + } + } + // Altrimenti bisogna andare di blit + else { + // Si calcola il rettangolo effettivamente visibile + GetWindowRect(m_hWnd, &rcWin); + OffsetRect(&rcWin, GetSystemMetrics(SM_CXDLGFRAME), GetSystemMetrics(SM_CYDLGFRAME) + GetSystemMetrics(SM_CYCAPTION)); + + // Aggiusta le dimensioni del rettangolo + rcWin.right = rcWin.left + RM_SX; + rcWin.bottom = rcWin.top + RM_SY; + + // Blit del back nel primary + while (1) { + err = m_Primary->Blt(&rcWin, m_Back, NULL,DDBLT_WAIT, NULL); + if (err == DD_OK) + break; + else if (err == DDERR_SURFACELOST) { + //MessageBox(NULL,"Primary lost!","RMWindow::Repaint()",MB_OK); + m_Primary->Restore(); + return; + } + } + } +#endif +} + + +void RMWindow::Unlock(DDSURFACEDESC &ddsd) { +#ifdef REFACTOR_ME + m_Back->Unlock(ddsd.lpSurface); +#endif +} + +void RMWindow::WipeEffect(Common::Rect &rcBoundEllipse) { +#ifdef REFACTOR_ME + Common::Rect rcScreen; + HRGN hrgnCombined; + HRGN hrgnScreen; + HRGN hrgnEllipse; + uint32 dwDataSize; + RGNDATA *rgnData; + + SetRect(&rcScreen, 0, 0, 640, 480); + + hrgnScreen = CreateRectRgnIndirect(&rcScreen); + hrgnEllipse = CreateEllipticRgnIndirect(&rcBoundEllipse); + hrgnCombined = CreateRectRgnIndirect(&rcScreen); + + CombineRgn(hrgnCombined, hrgnScreen, hrgnEllipse, RGN_DIFF); + + dwDataSize = GetRegionData(hrgnCombined, 0, NULL); + rgnData = (RGNDATA *)new char[dwDataSize]; + GetRegionData(hrgnCombined, dwDataSize, rgnData); + + m_BackClipper->SetClipList(rgnData, 0); + m_Back->SetClipper(m_BackClipper); + + DDBLTFX ddbltfx; + ddbltfx.dwSize=sizeof(ddbltfx); + ddbltfx.dwFillColor = 0; + m_Back->Blt(NULL, NULL, NULL, DDBLT_COLORFILL | DDBLT_WAIT, &ddbltfx); + + m_Back->SetClipper(NULL); + delete [] rgnData; + DeleteObject(hrgnCombined); + DeleteObject(hrgnEllipse); + DeleteObject(hrgnScreen); +#endif +} + +bool RMWindow::Lock(DDSURFACEDESC &ddsd) { +#ifdef REFACTOR_ME + HRESULT err; + + // Lock della surface + ddsd.dwSize = sizeof(ddsd); + while (1) { + err = m_Back->Lock(NULL,&ddsd,DDLOCK_WAIT|DDLOCK_WRITEONLY|DDLOCK_NOSYSLOCK, NULL); + if (err==DD_OK) + break; + else if (err==DDERR_SURFACELOST) { +// MessageBox(NULL,"Primary lost!","RMWindow::Repaint()",MB_OK); + m_Back->Restore(); + return false; + } + } +#endif + return true; +} + +void RMWindow::GetNewFrame(byte *lpBuf, Common::Rect *rcBoundEllipse) { +#ifdef REFACTOR_ME + HRESULT err; + DDSURFACEDESC ddsd; + int x,y; + byte *dest; + uint16 *destw; + RMString s; + uint16 *src,src2; + + if (GetAsyncKeyState(VK_F7)&0x8001) + goto DOFRAMERATE; + + if (!Lock(ddsd)) + return; + + // Copia del buffer + src = (uint16 *)lpBuf; + dest = (byte *)ddsd.lpSurface; +// src+=RM_SKIPY*RM_BBX; Lo skipY e' integrato nell'offseting del bigbuffer + + if (ISMODE2()) { + // 565 RGB, Marco - Matrox G200 + int lineinc = (ddsd.lPitch / 2 - RM_SX) * 2; + int lineinc2 = (RM_BBX - RM_SKIPX - RM_SX) * 2; + destw = (uint16 *)dest; + + if (bCfgAnni30) { + __asm { + pushad + + mov y,RM_SY + mov esi,src + mov edi,dest + + //ALIGN 4 + line30: + mov x,RM_SX + add esi,RM_SKIPX*2 + + line302: + mov eax,[esi] ; U 1 + mov ebx,[esi+4] ; V + mov ecx,eax ; U 2 + mov edx,ebx ; V + and eax,0x7FE07FE0 ; U 3 + and ebx,0x7FE07FE0 ; V + and ecx,0x001F001F ; U 4 + and edx,0x001F001F ; V + shl eax,1 ; U 5 + shl ebx,1 ; V + or eax,ecx ; U 6 + or ebx,edx ; V + + // Codice B&W - Pairato + mov ecx,eax + mov edx,ebx + and eax,0xFFFF + and ebx,0xFFFF + shr ecx,16 + shr edx,16 + mov eax,[offset m_wPrecalcTable + eax*2] + mov ebx,[offset m_wPrecalcTable + ebx*2] + mov ecx,[offset m_wPrecalcTable + ecx*2] + mov edx,[offset m_wPrecalcTable + edx*2] + shl ecx,16 + shl edx,16 + and eax,0xFFFF + and ebx,0xFFFF + or eax,ecx + or ebx,edx + + mov [edi],eax ; U 7 + mov [edi+4],ebx ; V + add esi,8 ; U 8 + add edi,8 ; V + sub x,4 ; U 9 + jnz line302 ; V + + add esi,lineinc2 + add edi,lineinc + + dec y + jnz line30 + + popad + } + + } else { + __asm { + pushad + + mov y,RM_SY + mov esi,src + mov edi,dest + + //ALIGN 4 + line: + mov x,RM_SX + add esi,RM_SKIPX*2 + + line2: + mov eax,[esi] ; U 1 + mov ebx,[esi+4] ; V + mov ecx,eax ; U 2 + mov edx,ebx ; V + and eax,0x7FE07FE0 ; U 3 + and ebx,0x7FE07FE0 ; V + and ecx,0x001F001F ; U 4 + and edx,0x001F001F ; V + shl eax,1 ; U 5 + shl ebx,1 ; V + or eax,ecx ; U 6 + or ebx,edx ; V + mov [edi],eax ; U 7 + mov [edi+4],ebx ; V + add esi,8 ; U 8 + add edi,8 ; V + sub x,4 ; U 9 + jnz line2 ; V + + add esi,lineinc2 + add edi,lineinc + + dec y + jnz line + + popad + } + } + } else if (ISMODE3()) { + // 5551 RGB + int lineinc = (ddsd.lPitch / 2 - RM_SX) * 2; + int lineinc2 = (RM_BBX - RM_SKIPX - RM_SX) * 2; + destw=(uint16 *)dest; + + if (bCfgAnni30) { + __asm { + mov y,RM_SY + mov esi,src + mov edi,dest + + aline30: + mov x,RM_SX + add esi,RM_SKIPX*2 + + aline302: + mov eax,[esi] ; U 1 + mov ebx,[esi+4] ; V + shl eax,1 ; U 2 + shl ebx,1 ; V + + // Codice B&W - Pairato + mov ecx,eax + mov edx,ebx + and eax,0xFFFF + and ebx,0xFFFF + shr ecx,16 + shr edx,16 + mov eax,[offset m_wPrecalcTable + eax*2] + mov ebx,[offset m_wPrecalcTable + ebx*2] + mov ecx,[offset m_wPrecalcTable + ecx*2] + mov edx,[offset m_wPrecalcTable + edx*2] + shl ecx,16 + shl edx,16 + and eax,0xFFFF + and ebx,0xFFFF + or eax,ecx + or ebx,edx + + mov [edi],eax ; U 3 + mov [edi+4],ebx ; V + add esi,8 ; U 4 + add edi,8 ; V + sub x,4 ; U 5 + jnz aline302 ; V + + add esi,lineinc2 + add edi,lineinc + + dec y + jnz aline30 + } + } else { + __asm { + mov y,RM_SY + mov esi,src + mov edi,dest + + aline: + mov x,RM_SX + add esi,RM_SKIPX*2 + + aline2: + mov eax,[esi] ; U 1 + mov ebx,[esi+4] ; V + shl eax,1 ; U 2 + shl ebx,1 ; V + mov [edi],eax ; U 3 + mov [edi+4],ebx ; V + add esi,8 ; U 4 + add edi,8 ; V + sub x,4 ; U 5 + jnz aline2 ; V + + add esi,lineinc2 + add edi,lineinc + + dec y + jnz aline + } + } + } else if (ISMODE4()) { + // 565 BGR - Intergraph + int lineinc=(ddsd.lPitch / 2 - RM_SX) * 2; + int lineinc2=(RM_BBX - RM_SKIPX - RM_SX) * 2; + destw=(uint16 *)dest; + + if (bCfgAnni30) // Manca supporto per Intergraph ... non so pairarlo!!! :) + { + __asm { + mov y,RM_SY + mov esi,src + mov edi,dest + + //ALIGN 4 + intersux30: + mov ecx,RM_SX + add esi,RM_SKIPX*2 + + intersux302: + mov eax,[esi] ; U 1 0BBBBBGGGGGRRRRR 0BBBBBGGGGGRRRRR + add esi,4 ; V + mov ebx,eax ; U 2 0BBBBBGGGGGRRRRR 0BBBBBGGGGGRRRRR + mov edx,eax ; V 0BBBBBGGGGGRRRRR 0BBBBBGGGGGRRRRR + shl eax,11 ; U 3 RRRRR0BBBBBGGGGG RRRRR00000000000 + and ebx,0x03E003E0 ; V 000000GGGGG00000 000000GGGGG00000 + and edx,0x7C007C00 ; U 4 0BBBBB0000000000 0BBBBB0000000000 + and eax,0xF800F800 ; V RRRRR00000000000 RRRRR00000000000 + shr edx,10 ; U 5 00000000000BBBBB 00000000000BBBBB + add ebx,ebx ; V 00000GGGGG000000 00000GGGGG000000 + or eax,edx ; U 6 RRRRR000000BBBBB RRRRR000000BBBBB + add edi,4 ; V + or eax,ebx ; U 7 RRRRRGGGGG0BBBBB RRRRRGGGGG0BBBBB + sub ecx,2 ; V + mov [edi-4],eax ; U 8 + jnz intersux302 ; V + + add esi,lineinc2 + add edi,lineinc + + dec y + jnz intersux30 + } + } else { + __asm { + mov y,RM_SY + mov esi,src + mov edi,dest + + //ALIGN 4 + intersux: + mov ecx,RM_SX + add esi,RM_SKIPX*2 + + intersux2: + mov eax,[esi] ; U 1 0BBBBBGGGGGRRRRR 0BBBBBGGGGGRRRRR + add esi,4 ; V + mov ebx,eax ; U 2 0BBBBBGGGGGRRRRR 0BBBBBGGGGGRRRRR + mov edx,eax ; V 0BBBBBGGGGGRRRRR 0BBBBBGGGGGRRRRR + shl eax,11 ; U 3 RRRRR0BBBBBGGGGG RRRRR00000000000 + and ebx,0x03E003E0 ; V 000000GGGGG00000 000000GGGGG00000 + and edx,0x7C007C00 ; U 4 0BBBBB0000000000 0BBBBB0000000000 + and eax,0xF800F800 ; V RRRRR00000000000 RRRRR00000000000 + shr edx,10 ; U 5 00000000000BBBBB 00000000000BBBBB + add ebx,ebx ; V 00000GGGGG000000 00000GGGGG000000 + or eax,edx ; U 6 RRRRR000000BBBBB RRRRR000000BBBBB + add edi,4 ; V + or eax,ebx ; U 7 RRRRRGGGGG0BBBBB RRRRRGGGGG0BBBBB + sub ecx,2 ; V + mov [edi-4],eax ; U 8 + jnz intersux2 ; V + + add esi,lineinc2 + add edi,lineinc + + dec y + jnz intersux + } + } + } else { + // 555 RGB - Computer di Bagio, nVidia Riva 128 + int lineinc = (ddsd.lPitch / 2 - RM_SX) * 2; + int lineinc2 = (RM_BBX - RM_SKIPX - RM_SX) * 2; + destw=(uint16 *)dest; + + if (bCfgAnni30) { + __asm { + mov y,RM_SY + mov esi,src + mov edi,dest + + bagioline30: + mov x,RM_SX + add esi,RM_SKIPX*2 + + bagioline302: + mov eax,[esi] ; U 1 + mov ebx,[esi+4] ; V + + // Codice B&W - Pairato + mov ecx,eax + mov edx,ebx + and eax,0xFFFF + and ebx,0xFFFF + shr ecx,16 + shr edx,16 + mov eax,[offset m_wPrecalcTable + eax*2] + mov ebx,[offset m_wPrecalcTable + ebx*2] + mov ecx,[offset m_wPrecalcTable + ecx*2] + mov edx,[offset m_wPrecalcTable + edx*2] + shl ecx,16 + shl edx,16 + and eax,0xFFFF + and ebx,0xFFFF + or eax,ecx + or ebx,edx + + mov [edi],eax ; U 3 + mov [edi+4],ebx ; V + add esi,8 ; U 4 + add edi,8 ; V + sub x,4 ; U 5 + jnz bagioline302 ; V + + add esi,lineinc2 + add edi,lineinc + + dec y + jnz bagioline30 + } + } else { + for (y = 0; y < RM_SY; y++) { + CopyMemory(dest, src + RM_SKIPX, RM_SX * 2); + dest += ddsd.lPitch; + src += RM_BBX; + } + } + } + + + // Unlock + Unlock(ddsd); + + // Effetto di wipe + if (rcBoundEllipse) { + WipeEffect(*rcBoundEllipse); + } + + // Repaint + Repaint(); + +DOFRAMERATE: + + // Conteggio per gli FPS + fcount++; + + if (lastsecond + 1000 < _vm->GetTime()) { + lastsecond = _vm->GetTime(); + fps=fcount - lastfcount; + lastfcount = fcount; + + if (!m_bFullscreen) { + s.Format("Tony Tough and the night of Roasted Moths - %u FPS",fps); + SetWindowText(m_hWnd,s); + } + } if (!_vm->getIsDemo()) { + if (m_bGrabScreenshot || m_bGrabMovie) { + RMSnapshot snapshot; + + snapshot.GrabScreenshot(lpBuf); + m_bGrabScreenshot = false; + } + + if (m_bGrabThumbnail) { + RMSnapshot snapshot; + + snapshot.GrabScreenshot(lpBuf, 4, m_wThumbBuf); + m_bGrabThumbnail = false; + } + } +#endif +} + + +/****************************************************************************\ +* Metodi di RMSnapshot +\****************************************************************************/ + +char RMSnapshot::bufDrive[_MAX_DRIVE]; +char RMSnapshot::bufDir[_MAX_DIR]; +char RMSnapshot::bufName[_MAX_FNAME]; +char RMSnapshot::bufExt[_MAX_EXT]; +char RMSnapshot::filename[512]; +byte RMSnapshot::rgb[RM_SX * RM_SY * 3]; + +bool RMSnapshot::GetFreeSnapName(char *fn) { +#ifdef REFACTOR_ME + int i, j, k; + HANDLE h; + + theGame.GetDataDirectory(RMGame::DD_SHOTS, fn); + _splitpath(fn, bufDrive, bufDir, NULL, NULL); + + for (i = 1; i < 10; i++) { + wsprintf(bufName,"rm%d00",i); + _makepath(fn,bufDrive,bufDir,bufName,".bmp"); + h = CreateFile(fn,GENERIC_READ,FILE_SHARE_READ, NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL, NULL); + if (h == INVALID_HANDLE_VALUE) + break; + CloseHandle(h); + } + + i--; + + for (j = 1; j < 10; j++) { + wsprintf(bufName,"rm%d%d0",i,j); + _makepath(fn,bufDrive,bufDir,bufName,".bmp"); + h=CreateFile(fn,GENERIC_READ,FILE_SHARE_READ, NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL, NULL); + if (h==INVALID_HANDLE_VALUE) + break; + CloseHandle(h); + } + + j--; + + for (k = 0; k < 10; k++) { + wsprintf(bufName,"rm%d%d%d",i,j,k); + _makepath(fn,bufDrive,bufDir,bufName,".bmp"); + h = CreateFile(fn,GENERIC_READ,FILE_SHARE_READ, NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL, NULL); + if (h==INVALID_HANDLE_VALUE) + break; + CloseHandle(h); + } + + if (k == 10) { + k = 0; + j++; + if (j == 10) { + j = 0; + i++; + if (i == 10) + return false; + } + + wsprintf(bufName,"rm%d%d%d",i,j,k); + _makepath(fn,bufDrive,bufDir,bufName,".bmp"); + } +#endif + return true; +} + +void RMSnapshot::GrabScreenshot(byte *lpBuf, int dezoom, uint16 *lpDestBuf) { +#ifdef REFACTOR_ME + uint16 *src = (uint16 *)lpBuf; + + int dimx = RM_SX / dezoom; + int dimy = RM_SY / dezoom; + + int u, v, curv; + + uint16 appo; + uint32 k = 0; + int sommar, sommab, sommag; + uint16 *cursrc; + + if (lpDestBuf == NULL) + src += (RM_SY - 1) * RM_BBX; + + if (dezoom == 1 && 0) { // @@@ NON E' TESTATA MOLTO BENE!!! + byte *curOut = rgb; + + for (int y = 0; y < dimy; y++) { + for (int x = 0; x < dimx; x++) { + cursrc = &src[RM_SKIPX + x]; + + *curOut++ = ((*cursrc) & 0x1F) << 3; + *curOut++ = (((*cursrc) >> 5) & 0x1F) << 3; + *curOut++ = (((*cursrc) >> 10) & 0x1F) << 3; + + if (lpDestBuf) + *lpDestBuf++ = *cursrc; + } + + if (lpDestBuf == NULL) + src -= RM_BBX; + else + src += RM_BBX; + } + } else { + for (int y = 0; y < dimy; y++) { + for(int x = 0; x < dimx; x++) { + cursrc = &src[RM_SKIPX + x * dezoom]; + sommar = sommab = sommag = 0; + + for (v = 0; v < dezoom; v++) + for (u = 0; u < dezoom; u++) { + if (lpDestBuf == NULL) + curv = -v; + else + curv = v; + + sommab += cursrc[curv*RM_BBX + u] & 0x1F; + sommag += (cursrc[curv*RM_BBX + u] >> 5) & 0x1F; + sommar += (cursrc[curv*RM_BBX + u] >> 10) & 0x1F; + } + + rgb[k + 0] = (byte) (sommab * 8 / (dezoom * dezoom)); + rgb[k + 1] = (byte) (sommag * 8 / (dezoom * dezoom)); + rgb[k + 2] = (byte) (sommar * 8 / (dezoom * dezoom)); + + if (lpDestBuf!=NULL) + lpDestBuf[k/3] = ((int)rgb[k+0]>>3) | (((int)rgb[k+1]>>3)<<5) | (((int)rgb[k+2]>>3)<<10); + + k+=3; + } + + if (lpDestBuf == NULL) + src -= RM_BBX * dezoom; + else + src += RM_BBX * dezoom; + } + } + + + if (lpDestBuf == NULL) { + if (!GetFreeSnapName(filename)) + return; + + HANDLE hFile = CreateFile(filename, + GENERIC_WRITE, + 0, + NULL, + CREATE_ALWAYS, + FILE_ATTRIBUTE_NORMAL | FILE_FLAG_SEQUENTIAL_SCAN, + NULL); + + BITMAPFILEHEADER bmfHeader; + bmfHeader.bfType = ((uint16) ('M' << 8) | 'B'); + bmfHeader.bfSize = sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) + dimx * dimy * 3; + bmfHeader.bfReserved1 = 0; + bmfHeader.bfReserved2 = 0; + bmfHeader.bfOffBits = sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER); + + BITMAPINFOHEADER bmiHeader; + bmiHeader.biSize = sizeof(BITMAPINFOHEADER); + bmiHeader.biWidth = dimx; + bmiHeader.biHeight = dimy; + bmiHeader.biPlanes = 1; + bmiHeader.biBitCount = 24; + bmiHeader.biCompression = BI_RGB; + bmiHeader.biSizeImage = dimx * dimy * 3; + bmiHeader.biXPelsPerMeter = 0xB12; + bmiHeader.biYPelsPerMeter = 0xB12; + bmiHeader.biClrUsed = 0; + bmiHeader.biClrImportant = 0; + + uint32 dwWritten; + WriteFile(hFile, &bmfHeader, sizeof(BITMAPFILEHEADER), &dwWritten, NULL); + WriteFile(hFile, &bmiHeader, sizeof(BITMAPINFOHEADER), &dwWritten, NULL); + + WriteFile(hFile, rgb, dimx * dimy * 3, &dwWritten, NULL); + CloseHandle(hFile); + } +#endif +} + +} // End of namespace Tony diff --git a/engines/tony/window.h b/engines/tony/window.h index d248ffb871..25aef5c619 100644 --- a/engines/tony/window.h +++ b/engines/tony/window.h @@ -50,15 +50,36 @@ #include "common/scummsys.h" #include "common/rect.h" +#include "tony/adv.h" namespace Tony { typedef uint32 HWND; +struct DDSURFACEDESC { +}; + +class RMSnapshot { +private: + // Buffer per la creazione dei path + static char bufDrive[_MAX_DRIVE], bufDir[_MAX_DIR], bufName[_MAX_FNAME], bufExt[_MAX_EXT]; + static char filename[512]; + + // Buffer per la conversione a RGB + static byte rgb[RM_SX * RM_SY * 3]; + +private: + bool GetFreeSnapName(char *fn); + +public: + // Prende uno screenshot + void GrabScreenshot(byte *lpBuf, int dezoom = 1, uint16 *lpDestBuf = NULL); +}; + class RMWindow { private: - bool Lock(/*DDSURFACEDESC& ddsd */); - void Unlock(/*DDSURFACEDESC& ddsd */); + bool Lock(DDSURFACEDESC &ddsd); + void Unlock(DDSURFACEDESC &ddsd); // Inizializza DirectDraw void DDInit(void); @@ -115,7 +136,7 @@ protected: void GetNewFrame(byte *lpBuf, Common::Rect *rcBoundEllipse); // Avverte di grabbare un thumbnail per il salvataggio -// void GrabThumbnail(uint16 *buf); + void GrabThumbnail(uint16 *buf); operator HWND() { return m_hWnd; } |