diff options
author | Strangerke | 2016-11-27 14:45:28 -0800 |
---|---|---|
committer | Eugene Sandulenko | 2017-01-25 22:42:08 +0100 |
commit | 61998c7a996a52e6988c48275e3a784aa9a2901a (patch) | |
tree | b8a4b8792af26f4a343aa0df81c37932dda6a746 /engines | |
parent | b735962436c2f33a877f623d92b61a4a46680fb3 (diff) | |
download | scummvm-rg350-61998c7a996a52e6988c48275e3a784aa9a2901a.tar.gz scummvm-rg350-61998c7a996a52e6988c48275e3a784aa9a2901a.tar.bz2 scummvm-rg350-61998c7a996a52e6988c48275e3a784aa9a2901a.zip |
CRYO: Move some more functions to HnmPlayer
Diffstat (limited to 'engines')
-rw-r--r-- | engines/cryo/clhnm.cpp | 338 | ||||
-rw-r--r-- | engines/cryo/cryolib.h | 14 | ||||
-rw-r--r-- | engines/cryo/eden.cpp | 12 | ||||
-rw-r--r-- | engines/cryo/video.cpp | 373 | ||||
-rw-r--r-- | engines/cryo/video.h | 16 |
5 files changed, 383 insertions, 370 deletions
diff --git a/engines/cryo/clhnm.cpp b/engines/cryo/clhnm.cpp index 0881126197..1e67001d30 100644 --- a/engines/cryo/clhnm.cpp +++ b/engines/cryo/clhnm.cpp @@ -26,152 +26,8 @@ namespace Cryo { -static bool safe_palette = false; static bool use_mono = false; -void CLHNM_Desentrelace320(byte *frame_buffer, byte *final_buffer, uint16 height); - -void CLHNM_DecompLempelZiv(byte *buffer, byte *output) { - byte *inp = buffer; - byte *out = output; - - unsigned int queue = 0; - int qpos = -1; - - //TODO: fix for BE -#define GetBit() ( 1 & ( (qpos >= 0) ? (queue >> qpos--) : (queue = *(unsigned int*)((inp += 4) - 4)) >> ((qpos = 30) + 1) ) ) - - for (;;) { - if (GetBit()) { - *out++ = *inp++; - } else { - int l, o; - if (GetBit()) { - l = *inp & 7; - o = *(uint16 *)inp >> 3; - inp += 2; - o -= 8192; - if (!l) - l = *inp++; - if (!l) - break; - } else { - l = GetBit() * 2 + GetBit(); - o = *(inp++) - 256; - } - l += 2; - while (l--) { - *out = *(out + o); - out++; - } - } - } - -#undef GetBit - - return; -} - -void CLHNM_DecompUBA(byte *output, byte *curr_buffer, byte *prev_buffer, - byte *input, int width, char flags) { - unsigned int code; - byte mode, count, color; - uint16 offs; - byte *ref; - byte *out_start = output; - byte swap; - int shft1, shft2; -// return; - if ((flags & 1) == 0) { - //HNM4 classic - int twolinesabove = -(width * 2); - for (;;) { - code = PLE32(input) & 0xFFFFFF; //input++; - count = code & 0x1F; - if (count) { - input += 3; - mode = (code >> 5) & 0xF; - offs = code >> 9; - // - swap = mode >> 3; - ref = ((mode & 1) ? prev_buffer : curr_buffer) + (output - out_start) + (offs * 2) - 32768; - if (mode & 2) { - // ref += twolinesabove; - shft1 = twolinesabove + 1; - shft2 = 0; - //swap ^= 1; - } else { - shft1 = 0; - shft2 = 1; - } - while (count--) { - byte b0 = ref[shft1]; - byte b1 = ref[shft2]; - output[swap] = b0; - output[swap ^ 1] = b1; - output += 2; - ref += (mode & 4) ? -2 : 2; - } - } else { - input++; - mode = code & 0xFF; // bits 0..4 are zero - switch (mode) { - case 0: - *(output++) = *(input++); - *(output++) = *(input++); - break; - case 0x20: - output += 2 * *(input++); - break; - case 0x40: - output += 2 * (code >> 8); - input += 2; - break; - case 0x60: - count = *(input++); - color = *(input++); - while (count--) { - *(output++) = color; - *(output++) = color; - } - break; - default: - return; - } - } - } - } else { - assert(0); - //HNM4 hires - for (;;) { - code = PLE32(input) & 0xFFFFFF; - input++; - count = code & 0x3F; - if (count) { - mode = (code >> 5) & 0xF; - offs = code >> 9; - // - } else { - mode = code & 0xFF; // bits 0..5 are zero - switch (mode) { - case 0x00: - output += *input++; - break; - case 0x40: - *output++ = *input++; - *(output++ + width) = *input++; - break; - case 0x80: - output += width; - break; - default: - return; - } - } - } - } -} - void CLHNM_Done() { } @@ -206,43 +62,6 @@ void CLHNM_SetFile(hnm_t *hnm, file_t *file) { hnm->_file = file; } -void CLHNM_SetFinalBuffer(hnm_t *hnm, byte *buffer) { - hnm->finalBuffer = buffer; -} - -void CLHNM_AllocMemory(hnm_t *hnm) { - hnm->tmpBuffer[0] = (byte *)malloc(hnm->_header._bufferSize + 2); - - if (!hnm->tmpBuffer[0]) - return; - - hnm->tmpBuffer[1] = (byte *)malloc(hnm->_header._bufferSize + 2); - - if (!hnm->tmpBuffer[1]) { - free(hnm->tmpBuffer[0]); - hnm->tmpBuffer[0] = nullptr; - return; - } - - hnm->_readBuffer = (byte *)malloc(hnm->_header._bufferSize + 2); - if (!hnm->_readBuffer) { - free(hnm->tmpBuffer[0]); - hnm->tmpBuffer[0] = nullptr; - free(hnm->tmpBuffer[1]); - hnm->tmpBuffer[1] = nullptr; - } -} - -void CLHNM_DeallocMemory(hnm_t *hnm) { - free(hnm->tmpBuffer[0]); - free(hnm->tmpBuffer[1]); - free(hnm->_readBuffer); - - hnm->tmpBuffer[0] = nullptr; - hnm->tmpBuffer[1] = nullptr; - hnm->_readBuffer = nullptr; -} - void CLHNM_GiveTime(hnm_t *hnm) { } @@ -250,165 +69,8 @@ void CLHNM_CanLoop(hnm_t *hnm, bool canLoop) { hnm->_canLoop = canLoop; } -void CLHNM_SelectBuffers(hnm_t *hnm) { - if (hnm->_frameNum % 2) { - hnm->_newFrameBuffer = hnm->tmpBuffer[1]; - hnm->_oldFrameBuffer = hnm->tmpBuffer[0]; - } else { - hnm->_newFrameBuffer = hnm->tmpBuffer[0]; - hnm->_oldFrameBuffer = hnm->tmpBuffer[1]; - } -} - -void CLHNM_ChangePalette(hnm_t *hnm) { - int16 mincolor, maxcolor; - uint16 fst, cnt; - byte *pal; - color_t *color; - CLPalette_GetLastPalette(hnm->_palette); - pal = hnm->_dataPtr; - if (*(uint16 *)pal == 0xFFFF) - return; - mincolor = 255; - maxcolor = 0; - do { - fst = *pal++; - cnt = *pal++; - if (cnt == 0) - cnt = 256; - debug("hnm: setting palette, fst = %d, cnt = %d, last = %d", fst, cnt, fst + cnt - 1); - assert(fst + cnt <= 256); - if (mincolor > fst) - mincolor = fst; - if (maxcolor < fst + cnt) - maxcolor = fst + cnt; - color = hnm->_palette + fst; - if (safe_palette) { - while (cnt--) { - byte r = *pal++; - byte g = *pal++; - byte b = *pal++; - int16 rr = r << 10; - int16 gg = g << 10; - int16 bb = b << 10; - if (color->r != rr || color->g != gg || color->b != bb) - CLBlitter_OneBlackFlash(); - color->r = rr; - color->g = gg; - color->b = bb; - color++; - } - } else { - while (cnt--) { - byte r = *pal++; - byte g = *pal++; - byte b = *pal++; - color->r = r << 10; - color->g = g << 10; - color->b = b << 10; - color++; - } - } - - } while (*(uint16 *)pal != 0xFFFF); -#if 0 - if (preserve_color0) { - hnm->palette[0].r = 0; - hnm->palette[0].g = 0; - hnm->palette[0].b = 0; - } -#endif -// CLBlitter_Send2ScreenNextCopy(hnm->palette, mincolor, maxcolor - mincolor); - CLBlitter_Send2ScreenNextCopy(hnm->_palette, 0, 256); -} - -void CLHNM_Desentrelace(hnm_t *hnm) { - switch (hnm->_header._width) { - case 320: - CLHNM_Desentrelace320(hnm->_newFrameBuffer, hnm->finalBuffer, hnm->_header._height); - break; -// case 480: -// CLHNM_Desentrelace480(hnm->new_frame_buffer, hnm->final_buffer, hnm->header.height); -// break; - default: - error("CLHNM_Desentrelace - Unexpected width"); - } -} - -void CLHNM_TryRead(hnm_t *hnm, int size) { - hnm->_file->read(hnm->_readBuffer, size); -} - -bool CLHNM_LoadFrame(hnm_t *hnm) { - int chunk; - CLHNM_TryRead(hnm, 4); - chunk = *(int *)hnm->_readBuffer; - chunk = LE32(chunk); - chunk &= 0xFFFFFF; // upper bit - keyframe mark? - if (!chunk) - return false; - - if (chunk - 4 > hnm->_header._bufferSize) - error("CLHNM_LoadFrame - Chunk size"); - - CLHNM_TryRead(hnm, chunk - 4); - hnm->_dataPtr = hnm->_readBuffer; - hnm->_totalRead += chunk; - return true; -} - void CLHNM_SoundMono(bool isMono) { use_mono = isMono; } -void CLHNM_ReadHeader(hnm_t *hnm) { - int32 size = sizeof(hnm->_header); - hnm->_file->read(&hnm->_header, size); - - hnm->_header._width = LE16(hnm->_header._width); - hnm->_header._height = LE16(hnm->_header._height); - hnm->_header._unusedFileSize = LE32(hnm->_header._unusedFileSize); - hnm->_header._numbFrame = LE32(hnm->_header._numbFrame); - hnm->_header._unusedTableOffset = LE32(hnm->_header._unusedTableOffset); - hnm->_header._unusedSpeed = LE16(hnm->_header._unusedSpeed); - hnm->_header._unusedMaxBuffer = LE16(hnm->_header._unusedMaxBuffer); - hnm->_header._bufferSize = LE32(hnm->_header._bufferSize); - hnm->_header._unusedUnknown = LE16(hnm->_header._unusedUnknown); - hnm->_header._bufferSize += 4096; //TODO: checkme -} - -int16 CLHNM_GetVersion(hnm_t *hnm) { - if (hnm->_header._signature == BE32('HNM4')) - return 4; - return -1; -} - -int CLHNM_GetFrameNum(hnm_t *hnm) { - return hnm->_frameNum; -} - -void CLHNM_Desentrelace320(byte *frame_buffer, byte *final_buffer, uint16 height) { - unsigned int *input = (unsigned int *)frame_buffer; - unsigned int *line0 = (unsigned int *)final_buffer; - unsigned int *line1 = (unsigned int *)(final_buffer + 320); - int count = (height) / 2; - while (count--) { - int16 i; - for (i = 0; i < 320 / 4; i++) { - unsigned int p0 = *input++; - unsigned int p4 = *input++; -#if 0 - *line0++ = ((p4 & 0xFF00) >> 8) | ((p4 & 0xFF000000) >> 16) | ((p0 & 0xFF00) << 8) | (p0 & 0xFF000000); -// *line0++ = (p0 & 0xFF000000) | ((p0 & 0xFF00) << 8) | ((p4 & 0xFF000000) >> 16) | ((p4 & 0xFF00) >> 8); - *line1++ = ((p0 & 0xFF0000) << 8) | ((p0 & 0xFF) << 16) | ((p4 & 0xFF0000) >> 8) | (p4 & 0xFF); -#else - *line0++ = (p0 & 0xFF) | ((p0 & 0xFF0000) >> 8) | ((p4 & 0xFF) << 16) | ((p4 & 0xFF0000) << 8); - *line1++ = ((p0 & 0xFF00) >> 8) | ((p0 & 0xFF000000) >> 16) | ((p4 & 0xFF00) << 8) | (p4 & 0xFF000000); -#endif - } - line0 += 320 / 4; - line1 += 320 / 4; - } -} - } // End of namespace Cryo diff --git a/engines/cryo/cryolib.h b/engines/cryo/cryolib.h index 2daed71034..4c2d81965f 100644 --- a/engines/cryo/cryolib.h +++ b/engines/cryo/cryolib.h @@ -252,27 +252,13 @@ void CLScreenView_CenterIn(View *view); void CRYOLib_ManagersInit(); void CRYOLib_ManagersDone(); -void CLHNM_DecompLempelZiv(byte *buffer, byte *output); -void CLHNM_DecompUBA(byte *output, byte *curr_buffer, byte *prev_buffer, - byte *input, int width, char flags); void CLHNM_Done(); hnm_t *CLHNM_New(int preload_size); void CLHNM_Dispose(hnm_t *hnm); void CLHNM_SetFile(hnm_t *hnm, file_t *file); -void CLHNM_SetFinalBuffer(hnm_t *hnm, byte *buffer); -void CLHNM_AllocMemory(hnm_t *hnm); -void CLHNM_DeallocMemory(hnm_t *hnm); void CLHNM_CanLoop(hnm_t *hnm, bool canLoop); -void CLHNM_SelectBuffers(hnm_t *hnm); -void CLHNM_ChangePalette(hnm_t *hnm); -void CLHNM_Desentrelace(hnm_t *hnm); -bool CLHNM_LoadFrame(hnm_t *hnm); void CLHNM_WantsSound(int16 sound); void CLHNM_SoundMono(int16 is_mono); -void CLHNM_ReadHeader(hnm_t *hnm); -int16 CLHNM_GetVersion(hnm_t *hnm); -int CLHNM_GetFrameNum(hnm_t *hnm); -void CLHNM_Desentrelace320(byte *frame_buffer, byte *final_buffer, uint16 height); } // End of namespace Cryo diff --git a/engines/cryo/eden.cpp b/engines/cryo/eden.cpp index 3c11a5785c..1541562354 100644 --- a/engines/cryo/eden.cpp +++ b/engines/cryo/eden.cpp @@ -6207,18 +6207,18 @@ void EdenGame::mouse() { ////// film.c // Original name: showfilm void EdenGame::showMovie(char arg1) { - CLHNM_ReadHeader(_hnmContext); + _vm->_video->readHeader(_hnmContext); if (_vm->_video->curVideoNum == 92) { // _hnmContext->_header._unusedFlag2 = 0; CHECKME: Useless? CLSoundChannel_SetVolumeLeft(_hnmSoundChannel, 0); CLSoundChannel_SetVolumeRight(_hnmSoundChannel, 0); } - if (CLHNM_GetVersion(_hnmContext) != 4) + if (_vm->_video->getVersion(_hnmContext) != 4) return; bool playing = true; - CLHNM_AllocMemory(_hnmContext); + _vm->_video->allocMemory(_hnmContext); p_hnmview = CLView_New(_hnmContext->_header._width, _hnmContext->_header._height); CLView_SetSrcZoomValues(p_hnmview, 0, 0); CLView_SetDisplayZoomValues(p_hnmview, _hnmContext->_header._width * 2, _hnmContext->_header._height * 2); @@ -6230,10 +6230,10 @@ void EdenGame::showMovie(char arg1) { p_hnmview->_normal._dstTop = p_mainview->_normal._dstTop + 16; p_hnmview->_zoom._dstTop = p_mainview->_zoom._dstTop + 32; } - CLHNM_SetFinalBuffer(_hnmContext, p_hnmview->_bufferPtr); + _vm->_video->setFinalBuffer(_hnmContext, p_hnmview->_bufferPtr); p_hnmview->_doubled = _doubledScreen; do { - hnm_position = CLHNM_GetFrameNum(_hnmContext); + hnm_position = _vm->_video->getFrameNum(_hnmContext); _vm->_video->waitLoop(_hnmContext); playing = _vm->_video->nextElement(_hnmContext); if (specialTextMode) @@ -6265,7 +6265,7 @@ void EdenGame::showMovie(char arg1) { } } while (playing && !videoCanceled); CLView_Free(p_hnmview); - CLHNM_DeallocMemory(_hnmContext); + _vm->_video->deallocMemory(_hnmContext); } void EdenGame::playHNM(int16 num) { diff --git a/engines/cryo/video.cpp b/engines/cryo/video.cpp index ab2bf4efc1..128c9815ee 100644 --- a/engines/cryo/video.cpp +++ b/engines/cryo/video.cpp @@ -42,6 +42,7 @@ HnmPlayer::HnmPlayer(CryoEngine *vm) : _vm(vm) { use_adpcm = false; custom_chunk_handler = nullptr; preserve_color0 = false; + safe_palette = false; for (int i = 0; i < 256; i++) decomp_table[i] = 0; @@ -152,12 +153,286 @@ void HnmPlayer::decompADPCM(byte *buffer, int16 *output, int size) { *output++ = l += decomp_table[*buffer++]; *output++ = r += decomp_table[*buffer++]; if (l > 512 || r > 512) - error("CLHNM_DecompADPCM - Unexpected values"); + error("decompADPCM - Unexpected values"); } pred_l = l; pred_r = r; } +// Original name: CLHNM_ReadHeader +void HnmPlayer::readHeader(hnm_t *hnm) { + int32 size = sizeof(hnm->_header); + hnm->_file->read(&hnm->_header, size); + + hnm->_header._width = LE16(hnm->_header._width); + hnm->_header._height = LE16(hnm->_header._height); + hnm->_header._unusedFileSize = LE32(hnm->_header._unusedFileSize); + hnm->_header._numbFrame = LE32(hnm->_header._numbFrame); + hnm->_header._unusedTableOffset = LE32(hnm->_header._unusedTableOffset); + hnm->_header._unusedSpeed = LE16(hnm->_header._unusedSpeed); + hnm->_header._unusedMaxBuffer = LE16(hnm->_header._unusedMaxBuffer); + hnm->_header._bufferSize = LE32(hnm->_header._bufferSize); + hnm->_header._unusedUnknown = LE16(hnm->_header._unusedUnknown); + hnm->_header._bufferSize += 4096; //TODO: checkme +} + +// Original name: CLHNM_GetVersion +int16 HnmPlayer::getVersion(hnm_t *hnm) { + if (hnm->_header._signature == BE32('HNM4')) + return 4; + return -1; +} + +// Original name: CLHNM_AllocMemory +void HnmPlayer::allocMemory(hnm_t *hnm) { + hnm->tmpBuffer[0] = (byte *)malloc(hnm->_header._bufferSize + 2); + + if (!hnm->tmpBuffer[0]) + return; + + hnm->tmpBuffer[1] = (byte *)malloc(hnm->_header._bufferSize + 2); + + if (!hnm->tmpBuffer[1]) { + free(hnm->tmpBuffer[0]); + hnm->tmpBuffer[0] = nullptr; + return; + } + + hnm->_readBuffer = (byte *)malloc(hnm->_header._bufferSize + 2); + if (!hnm->_readBuffer) { + free(hnm->tmpBuffer[0]); + hnm->tmpBuffer[0] = nullptr; + free(hnm->tmpBuffer[1]); + hnm->tmpBuffer[1] = nullptr; + } +} + +// Original name: CLHNM_DeallocMemory +void HnmPlayer::deallocMemory(hnm_t *hnm) { + free(hnm->tmpBuffer[0]); + free(hnm->tmpBuffer[1]); + free(hnm->_readBuffer); + + hnm->tmpBuffer[0] = nullptr; + hnm->tmpBuffer[1] = nullptr; + hnm->_readBuffer = nullptr; +} + +// Original name: CLHNM_SetFinalBuffer +void HnmPlayer::setFinalBuffer(hnm_t *hnm, byte *buffer) { + hnm->finalBuffer = buffer; +} + +// Original name: CLHNM_GetFrameNum +int HnmPlayer::getFrameNum(hnm_t *hnm) { + return hnm->_frameNum; +} + +// Original name: CLHNM_TryRead +void HnmPlayer::tryRead(hnm_t *hnm, int size) { + hnm->_file->read(hnm->_readBuffer, size); +} + +// Original name: CLHNM_LoadFrame +bool HnmPlayer::loadFrame(hnm_t *hnm) { + int chunk; + tryRead(hnm, 4); + chunk = *(int *)hnm->_readBuffer; + chunk = LE32(chunk); + chunk &= 0xFFFFFF; // upper bit - keyframe mark? + if (!chunk) + return false; + + if (chunk - 4 > hnm->_header._bufferSize) + error("loadFrame - Chunk size"); + + tryRead(hnm, chunk - 4); + hnm->_dataPtr = hnm->_readBuffer; + hnm->_totalRead += chunk; + return true; +} + +// Original name CLHNM_DecompLempelZiv +void HnmPlayer::decompLempelZiv(byte *buffer, byte *output) { + byte *inp = buffer; + byte *out = output; + + unsigned int queue = 0; + int qpos = -1; + + //TODO: fix for BE +#define GetBit() ( 1 & ( (qpos >= 0) ? (queue >> qpos--) : (queue = *(unsigned int*)((inp += 4) - 4)) >> ((qpos = 30) + 1) ) ) + + for (;;) { + if (GetBit()) { + *out++ = *inp++; + } else { + int l, o; + if (GetBit()) { + l = *inp & 7; + o = *(uint16 *)inp >> 3; + inp += 2; + o -= 8192; + if (!l) + l = *inp++; + if (!l) + break; + } else { + l = GetBit() * 2 + GetBit(); + o = *(inp++) - 256; + } + l += 2; + while (l--) { + *out = *(out + o); + out++; + } + } + } + +#undef GetBit + + return; +} + +// Original name: CLHNM_Desentrelace320 +void HnmPlayer::desentrelace320(byte *frame_buffer, byte *final_buffer, uint16 height) { + unsigned int *input = (unsigned int *)frame_buffer; + unsigned int *line0 = (unsigned int *)final_buffer; + unsigned int *line1 = (unsigned int *)(final_buffer + 320); + int count = (height) / 2; + while (count--) { + int16 i; + for (i = 0; i < 320 / 4; i++) { + unsigned int p0 = *input++; + unsigned int p4 = *input++; +#if 0 + *line0++ = ((p4 & 0xFF00) >> 8) | ((p4 & 0xFF000000) >> 16) | ((p0 & 0xFF00) << 8) | (p0 & 0xFF000000); + // *line0++ = (p0 & 0xFF000000) | ((p0 & 0xFF00) << 8) | ((p4 & 0xFF000000) >> 16) | ((p4 & 0xFF00) >> 8); + *line1++ = ((p0 & 0xFF0000) << 8) | ((p0 & 0xFF) << 16) | ((p4 & 0xFF0000) >> 8) | (p4 & 0xFF); +#else + *line0++ = (p0 & 0xFF) | ((p0 & 0xFF0000) >> 8) | ((p4 & 0xFF) << 16) | ((p4 & 0xFF0000) << 8); + *line1++ = ((p0 & 0xFF00) >> 8) | ((p0 & 0xFF000000) >> 16) | ((p4 & 0xFF00) << 8) | (p4 & 0xFF000000); +#endif + } + line0 += 320 / 4; + line1 += 320 / 4; + } +} + +// Original name: CLHNM_Desentrelace +void HnmPlayer::desentrelace(hnm_t *hnm) { + switch (hnm->_header._width) { + case 320: + desentrelace320(hnm->_newFrameBuffer, hnm->finalBuffer, hnm->_header._height); + break; + // case 480: + // CLHNM_Desentrelace480(hnm->new_frame_buffer, hnm->final_buffer, hnm->header.height); + // break; + default: + error("desentrelace - Unexpected width"); + } +} + +// Original name: CLHNM_DecompUBA +void HnmPlayer::decompUBA(byte *output, byte *curr_buffer, byte *prev_buffer, byte *input, int width, char flags) { + unsigned int code; + byte mode, count, color; + uint16 offs; + byte *ref; + byte *out_start = output; + byte swap; + int shft1, shft2; + // return; + if ((flags & 1) == 0) { + //HNM4 classic + int twolinesabove = -(width * 2); + for (;;) { + code = PLE32(input) & 0xFFFFFF; //input++; + count = code & 0x1F; + if (count) { + input += 3; + mode = (code >> 5) & 0xF; + offs = code >> 9; + // + swap = mode >> 3; + ref = ((mode & 1) ? prev_buffer : curr_buffer) + (output - out_start) + (offs * 2) - 32768; + if (mode & 2) { + // ref += twolinesabove; + shft1 = twolinesabove + 1; + shft2 = 0; + //swap ^= 1; + } else { + shft1 = 0; + shft2 = 1; + } + while (count--) { + byte b0 = ref[shft1]; + byte b1 = ref[shft2]; + output[swap] = b0; + output[swap ^ 1] = b1; + output += 2; + ref += (mode & 4) ? -2 : 2; + } + } else { + input++; + mode = code & 0xFF; // bits 0..4 are zero + switch (mode) { + case 0: + *(output++) = *(input++); + *(output++) = *(input++); + break; + case 0x20: + output += 2 * *(input++); + break; + case 0x40: + output += 2 * (code >> 8); + input += 2; + break; + case 0x60: + count = *(input++); + color = *(input++); + while (count--) { + *(output++) = color; + *(output++) = color; + } + break; + default: + return; + } + } + } + } else { + assert(0); + //HNM4 hires + for (;;) { + code = PLE32(input) & 0xFFFFFF; + input++; + count = code & 0x3F; + if (count) { + mode = (code >> 5) & 0xF; + offs = code >> 9; + // + } else { + mode = code & 0xFF; // bits 0..5 are zero + switch (mode) { + case 0x00: + output += *input++; + break; + case 0x40: + *output++ = *input++; + *(output++ + width) = *input++; + break; + case 0x80: + output += width; + break; + default: + return; + } + } + } + } +} + // Original name: CLHNM_NextElement bool HnmPlayer::nextElement(hnm_t *hnm) { int sz; @@ -171,7 +446,7 @@ bool HnmPlayer::nextElement(hnm_t *hnm) { if (hnm->_frameNum == hnm->_header._numbFrame) return false; - if (!CLHNM_LoadFrame(hnm)) + if (!loadFrame(hnm)) return false; for (;;) { @@ -186,23 +461,23 @@ bool HnmPlayer::nextElement(hnm_t *hnm) { hnm->_chunkId = id; switch (id) { case BE16('PL'): - CLHNM_ChangePalette(hnm); + changePalette(hnm); hnm->_dataPtr += sz - 8; break; case BE16('IZ'): hnm->_frameNum++; - CLHNM_SelectBuffers(hnm); - CLHNM_DecompLempelZiv(hnm->_dataPtr + 4, hnm->_newFrameBuffer); + selectBuffers(hnm); + decompLempelZiv(hnm->_dataPtr + 4, hnm->_newFrameBuffer); switch (hnm->_header._width) { // case 320: CLBlitter_RawCopy320ASM(hnm->new_frame_buffer, hnm->old_frame_buffer, hnm->header.height); break; // case 480: CLBlitter_RawCopy480ASM(hnm->new_frame_buffer, hnm->old_frame_buffer, hnm->header.height); break; // case 640: CLBlitter_RawCopy640ASM(hnm->new_frame_buffer, hnm->old_frame_buffer, hnm->header.height); break; // default: memcpy(hnm->old_frame_buffer, hnm->new_frame_buffer, hnm->header.width * hnm->header.height); - default: - memcpy(hnm->_oldFrameBuffer, hnm->_newFrameBuffer, hnm->_header._bufferSize); //TODO strange buffer size here + default: + memcpy(hnm->_oldFrameBuffer, hnm->_newFrameBuffer, hnm->_header._bufferSize); //TODO strange buffer size here } if (!(h6 & 1)) - CLHNM_Desentrelace(hnm); + desentrelace(hnm); else { // if(hnm->header.width == 640) // CLBlitter_RawCopy640(hnm->new_frame_buffer, hnm->final_buffer, hnm->header.height); @@ -224,10 +499,10 @@ bool HnmPlayer::nextElement(hnm_t *hnm) { return true; case BE16('IU'): hnm->_frameNum++; - CLHNM_SelectBuffers(hnm); - CLHNM_DecompUBA(hnm->_newFrameBuffer, hnm->_newFrameBuffer, hnm->_oldFrameBuffer, hnm->_dataPtr, hnm->_header._width, h6); + selectBuffers(hnm); + decompUBA(hnm->_newFrameBuffer, hnm->_newFrameBuffer, hnm->_oldFrameBuffer, hnm->_dataPtr, hnm->_header._width, h6); if (!(h6 & 1)) - CLHNM_Desentrelace(hnm); + desentrelace(hnm); else { // if(hnm->header.width == 640) // CLBlitter_RawCopy640(hnm->new_frame_buffer, hnm->final_buffer, hnm->header.height); @@ -263,7 +538,7 @@ bool HnmPlayer::nextElement(hnm_t *hnm) { CLSoundGroup_PlayNextSample(soundGroup_adpcm, soundChannel); } } else - error("CLHNM_NextElement - unexpected flag"); + error("nextElement - unexpected flag"); } hnm->_dataPtr += sz - 8; break; @@ -285,5 +560,79 @@ soundchannel_t *HnmPlayer::getSoundChannel() { void HnmPlayer::flushPreloadBuffer(hnm_t *hnm) { } +// Original name: CLHNM_ChangePalette +void HnmPlayer::changePalette(hnm_t *hnm) { + int16 mincolor, maxcolor; + uint16 fst, cnt; + byte *pal; + color_t *color; + CLPalette_GetLastPalette(hnm->_palette); + pal = hnm->_dataPtr; + if (*(uint16 *)pal == 0xFFFF) + return; + mincolor = 255; + maxcolor = 0; + do { + fst = *pal++; + cnt = *pal++; + if (cnt == 0) + cnt = 256; + debug("hnm: setting palette, fst = %d, cnt = %d, last = %d", fst, cnt, fst + cnt - 1); + assert(fst + cnt <= 256); + if (mincolor > fst) + mincolor = fst; + if (maxcolor < fst + cnt) + maxcolor = fst + cnt; + color = hnm->_palette + fst; + if (safe_palette) { + while (cnt--) { + byte r = *pal++; + byte g = *pal++; + byte b = *pal++; + int16 rr = r << 10; + int16 gg = g << 10; + int16 bb = b << 10; + if (color->r != rr || color->g != gg || color->b != bb) + CLBlitter_OneBlackFlash(); + color->r = rr; + color->g = gg; + color->b = bb; + color++; + } + } else { + while (cnt--) { + byte r = *pal++; + byte g = *pal++; + byte b = *pal++; + color->r = r << 10; + color->g = g << 10; + color->b = b << 10; + color++; + } + } + + } while (*(uint16 *)pal != 0xFFFF); +#if 0 + if (preserve_color0) { + hnm->palette[0].r = 0; + hnm->palette[0].g = 0; + hnm->palette[0].b = 0; + } +#endif + // CLBlitter_Send2ScreenNextCopy(hnm->palette, mincolor, maxcolor - mincolor); + CLBlitter_Send2ScreenNextCopy(hnm->_palette, 0, 256); +} + +// Original name: CLHNM_SelectBuffers +void HnmPlayer::selectBuffers(hnm_t *hnm) { + if (hnm->_frameNum % 2) { + hnm->_newFrameBuffer = hnm->tmpBuffer[1]; + hnm->_oldFrameBuffer = hnm->tmpBuffer[0]; + } else { + hnm->_newFrameBuffer = hnm->tmpBuffer[0]; + hnm->_oldFrameBuffer = hnm->tmpBuffer[1]; + } +} + } // namespace Cryo diff --git a/engines/cryo/video.h b/engines/cryo/video.h index b574fe0ec8..fdb0d2403c 100644 --- a/engines/cryo/video.h +++ b/engines/cryo/video.h @@ -36,6 +36,14 @@ private: void decompADPCM(byte *buffer, int16 *output, int size); void loadDecompTable(int16 *buffer); void soundInADPCM(bool is_adpcm); // Unused + bool loadFrame(hnm_t *hnm); + void tryRead(hnm_t *hnm, int size); // TODO: remove this function + void changePalette(hnm_t *hnm); + void selectBuffers(hnm_t *hnm); + void decompLempelZiv(byte *buffer, byte *output); + void desentrelace320(byte *frame_buffer, byte *final_buffer, uint16 height); + void desentrelace(hnm_t *hnm); + void decompUBA(byte *output, byte *curr_buffer, byte *prev_buffer, byte *input, int width, char flags); bool sound_started; int16 pending_sounds; @@ -50,6 +58,7 @@ private: bool use_adpcm; bool preserve_color0; int16 decomp_table[256]; + bool safe_palette; void (*custom_chunk_handler)(byte *buffer, int size, int16 id, char h6, char h7); @@ -73,6 +82,13 @@ public: bool nextElement(hnm_t *hnm); void init(); void setForceZero2Black(bool forceblack); + void readHeader(hnm_t *hnm); + int16 getVersion(hnm_t *hnm); + void allocMemory(hnm_t *hnm); + void deallocMemory(hnm_t *hnm); + void setFinalBuffer(hnm_t *hnm, byte *buffer); + int getFrameNum(hnm_t *hnm); + soundchannel_t *getSoundChannel(); }; |