diff options
author | Paul Gilbert | 2012-09-09 19:55:05 +1000 |
---|---|---|
committer | Paul Gilbert | 2012-09-09 19:55:05 +1000 |
commit | 97e84b2169e8f3084e568776b1a9561a2df6878e (patch) | |
tree | e70cab3661314615ab0b123ef6654f18e7cc954f | |
parent | 42a09f00b336ce3405ff7558719f07e6f15326aa (diff) | |
download | scummvm-rg350-97e84b2169e8f3084e568776b1a9561a2df6878e.tar.gz scummvm-rg350-97e84b2169e8f3084e568776b1a9561a2df6878e.tar.bz2 scummvm-rg350-97e84b2169e8f3084e568776b1a9561a2df6878e.zip |
HOPKINS: Implemented image loading code
-rw-r--r-- | engines/hopkins/files.cpp | 161 | ||||
-rw-r--r-- | engines/hopkins/files.h | 1 | ||||
-rw-r--r-- | engines/hopkins/globals.cpp | 7 | ||||
-rw-r--r-- | engines/hopkins/globals.h | 5 | ||||
-rw-r--r-- | engines/hopkins/graphics.cpp | 710 | ||||
-rw-r--r-- | engines/hopkins/graphics.h | 64 | ||||
-rw-r--r-- | engines/hopkins/hopkins.cpp | 9 | ||||
-rw-r--r-- | engines/hopkins/hopkins.h | 5 |
8 files changed, 844 insertions, 118 deletions
diff --git a/engines/hopkins/files.cpp b/engines/hopkins/files.cpp index cf6c06f22c..565143d3ff 100644 --- a/engines/hopkins/files.cpp +++ b/engines/hopkins/files.cpp @@ -163,4 +163,165 @@ byte *FileManager::LIBERE_FICHIER(byte *ptr) { return PTRNUL; } +bool FileManager::RECHERCHE_CAT(const Common::String &file, int a2) { + byte *ptr; // [sp+1Ch] [bp-40h]@0 + Common::File f; + + switch (a2) { + case 1: + CONSTRUIT_FICHIER(GLOBALS.HOPLINK, "RES_INI.CAT"); + if (!f.exists(GLOBALS.NFICHIER)) + return PTRNUL; + + ptr = CHARGE_FICHIER(GLOBALS.NFICHIER); + CONSTRUIT_FICHIER(GLOBALS.HOPLINK, "RES_INI.RES"); + break; + + case 2: + CONSTRUIT_FICHIER(GLOBALS.HOPLINK, "RES_REP.CAT"); + if (!f.exists(GLOBALS.NFICHIER)) + return PTRNUL; + + ptr = CHARGE_FICHIER(GLOBALS.NFICHIER); + CONSTRUIT_FICHIER(GLOBALS.HOPLINK, "RES_REP.RES"); + break; + + case 3: + CONSTRUIT_FICHIER(GLOBALS.HOPLINK, "RES_LIN.CAT"); + if (!f.exists(GLOBALS.NFICHIER)) + return PTRNUL; + + ptr = CHARGE_FICHIER(GLOBALS.NFICHIER); + CONSTRUIT_FICHIER(GLOBALS.HOPLINK, "RES_LIN.RES"); + break; + + case 4: + CONSTRUIT_FICHIER(GLOBALS.HOPANIM, "RES_ANI.CAT"); + if (!f.exists(GLOBALS.NFICHIER)) + return PTRNUL; + + ptr = CHARGE_FICHIER(GLOBALS.NFICHIER); + CONSTRUIT_FICHIER(GLOBALS.HOPANIM, "RES_ANI.RES"); + break; + + case 5: + CONSTRUIT_FICHIER(GLOBALS.HOPANIM, "RES_PER.CAT"); + if (!f.exists(GLOBALS.NFICHIER)) + return PTRNUL; + + ptr = CHARGE_FICHIER(GLOBALS.NFICHIER); + CONSTRUIT_FICHIER(GLOBALS.HOPANIM, "RES_PER.RES"); + break; + + case 6: + CONSTRUIT_FICHIER(GLOBALS.HOPIMAGE, "PIC.CAT"); + if (!f.exists(GLOBALS.NFICHIER)) + return PTRNUL; + + ptr = CHARGE_FICHIER(GLOBALS.NFICHIER); + break; + + case 7: + CONSTRUIT_FICHIER(GLOBALS.HOPANIM, "RES_SAN.CAT"); + if (!f.exists(GLOBALS.NFICHIER)) + return PTRNUL; + + ptr = CHARGE_FICHIER(GLOBALS.NFICHIER); + break; + + case 8: + CONSTRUIT_FICHIER(GLOBALS.HOPLINK, "RES_SLI.CAT"); + if (!f.exists(GLOBALS.NFICHIER)) + return PTRNUL; + + ptr = CHARGE_FICHIER(GLOBALS.NFICHIER); + break; + + case 9: + switch (GLOBALS.FR) { + case 0: + CONSTRUIT_FICHIER(GLOBALS.HOPLINK, "RES_VAN.CAT"); + break; + case 1: + CONSTRUIT_FICHIER(GLOBALS.HOPLINK, "RES_VFR.CAT"); + break; + case 2: + CONSTRUIT_FICHIER(GLOBALS.HOPLINK, "RES_VES.CAT"); + break; + } + + if (!f.exists(GLOBALS.NFICHIER)) + return PTRNUL; + + ptr = CHARGE_FICHIER(GLOBALS.NFICHIER); + break; + // Deliberate fall-through to + default: + break; + } + + // Scan for an entry in the catalogue + const byte *startP = ptr; + int result; // eax@50 + void *v22; // ebx@53 + bool matchFlag = false; + int offsetVal = 0; + + do { + Common::String name = (const char *)startP; + + if (file == name) { + // Found entry for file, so get it's details from the catalogue entry + const byte *pData = startP + offsetVal; + startP += offsetVal + 15; + GLOBALS.CAT_POSI = READ_LE_UINT32(pData + 15); + GLOBALS.CAT_TAILLE = READ_LE_UINT32(pData + 19); + matchFlag = true; + } + + const char *finishString = "FINIS"; + const char *nameP = name.c_str(); + int finishRemainingChars = 6; + int v19 = 0; + bool finishMatch = true; + + do { + if (!finishRemainingChars) + break; + finishMatch = *finishString++ == *nameP++; + --finishRemainingChars; + } while (finishMatch); + + if (!finishMatch) + v19 = *(byte *)(finishString - 1) - *(byte *)(nameP - 1); + if (!v19) { + GLOBALS.dos_free2(ptr); + return PTRNUL; + } + + offsetVal += 23; + } while (!matchFlag); + GLOBALS.dos_free2(ptr); + + // TODO: Double check whether this really should be an unsigned int comparison + if ((uint16)(a2 - 6) > 1 && (uint16)(a2 - 8) > 1) { + if (!f.open(GLOBALS.NFICHIER)) + error("CHARGE_FICHIER"); + + f.seek(GLOBALS.CAT_POSI); + + byte *catData = GLOBALS.dos_malloc2(GLOBALS.CAT_TAILLE); + if (catData == PTRNUL) + error("CHARGE_FICHIER"); + + bload_it(f, catData, GLOBALS.CAT_TAILLE); + f.close(); + result = true; + } else { + result = false; + } + + return result; +} + } // End of namespace Hopkins diff --git a/engines/hopkins/files.h b/engines/hopkins/files.h index 52412c11e8..8c8f01004d 100644 --- a/engines/hopkins/files.h +++ b/engines/hopkins/files.h @@ -43,6 +43,7 @@ public: static int CONSTRUIT_SYSTEM(const Common::String &file); static void CONSTRUIT_FICHIER(const Common::String &hop, const Common::String &file); static byte *LIBERE_FICHIER(byte *ptr); + static bool RECHERCHE_CAT(const Common::String &file, int a2); }; } // End of namespace Hopkins diff --git a/engines/hopkins/globals.cpp b/engines/hopkins/globals.cpp index 1f00651f9c..a04387e3a4 100644 --- a/engines/hopkins/globals.cpp +++ b/engines/hopkins/globals.cpp @@ -30,8 +30,6 @@ namespace Hopkins { Globals::Globals() { FR = 0; SVGA = 2; - MANU_SCROLL = 1; - SPEED_SCROLL = 16; internet = 1; PUBEXIT = 0; FADESPD = 15; @@ -658,4 +656,9 @@ byte *Globals::dos_malloc2(int count) { return result; } +byte *Globals::dos_free2(byte *p) { + free(p); + return PTRNUL; +} + } // End of namespace Hopkins diff --git a/engines/hopkins/globals.h b/engines/hopkins/globals.h index 3289a49575..8a10315cf7 100644 --- a/engines/hopkins/globals.h +++ b/engines/hopkins/globals.h @@ -111,8 +111,6 @@ public: int FADESPD; int FR; int SVGA; - int MANU_SCROLL; - int SPEED_SCROLL; int internet; int PUBEXIT; bool XFULLSCREEN; @@ -202,6 +200,8 @@ public: int OBJL, OBJH; int Nouv_objet; int HELICO; + uint32 CAT_POSI; + uint32 CAT_TAILLE; Globals(); ~Globals(); @@ -213,6 +213,7 @@ public: void INIT_VBOB(); void CHARGE_OBJET(); byte *dos_malloc2(int count); + byte *dos_free2(byte *p); }; #define PTRNUL (byte *)NULL diff --git a/engines/hopkins/graphics.cpp b/engines/hopkins/graphics.cpp index 21c5d6c478..385d9f46e8 100644 --- a/engines/hopkins/graphics.cpp +++ b/engines/hopkins/graphics.cpp @@ -21,6 +21,7 @@ */ #include "common/system.h" +#include "common/file.h" #include "common/rect.h" #include "engines/util.h" #include "hopkins/files.h" @@ -30,6 +31,614 @@ namespace Hopkins { +GraphicsManager::GraphicsManager() { + SDL_MODEYES = false; + MANU_SCROLL = 1; + SPEED_SCROLL = 16; + Agr_x = Agr_y = 0; + Agr_Flag_x = Agr_Flag_y = 0; +} + +GraphicsManager::~GraphicsManager() { +} + + +void GraphicsManager::SET_MODE(int width, int height) { + if (!SDL_MODEYES) { + SDL_ECHELLE = 0; + + if (GLOBALS.XSETMODE == 1) + SDL_ECHELLE = 0; + if (GLOBALS.XSETMODE == 2) + SDL_ECHELLE = 25; + if (GLOBALS.XSETMODE == 3) + SDL_ECHELLE = 50; + if (GLOBALS.XSETMODE == 4) + SDL_ECHELLE = 75; + if (GLOBALS.XSETMODE == 5) + SDL_ECHELLE = GLOBALS.XZOOM; + + int bpp = 8; + if (GLOBALS.XFORCE8 == 1) + bpp = 8; + if (GLOBALS.XFORCE16 == 1) + bpp = 16; + + if (SDL_ECHELLE) { + error("TODO: Implement zooming support"); + //width = Reel_Zoom(width, SDL_ECHELLE); + //height = Reel_Zoom(height, SDL_ECHELLE); + } + + if (bpp == 8) { + initGraphics(width, height, true); + } else { + Graphics::PixelFormat pixelFormat(2, 5, 5, 5, 0, 10, 5, 0, 0); + initGraphics(width, height, true, &pixelFormat); + } + + // Init surfaces + //VESA_SCREEN = dos_malloc2(0x96000u); + //VESA_BUFFER = dos_malloc2(0x96000u); + + VideoPtr = NULL; + XSCREEN = width; + YSCREEN = height; + + Linear = true; + Winbpp = bpp; + WinScan = width; + + PAL_PIXELS = SD_PIXELS; + nbrligne = width; + + for (int idx = 0; idx < 256; ++idx) { + cmap[idx].r = cmap[idx].g = cmap[idx].b = 0; + } + + SDL_MODEYES = true; + } else { + error("Called SET_MODE multiple times"); + } +} + +void GraphicsManager::DD_Lock() { + VideoPtr = g_system->lockScreen(); +} + +void GraphicsManager::DD_Unlock() { + g_system->unlockScreen(); +} + +void GraphicsManager::Cls_Video() { + assert(VideoPtr); + + VideoPtr->fillRect(Common::Rect(0, 0, XSCREEN, YSCREEN), 0); +} + +void GraphicsManager::LOAD_IMAGE(const Common::String &file) { + Common::String filename = Common::String::format("%s.PCX", file); + CHARGE_ECRAN(filename); + GraphicsManager::INIT_TABLE(165, 170, Palette); +} + +void GraphicsManager::CHARGE_ECRAN(const Common::String &file) { + int v1; + byte *v4; + byte *v5; + Common::File f; + + FileManager::DMESS1(); + + v1 = 1; + if (FileManager::RECHERCHE_CAT(file, 6)) { + FileManager::CONSTRUIT_FICHIER(GLOBALS.HOPIMAGE, file); + if (!f.open(GLOBALS.NFICHIER)) + error("CHARGE_ECRAN - %s", file.c_str()); + + f.seek(0, SEEK_END); + f.close(); + v1 = 0; + } + + SCROLL_ECRAN(0); + A_PCXSCREEN_WIDTH_SCREEN_HEIGHT((byte *)VESA_SCREEN.pixels, file, Palette, v1); + + SCROLL = 0; + OLD_SCROLL = 0; + Cls_Pal(); + + if (!DOUBLE_ECRAN) { + souris_max(); + SCANLINE(SCREEN_WIDTH); + GLOBALS.max_x = SCREEN_WIDTH; + DD_Lock(); + Cls_Video(); + if (Winbpp == 2) { + if (SDL_ECHELLE) + m_scroll16A((byte *)VESA_SCREEN.pixels, 0, 0, SCREEN_WIDTH, SCREEN_HEIGHT, 0, 0); + else + m_scroll16((byte *)VESA_SCREEN.pixels, 0, 0, SCREEN_WIDTH, SCREEN_HEIGHT, 0, 0); + } else if (Winbpp == 1) { + if (!SDL_ECHELLE) + m_scroll2((byte *)VESA_SCREEN.pixels, 0, 0, SCREEN_WIDTH, SCREEN_HEIGHT, 0, 0); + else + m_scroll2A((byte *)VESA_SCREEN.pixels, 0, 0, SCREEN_WIDTH, SCREEN_HEIGHT, 0, 0); + } + } else { + SCANLINE(0x500u); + GLOBALS.max_x = SCREEN_WIDTH * 2; + DD_Lock(); + Cls_Video(); + DD_Unlock(); + + if (MANU_SCROLL == 1) { + DD_Lock(); + if (Winbpp == 2) { + if (SDL_ECHELLE) + m_scroll16A((byte *)VESA_SCREEN.pixels, 0, 0, SCREEN_WIDTH, SCREEN_HEIGHT, 0, 0); + else + m_scroll16((byte *)VESA_SCREEN.pixels, 0, 0, SCREEN_WIDTH, SCREEN_HEIGHT, 0, 0); + } + if (Winbpp == 1) { + if (!SDL_ECHELLE) + m_scroll2((byte *)VESA_SCREEN.pixels, 0, 0, SCREEN_WIDTH, SCREEN_HEIGHT, 0, 0); + else + m_scroll2A((byte *)VESA_SCREEN.pixels, 0, 0, SCREEN_WIDTH, SCREEN_HEIGHT, 0, 0); + } + + DD_Unlock(); + } + } + + v4 = (byte *)VESA_BUFFER.pixels; + v5 = (byte *)VESA_SCREEN.pixels; + memcpy(v4, v5, 614396); + + v5 = (byte *)v5 + 614396; + v4 = (byte *)v4 + 614396; + WRITE_LE_UINT16(v4, READ_LE_UINT16(v5)); + *((byte *)v4 + 2) = *((byte *)v5 + 2); +} + +void GraphicsManager::INIT_TABLE(int a1, int a2, byte *a3) { + for (int idx = 0; idx < 256; ++idx) + TABLE_COUL[idx] = idx; + + Trans_bloc(TABLE_COUL, a3, 256, a1, a2); + + for (int idx = 0; idx < 256; ++idx) { + byte v = TABLE_COUL[idx]; + if (v > 27) + TABLE_COUL[idx] = 0; + if (!v) + TABLE_COUL[idx] = 0; + } + + TABLE_COUL[0] = 1; +} + +int GraphicsManager::SCROLL_ECRAN(int amount) { + int result = CLIP(amount, 0, SCREEN_WIDTH); + start_x = result; + ofscroll = result; + SCROLL = result; + return result; +} + +void GraphicsManager::Trans_bloc(byte *destP, byte *srcP, int count, int param1, int param2) { + byte *v5; + int v6; + int v7; + int v8; + unsigned int v11; + int v12; + int v13; + int v14; + int v15; + int v16; + int v17; + unsigned int v18; + char v19; + int v20; + bool breakFlag; + + v5 = destP; + v6 = count - 1; + do { + breakFlag = v6; + v7 = *(byte *)v5++; + v8 = (unsigned int)(3 * v7); + + // TODO: Ensure this is the right calculation + v11 = *(byte *)(v8 + srcP) + *(byte *)(v8 + srcP + 1) + + *(byte *)(v8 + srcP + 2); + + v12 = 0; + for (;;) { + v13 = v12 + 1; + if ( v13 == 38 ) + break; + + v20 = v13; + v8 = 3 * v8; + v14 = *(byte *)(v8 + srcP); + v15 = v14; + v14 = *(byte *)(v8 + srcP + 1); + v16 = v14 + v15; + v14 = *(byte *)(v8 + srcP + 2); + v17 = v14 + v16; + v12 = v20; + v18 = param1 + v17; + if (v18 >= v11 && (unsigned int)(v18 - param2) <= v11) { + v19 = v20; + if (!v20) + v19 = 1; + *(byte *)(v5 - 1) = v19; + break; + } + } + + v6 = breakFlag - 1; + } while ( !breakFlag); +} + +// TODO: See if it's feasible and/or desirable to change this to use the Common PCX decoder +void GraphicsManager::A_PCXSCREEN_WIDTH_SCREEN_HEIGHT(byte *surface, const Common::String &file, byte *palette, bool typeFlag) { + int filesize; + signed __int16 v6; + int v7; + __int16 v8; + int v9; + int v10; + int v11; + unsigned __int8 v12; + int v13; + int v14; + char v15; + int v18; + int v19; + int v20; + unsigned int v21; + int v22; + int32 v23; + byte *ptr; + Common::File f; + + // Clear the passed surface + memset(surface, 0, SCREEN_WIDTH * 2 * SCREEN_HEIGHT); + + if (typeFlag) { + FileManager::CONSTRUIT_FICHIER(GLOBALS.HOPIMAGE, "PIC.RES"); + if (!f.open(GLOBALS.NFICHIER)) + error("(nom)Erreur en cours de lecture."); + f.seek(GLOBALS.CAT_POSI); + + v7 = GLOBALS.CAT_TAILLE - 896; + v8 = f.read(HEADER_PCX, 128); + + v6 = READ_LE_UINT16(&HEADER_PCX[8]) + 1; + v20 = READ_LE_UINT16(&HEADER_PCX[10]) + 1; + if ((READ_LE_UINT16(&HEADER_PCX[8]) + 1) <= SCREEN_WIDTH) { + DOUBLE_ECRAN = false; + } else { + v6 = SCREEN_WIDTH * 2; + DOUBLE_ECRAN = true; + } + if (v20 > SCREEN_HEIGHT) + v20 = SCREEN_HEIGHT; + PCX_L = v6; + PCX_H = v20; + if (v8 == -1) + error("Erreur en cours de lecture."); + } else { + FileManager::CONSTRUIT_FICHIER(GLOBALS.HOPIMAGE, file); + if (!f.open(GLOBALS.NFICHIER)) + error("(nom)Erreur en cours de lecture."); + + filesize = f.size(); + int bytesRead = f.read(HEADER_PCX, 128); + if (bytesRead < 128) + error("Erreur en cours de lecture."); + + v6 = READ_LE_UINT16(&HEADER_PCX[8]) + 1; + v20 = READ_LE_UINT16(&HEADER_PCX[10]) + 1; + if (v6 <= SCREEN_WIDTH) { + DOUBLE_ECRAN = false; + } else { + v6 = SCREEN_WIDTH * 2; + DOUBLE_ECRAN = true; + } + if (v20 > SCREEN_HEIGHT) + v20 = SCREEN_HEIGHT; + PCX_L = v6; + PCX_H = v20; + v7 = filesize - 896; + } + + ptr = GLOBALS.dos_malloc2(0xEE60u); + if (v7 >= 60000) { + v21 = v7 / 60000 + 1; + v23 = 60000 * (v7 / 60000) - v7; + + if (((uint32)v23 & 0x80000000u) != 0) + v23 = -v23; + f.read(ptr, 60000); + v7 = 60000; + } else { + v21 = 1; + v23 = v7; + f.read(ptr, v7); + } + v22 = v21 - 1; + v18 = 0; + v9 = 0; + v10 = 0; + v19 = v6; + + do { + if (v9 == v7) { + v9 = 0; + --v22; + v7 = 60000; + if ( !v22 ) + v7 = v23; + v11 = v10; + f.read(ptr, v7); + v10 = v11; + } + + v12 = *((byte *)ptr + v9++); + if (v12 > 0xC0u) { + v13 = v12 - 192; + if (v9 == v7) { + v9 = 0; + --v22; + v7 = 60000; + if ( v22 == 1 ) + v7 = v23; + v14 = v10; + f.read(ptr, v7); + v10 = v14; + } + v15 = *((byte *)ptr + v9++); + + do { + *((byte *)surface + v10++) = v15; + ++v18; + --v13; + } while (v13); + } else { + *((byte *)surface + v10++) = v12; + ++v18; + } + } while (v18 < v19 * v20); + + if (typeFlag) { + f.seek(GLOBALS.CAT_TAILLE + GLOBALS.CAT_POSI - 768); + } else { + filesize = f.size(); + f.seek(filesize - 768); + } + + if (f.read(palette, PALETTE_SIZE * 3) != (PALETTE_SIZE * 3)) + error("A_PCXSCREEN_WIDTH_SCREEN_HEIGHT"); + + f.close(); + GLOBALS.dos_free2(ptr); +} + +void GraphicsManager::Cls_Pal() { + warning("TODO"); +} +void GraphicsManager::souris_max() { + warning("TODO"); +} + +void GraphicsManager::SCANLINE(int width) { + // Original has no implementatoin +} + +void GraphicsManager::m_scroll(const byte *surface, int xs, int ys, int width, int height, int destX, int destY) { + const byte *v7; + byte *v8; + int v9; + int v10; + byte *v11; + const byte *v12; + unsigned int v13; + + assert(VideoPtr); + v7 = xs + nbrligne2 * ys + surface; + v8 = destX + WinScan * destY + (byte *)VideoPtr->pixels; + v9 = height; + do { + v10 = v9; + memcpy((byte *)v8, (const byte *)v7, 4 * (width >> 2)); + v12 = (const byte *)(v7 + 4 * (width >> 2)); + v11 = (byte *)(v8 + 4 * (width >> 2)); + v13 = width - 4 * (width >> 2); + memcpy(v11, v12, v13); + v8 = ((byte *)v11 + v13 + WinScan - width); + v7 = ((byte *)v12 + v13 + nbrligne2 - width); + v9 = v10 - 1; + } while (v10 != 1); +} + +void GraphicsManager::m_scroll2(const byte *surface, int xs, int ys, int width, int height, int destX, int destY) { + const byte *v7; + byte *v8; + int v9; + int v10; + int v11; + + assert(VideoPtr); + v7 = (const byte *)(xs + nbrligne2 * ys + surface); + v8 = (byte *)(destX + WinScan * destY + (byte *)VideoPtr->pixels); + v9 = WinScan - SCREEN_WIDTH; + v10 = nbrligne2 - SCREEN_WIDTH; + v11 = height; + + do { + memcpy(v8, v7, SCREEN_WIDTH); + v8 = (byte *)v8 + v9 + SCREEN_WIDTH; + v7 = (const byte *)v7 + v10 + SCREEN_WIDTH; + --v11; + } while (v11); +} + +void GraphicsManager::m_scroll2A(const byte *surface, int xs, int ys, int width, int height, int destX, int destY) { + const byte *v7; + const byte *v8; + int v9; + int v10; + byte v11; + const byte *v12; + const byte *v13; + + assert(VideoPtr); + v7 = xs + nbrligne2 * ys + surface; + v8 = destX + WinScan * destY + (byte *)VideoPtr->pixels; + v9 = height; + Agr_x = 0; + Agr_y = 0; + Agr_Flag_y = 0; + do { + for (;;) { + v13 = v8; + v12 = v7; + v10 = width; + Agr_x = 0; + do { + v11 = *(byte *)v7; + *(byte *)v8++ = *(byte *)v7++; + Agr_x += SDL_ECHELLE; + if ((unsigned int)Agr_x >= 100) { + Agr_x -= 100; + *(byte *)v8++ = v11; + } + --v10; + } while ( v10 ); + + v7 = v12; + v8 = WinScan + v13; + if (Agr_Flag_y) + break; + + Agr_y += SDL_ECHELLE; + if ((unsigned int)Agr_y < 100) + break; + + Agr_y -= 100; + Agr_Flag_y = 1; + } + + Agr_Flag_y = 0; + v7 = nbrligne2 + v12; + --v9; + } while (v9); +} + +void GraphicsManager::m_scroll16(const byte *surface, int xs, int ys, int width, int height, int destX, int destY) { + const byte *v7; + const byte *v8; + int v9; + int v10; + const byte *v11; + int v12; + const byte *v13; + const byte *v14; + + assert(VideoPtr); + v7 = xs + nbrligne2 * ys + surface; + v8 = destX + destX + WinScan * destY + (byte *)VideoPtr->pixels; + v9 = height; + + do { + v14 = v8; + v13 = v7; + v10 = width; + v12 = v9; + v11 = PAL_PIXELS; + + do { + *(uint16 *)v8 = *(uint16 *)(v11 + 2 * *(byte *)v7++); + v8 += 2; + --v10; + } while (v10); + + v7 = nbrligne2 + v13; + v8 = WinScan + v14; + v9 = v12 - 1; + } while (v12 != 1); +} + +void GraphicsManager::m_scroll16A(const byte *surface, int xs, int ys, int width, int height, int destX, int destY) { + const byte *v7; + const byte *v8; + int v9; + int v10; + const byte *v11; + int v12; + int v13; + const byte *v14; + const byte *v15; + + assert(VideoPtr); + v7 = xs + nbrligne2 * ys + surface; + v8 = destX + destX + WinScan * destY + (byte *)VideoPtr->pixels; + v9 = height; + Agr_x = 0; + Agr_y = 0; + Agr_Flag_y = 0; + + do { + for (;;) { + v15 = v8; + v14 = v7; + v10 = width; + v13 = v9; + v11 = PAL_PIXELS; + Agr_x = 0; + + do { + v12 = *(uint16 *)(v11 + 2 * *(byte *)v7); + *(uint16 *)v8 = v12; + ++v7; + v8 += 2; + Agr_x += SDL_ECHELLE; + if ((unsigned int)Agr_x >= 100) { + Agr_x -= 100; + *(uint16 *)v8 = v12; + v8 += 2; + } + + --v10; + } while (v10); + + v9 = v13; + v7 = v14; + v8 = WinScan + v15; + if (Agr_Flag_y == 1) + break; + + Agr_y += SDL_ECHELLE; + + if ((unsigned int)Agr_y < 100) + break; + + Agr_y -= 100; + Agr_Flag_y = 1; + } + + Agr_Flag_y = 0; + v7 = nbrligne2 + v14; + v9 = v13 - 1; + } while (v13 != 1); +} + +/*------------------------------------------------------------------------*/ + byte *ObjectManager::CHANGE_OBJET(int objIndex) { byte *result = ObjectManager::CAPTURE_OBJET(objIndex, 1); GLOBALS.Bufferobjet = result; @@ -43,23 +652,23 @@ byte *ObjectManager::CAPTURE_OBJET(int objIndex, int mode) { byte *dataP; dataP = 0; - int v2 = GLOBALS.ObjetW[objIndex].field0; - int v3 = GLOBALS.ObjetW[objIndex].field1; + int val1 = GLOBALS.ObjetW[objIndex].field0; + int val2 = GLOBALS.ObjetW[objIndex].field1; if (mode == 1) - ++v3; - if (v2 != GLOBALS.NUM_FICHIER_OBJ) { + ++val2; + if (val1 != GLOBALS.NUM_FICHIER_OBJ) { if (GLOBALS.ADR_FICHIER_OBJ != PTRNUL) ObjectManager::DEL_FICHIER_OBJ(); - if (v2 == 1) { + if (val1 == 1) { FileManager::CONSTRUIT_SYSTEM("OBJET1.SPR"); GLOBALS.ADR_FICHIER_OBJ = ObjectManager::CHARGE_SPRITE(GLOBALS.NFICHIER); } - GLOBALS.NUM_FICHIER_OBJ = v2; + GLOBALS.NUM_FICHIER_OBJ = val1; } - int width = ObjectManager::Get_Largeur(GLOBALS.ADR_FICHIER_OBJ, v3); - int height = ObjectManager::Get_Hauteur(GLOBALS.ADR_FICHIER_OBJ, v3); + int width = ObjectManager::Get_Largeur(GLOBALS.ADR_FICHIER_OBJ, val2); + int height = ObjectManager::Get_Hauteur(GLOBALS.ADR_FICHIER_OBJ, val2); GLOBALS.OBJL = width; GLOBALS.OBJH = height; @@ -69,16 +678,16 @@ byte *ObjectManager::CAPTURE_OBJET(int objIndex, int mode) { if (dataP == PTRNUL) error("CAPTURE_OBJET"); - ObjectManager::capture_mem_sprite(GLOBALS.ADR_FICHIER_OBJ, dataP, v3); + ObjectManager::capture_mem_sprite(GLOBALS.ADR_FICHIER_OBJ, dataP, val2); break; case 1: - ObjectManager::sprite_alone(GLOBALS.ADR_FICHIER_OBJ, GLOBALS.Bufferobjet, v3); + ObjectManager::sprite_alone(GLOBALS.ADR_FICHIER_OBJ, GLOBALS.Bufferobjet, val2); result = GLOBALS.Bufferobjet; break; case 3: - ObjectManager::capture_mem_sprite(GLOBALS.ADR_FICHIER_OBJ, GLOBALS.INVENTAIRE_OBJET, v3); + ObjectManager::capture_mem_sprite(GLOBALS.ADR_FICHIER_OBJ, GLOBALS.INVENTAIRE_OBJET, val2); result = GLOBALS.INVENTAIRE_OBJET; break; @@ -162,83 +771,4 @@ int ObjectManager::AJOUTE_OBJET(int objIndex) { return arrIndex; } -/*------------------------------------------------------------------------*/ - -GraphicsManager::GraphicsManager() { - SDL_MODEYES = false; -} - -GraphicsManager::~GraphicsManager() { -} - - -void GraphicsManager::SET_MODE(int width, int height) { - if (!SDL_MODEYES) { - SDL_ECHELLE = 0; - - if (GLOBALS.XSETMODE == 1) - SDL_ECHELLE = 0; - if (GLOBALS.XSETMODE == 2) - SDL_ECHELLE = 25; - if (GLOBALS.XSETMODE == 3) - SDL_ECHELLE = 50; - if (GLOBALS.XSETMODE == 4) - SDL_ECHELLE = 75; - if (GLOBALS.XSETMODE == 5) - SDL_ECHELLE = GLOBALS.XZOOM; - - int bpp = 8; - if (GLOBALS.XFORCE8 == 1) - bpp = 8; - if (GLOBALS.XFORCE16 == 1) - bpp = 16; - - if (SDL_ECHELLE) { - error("TODO: Implement zooming support"); - //width = Reel_Zoom(a1, SDL_ECHELLE); - //height = Reel_Zoom(a2, SDL_ECHELLE); - } - - if (bpp == 8) { - initGraphics(width, height, true); - } else { - Graphics::PixelFormat pixelFormat(2, 5, 5, 5, 0, 10, 5, 0, 0); - initGraphics(width, height, true, &pixelFormat); - } - - VideoPtr = NULL; - XSCREEN = width; - YSCREEN = height; - - Linear = true; - Winbpp = bpp; - WinScan = width; - - PAL_PIXELS = SD_PIXELS; - nbrligne = width; - - for (int idx = 0; idx < 256; ++idx) { - cmap[idx].r = cmap[idx].g = cmap[idx].b = 0; - } - - SDL_MODEYES = true; - } else { - error("Called SET_MODE multiple times"); - } -} - -void GraphicsManager::DD_Lock() { - VideoPtr = g_system->lockScreen(); -} - -void GraphicsManager::DD_Unlock() { - g_system->unlockScreen(); -} - -void GraphicsManager::Cls_Video() { - assert(VideoPtr); - - VideoPtr->fillRect(Common::Rect(0, 0, XSCREEN, YSCREEN), 0); -} - } // End of namespace Hopkins diff --git a/engines/hopkins/graphics.h b/engines/hopkins/graphics.h index 18cb44254e..e6d56575f5 100644 --- a/engines/hopkins/graphics.h +++ b/engines/hopkins/graphics.h @@ -30,28 +30,17 @@ namespace Hopkins { +#define PALETTE_SIZE 256 + struct RGB8 { byte r; byte g; byte b; }; -class ObjectManager { -public: - static byte *CHANGE_OBJET(int objIndex); - static byte *CAPTURE_OBJET(int objIndex, int mode); - - static int Get_Largeur(const byte *objectData, int objIndex); - static int Get_Hauteur(const byte *objectData, int objIndex); - static int sprite_alone(const byte *objectData, byte *sprite, int objIndex); - static byte *DEL_FICHIER_OBJ(); - - static byte *CHARGE_SPRITE(const Common::String &file); - static int capture_mem_sprite(const byte *objectData, byte *sprite, int objIndex); - static int AJOUTE_OBJET(int objIndex); -}; - class GraphicsManager { +private: + void CHARGE_ECRAN(const Common::String &file); public: bool SDL_MODEYES; int SDL_ECHELLE; @@ -62,9 +51,26 @@ public: byte SD_PIXELS[514]; byte *PAL_PIXELS; int nbrligne; + byte TABLE_COUL[256]; RGB8 cmap[256]; + byte Palette[PALETTE_SIZE * 3]; bool Linear; Graphics::Surface *VideoPtr; + Graphics::Surface VESA_SCREEN; + Graphics::Surface VESA_BUFFER; + int start_x; + int ofscroll; + int SCROLL; + byte HEADER_PCX[128]; + int PCX_L, PCX_H; + bool DOUBLE_ECRAN; + int OLD_SCROLL; + int MANU_SCROLL; + int SPEED_SCROLL; + int nbrligne2; + int Agr_x, Agr_y; + int Agr_Flag_x, Agr_Flag_y; + public: GraphicsManager(); ~GraphicsManager(); @@ -73,6 +79,34 @@ public: void DD_Lock(); void DD_Unlock(); void Cls_Video(); + void LOAD_IMAGE(const Common::String &file); + void INIT_TABLE(int a1, int a2, byte *a3); + int SCROLL_ECRAN(int amount); + void Trans_bloc(byte *destP, byte *srcP, int count, int param1, int param2); + void A_PCXSCREEN_WIDTH_SCREEN_HEIGHT(byte *surface, const Common::String &file, byte *palette, bool typeFlag); + void Cls_Pal(); + void souris_max(); + void SCANLINE(int width); + void m_scroll(const byte *surface, int xs, int ys, int width, int height, int destX, int destY); + void m_scroll2(const byte *surface, int xs, int ys, int width, int height, int destX, int destY); + void m_scroll2A(const byte *surface, int xs, int ys, int width, int height, int destX, int destY); + void m_scroll16(const byte *surface, int xs, int ys, int width, int height, int destX, int destY); + void m_scroll16A(const byte *surface, int xs, int ys, int width, int height, int destX, int destY); +}; + +class ObjectManager { +public: + static byte *CHANGE_OBJET(int objIndex); + static byte *CAPTURE_OBJET(int objIndex, int mode); + + static int Get_Largeur(const byte *objectData, int objIndex); + static int Get_Hauteur(const byte *objectData, int objIndex); + static int sprite_alone(const byte *objectData, byte *sprite, int objIndex); + static byte *DEL_FICHIER_OBJ(); + + static byte *CHARGE_SPRITE(const Common::String &file); + static int capture_mem_sprite(const byte *objectData, byte *sprite, int objIndex); + static int AJOUTE_OBJET(int objIndex); }; } // End of namespace Hopkins diff --git a/engines/hopkins/hopkins.cpp b/engines/hopkins/hopkins.cpp index af8cd668ef..0dd1fbc03b 100644 --- a/engines/hopkins/hopkins.cpp +++ b/engines/hopkins/hopkins.cpp @@ -43,9 +43,6 @@ HopkinsEngine::~HopkinsEngine() { } Common::Error HopkinsEngine::run() { -// char v1; // al@93 -// char v2; // al@114 - FileManager::initSaves(); Common::StringMap iniParams; @@ -69,8 +66,9 @@ Common::Error HopkinsEngine::run() { _graphicsManager.DD_Lock(); _graphicsManager.Cls_Video(); _graphicsManager.DD_Unlock(); + + _graphicsManager.LOAD_IMAGE("LINUX"); /* - LOAD_IMAGE("LINUX"); FADE_INW(); SDL_Delay(1500); FADE_OUTW(); @@ -503,9 +501,6 @@ void HopkinsEngine::INIT_SYSTEM() { // Set graphics mode _graphicsManager.SET_MODE(640, 480); - // TODO: init surfaces - //VESA_SCREEN = dos_malloc2(0x96000u); - //VESA_BUFFER = dos_malloc2(0x96000u); _mouse.mouse_linux = true; switch (GLOBALS.FR) { diff --git a/engines/hopkins/hopkins.h b/engines/hopkins/hopkins.h index 5f6b19d47a..1a2e6961b2 100644 --- a/engines/hopkins/hopkins.h +++ b/engines/hopkins/hopkins.h @@ -57,14 +57,15 @@ enum { #define DEBUG_INTERMEDIATE 2 #define DEBUG_DETAILED 3 +#define SCREEN_WIDTH 640 +#define SCREEN_HEIGHT 480 + struct HopkinsGameDescription; class HopkinsEngine : public Engine { private: const HopkinsGameDescription *_gameDescription; Common::RandomSource _randomSource; - Graphics::Surface VESA_SCREEN; - Graphics::Surface VESA_BUFFER; Mouse _mouse; GraphicsManager _graphicsManager; |