[Scummvm-git-logs] scummvm master -> 54240bdac64b5d19c08852180d127faa0789ba0e
rvanlaar
noreply at scummvm.org
Sat Mar 5 21:14:27 UTC 2022
This automated email contains information about 3 new commits which have been
pushed to the 'scummvm' repo located at https://github.com/scummvm/scummvm .
Summary:
bee055140f DIRECTOR: Sanity check PACo palette was off by one
e931a1a985 VIDEO: PACo decoder: refactor for audio track
54240bdac6 VIDEO: PACo decoder: Add audio support
Commit: bee055140fbfd139df1c2f75f569d98e343037d8
https://github.com/scummvm/scummvm/commit/bee055140fbfd139df1c2f75f569d98e343037d8
Author: Roland van Laar (roland at rolandvanlaar.nl)
Date: 2022-03-05T22:11:40+01:00
Commit Message:
DIRECTOR: Sanity check PACo palette was off by one
Palette has a length of 256.
Changed paths:
engines/director/lingo/lingo-builtins.cpp
diff --git a/engines/director/lingo/lingo-builtins.cpp b/engines/director/lingo/lingo-builtins.cpp
index 18134c9b333..c9c8388d2ab 100644
--- a/engines/director/lingo/lingo-builtins.cpp
+++ b/engines/director/lingo/lingo-builtins.cpp
@@ -2711,9 +2711,9 @@ void LB::b_xPlayAnim(int nargs){
byte origPalette[256 * 3];
uint16 origCount = g_director->getPaletteColorCount();
- if (origCount > 255) {
+ if (origCount > 256) {
warning("b_xPlayAnim: too big palette, %d > 256", origCount);
- origCount = 255;
+ origCount = 256;
}
memcpy(origPalette, g_director->getPalette(), origCount * 3);
Commit: e931a1a9854dfba40c4813ed6b99efb2256c7ad6
https://github.com/scummvm/scummvm/commit/e931a1a9854dfba40c4813ed6b99efb2256c7ad6
Author: Roland van Laar (roland at rolandvanlaar.nl)
Date: 2022-03-05T22:11:40+01:00
Commit Message:
VIDEO: PACo decoder: refactor for audio track
A PACo 'frame' has both the audio and video part of the frame. Where decodeNextFrame only handles video, readNextPacket enables the option to read a PACo frame and decode and queue both audio and video.
Changed paths:
video/paco_decoder.cpp
video/paco_decoder.h
diff --git a/video/paco_decoder.cpp b/video/paco_decoder.cpp
index 457cf2f7c5d..9ffbcb1f53a 100644
--- a/video/paco_decoder.cpp
+++ b/video/paco_decoder.cpp
@@ -44,6 +44,7 @@ PacoDecoder::~PacoDecoder() {
bool PacoDecoder::loadStream(Common::SeekableReadStream *stream) {
close();
+ _curFrame = 0;
stream->readUint16BE(); // 1
stream->readUint16BE(); // 0x26
@@ -64,7 +65,15 @@ bool PacoDecoder::loadStream(Common::SeekableReadStream *stream) {
stream->readUint32BE(); // flags
stream->readUint16BE(); // 0
- addTrack(new PacoVideoTrack(stream, frameRate, frameCount, hasAudio, width, height));
+ for (uint i = 0; i < frameCount; i++) {
+ _frameSizes[i] = stream->readUint32BE();
+ }
+
+ _fileStream = stream;
+
+ _videoTrack = new PacoVideoTrack(frameRate, frameCount, width, height);
+ addTrack(_videoTrack);
+
return true;
}
@@ -105,9 +114,8 @@ const byte* PacoDecoder::PacoVideoTrack::getPalette() const {
}
PacoDecoder::PacoVideoTrack::PacoVideoTrack(
- Common::SeekableReadStream *stream, uint16 frameRate, uint16 frameCount, bool hasAudio, uint16 width, uint16 height) {
-
- _fileStream = stream;
+ uint16 frameRate, uint16 frameCount, uint16 width, uint16 height) {
+ _curFrame = 0;
_frameRate = frameRate;
_frameCount = frameCount;
@@ -115,16 +123,9 @@ PacoDecoder::PacoVideoTrack::PacoVideoTrack(
_surface->create(width, height, Graphics::PixelFormat::createFormatCLUT8());
_palette = const_cast<byte *>(quickTimeDefaultPalette256);
_dirtyPalette = true;
-
- _curFrame = 0;
-
- for (uint i = 0; i < _frameCount; i++) {
- _frameSizes[i] = stream->readUint32BE();
- }
}
PacoDecoder::PacoVideoTrack::~PacoVideoTrack() {
- delete _fileStream;
_surface->free();
delete _surface;
}
@@ -161,11 +162,13 @@ enum frameTypes {
EOC = 11 // - end of chunk marker
};
-const Graphics::Surface *PacoDecoder::PacoVideoTrack::decodeNextFrame() {
+void PacoDecoder::readNextPacket() {
uint32 nextFrame = _fileStream->pos() + _frameSizes[_curFrame];
debug(2, " frame %3d size %d @ %lX", _curFrame, _frameSizes[_curFrame], _fileStream->pos());
+ _curFrame++;
+
while (_fileStream->pos() < nextFrame) {
int64 currentPos = _fileStream->pos();
int frameType = _fileStream->readByte();
@@ -178,10 +181,10 @@ const Graphics::Surface *PacoDecoder::PacoVideoTrack::decodeNextFrame() {
warning("PacoDecode::decodeFrame(): Audio not implemented");
break;
case VIDEO:
- handleFrame(chunkSize - 4);
+ _videoTrack->handleFrame(_fileStream, chunkSize - 4, _curFrame);
break;
case PALLETE:
- handlePalette();
+ _videoTrack->handlePalette(_fileStream);
break;
case EOC:
break;
@@ -192,20 +195,22 @@ const Graphics::Surface *PacoDecoder::PacoVideoTrack::decodeNextFrame() {
_fileStream->seek(currentPos + chunkSize);
}
- _curFrame++;
+}
+
+const Graphics::Surface *PacoDecoder::PacoVideoTrack::decodeNextFrame() {
return _surface;
}
-void PacoDecoder::PacoVideoTrack::handlePalette() {
- uint32 header = _fileStream->readUint32BE();
+void PacoDecoder::PacoVideoTrack::handlePalette(Common::SeekableReadStream *fileStream) {
+ uint32 header = fileStream->readUint32BE();
if (header == 0x30000000) { // default quicktime palette
_palette = const_cast<byte *>(quickTimeDefaultPalette256);
} else {
- _fileStream->readUint32BE(); // 4 bytes of 00
+ fileStream->readUint32BE(); // 4 bytes of 00
_palette = new byte[256 * 3]();
for (int i = 0; i < 256 * 3; i++){
- _palette[i] = _fileStream->readByte();
+ _palette[i] = fileStream->readByte();
}
}
_dirtyPalette = true;
@@ -246,23 +251,24 @@ enum {
} while(0);
-void PacoDecoder::PacoVideoTrack::handleFrame(uint32 chunkSize) {
+void PacoDecoder::PacoVideoTrack::handleFrame(Common::SeekableReadStream *fileStream, uint32 chunkSize, int curFrame) {
+ _curFrame = curFrame;
uint16 w = getWidth();
- uint16 x = _fileStream->readUint16BE(); // x offset of the updated area
- uint16 y = _fileStream->readUint16BE(); // y offset of the updated area
- uint16 bw = _fileStream->readUint16BE(); // updated area width
- uint16 bh = _fileStream->readUint16BE(); // updated area height
- uint compr = _fileStream->readByte(); // compression method and flags
- _fileStream->readByte(); // padding
+ uint16 x = fileStream->readUint16BE(); // x offset of the updated area
+ uint16 y = fileStream->readUint16BE(); // y offset of the updated area
+ uint16 bw = fileStream->readUint16BE(); // updated area width
+ uint16 bh = fileStream->readUint16BE(); // updated area height
+ uint compr = fileStream->readByte(); // compression method and flags
+ fileStream->readByte(); // padding
debug(5, " +%d,%d - %dx%d compr %X", x, y, bw, bh, compr);
compr = compr & 0xF;
uint8 *fdata = new uint8[1048576]; // 0x100000 copied from original pacodec
- _fileStream->read(fdata, chunkSize - 10); // remove header length
- debug(5, "pos: %ld", _fileStream->pos());
+ fileStream->read(fdata, chunkSize - 10); // remove header length
+ debug(5, "pos: %ld", fileStream->pos());
int16 xpos = x, ypos = y, ypos2 = y;
byte *dst = (byte *)_surface->getPixels() + x + y * w;
diff --git a/video/paco_decoder.h b/video/paco_decoder.h
index feca06f946d..387da2cc409 100644
--- a/video/paco_decoder.h
+++ b/video/paco_decoder.h
@@ -22,9 +22,9 @@
#ifndef VIDEO_PACODECODER_H
#define VIDEO_PACODECODER_H
-#include "video/video_decoder.h"
#include "common/list.h"
#include "common/rect.h"
+#include "video/video_decoder.h"
namespace Common {
class SeekableReadStream;
@@ -33,7 +33,7 @@ class SeekableReadStream;
namespace Graphics {
struct PixelFormat;
struct Surface;
-}
+} // namespace Graphics
namespace Video {
@@ -54,14 +54,14 @@ public:
void clearDirtyRects();
void copyDirtyRectsToBuffer(uint8 *dst, uint pitch);
const byte *getPalette();
+ virtual void readNextPacket() override;
-protected:
+protected:
class PacoVideoTrack : public FixedRateVideoTrack {
public:
PacoVideoTrack(
- Common::SeekableReadStream *stream, uint16 frameRate, uint16 frameCount,
- bool hasAudio, uint16 width, uint16 height);
+ uint16 frameRate, uint16 frameCount, uint16 width, uint16 height);
~PacoVideoTrack();
bool endOfTrack() const override;
@@ -73,8 +73,8 @@ protected:
int getCurFrame() const override { return _curFrame; }
int getFrameCount() const override { return _frameCount; }
virtual const Graphics::Surface *decodeNextFrame() override;
- virtual void handleFrame(uint32 chunkSize);
- void handlePalette();
+ virtual void handleFrame(Common::SeekableReadStream *fileStream, uint32 chunkSize, int curFrame);
+ void handlePalette(Common::SeekableReadStream *fileStream);
const byte *getPalette() const override;
bool hasDirtyPalette() const override { return _dirtyPalette; }
@@ -83,24 +83,27 @@ protected:
void copyDirtyRectsToBuffer(uint8 *dst, uint pitch);
Common::Rational getFrameRate() const override { return Common::Rational(_frameRate, 1); }
-
protected:
- Common::SeekableReadStream *_fileStream;
Graphics::Surface *_surface;
- int _curFrame;
-
byte *_palette;
- int _frameSizes[65536]; // can be done differently?
mutable bool _dirtyPalette;
+ int _curFrame;
uint32 _frameCount;
uint32 _frameDelay;
uint16 _frameRate;
Common::List<Common::Rect> _dirtyRects;
};
+
+private:
+ PacoVideoTrack *_videoTrack;
+ Common::SeekableReadStream *_fileStream;
+ int _curFrame = 0;
+ int _frameSizes[65536]; // can be done differently?
+
};
} // End of namespace Video
Commit: 54240bdac64b5d19c08852180d127faa0789ba0e
https://github.com/scummvm/scummvm/commit/54240bdac64b5d19c08852180d127faa0789ba0e
Author: Roland van Laar (roland at rolandvanlaar.nl)
Date: 2022-03-05T22:11:40+01:00
Commit Message:
VIDEO: PACo decoder: Add audio support
PACo audio is single channel 8 bit unsigned pcm.
The first sound packet is read to determine the sampling rate.
Changed paths:
video/paco_decoder.cpp
video/paco_decoder.h
diff --git a/video/paco_decoder.cpp b/video/paco_decoder.cpp
index 9ffbcb1f53a..99e5b5a275c 100644
--- a/video/paco_decoder.cpp
+++ b/video/paco_decoder.cpp
@@ -34,6 +34,21 @@
namespace Video {
+enum frameTypes {
+ NOP = 0, // nop
+ // 1 - old initialisation data?
+ PALLETE = 2, // - new initialisation data (usually 0x30 0x00 0x00 ... meaning 8-bit with default QuickTime palette)
+ DELAY = 3, // - delay information
+ AUDIO = 4, // - audio data (8-bit unsigned PCM)
+ // 5 - should not be present
+ // 6 - should not be present
+ // 7 - unknown
+ VIDEO = 8, // - video frame
+ // 9 - unknown
+ // 10 - dummy?
+ EOC = 11 // - end of chunk marker
+};
+
PacoDecoder::PacoDecoder() {
}
@@ -73,10 +88,42 @@ bool PacoDecoder::loadStream(Common::SeekableReadStream *stream) {
_videoTrack = new PacoVideoTrack(frameRate, frameCount, width, height);
addTrack(_videoTrack);
-
+ if (hasAudio) {
+ _audioTrack = new PacoAudioTrack(getAudioSamplingRate());
+ addTrack(_audioTrack);
+ }
return true;
}
+int PacoDecoder::getAudioSamplingRate() {
+ /**
+ * SamplingRate is found inside the audio packets
+ * Search for the first audio packet and use it.
+ */
+ const Common::Array<int> samplingRates = {5563, 7418, 11127, 22254};
+ int index;
+
+ int64 startPos = _fileStream->pos();
+
+ while (true){
+ int64 currentPos = _fileStream->pos();
+ int frameType = _fileStream->readByte();
+ int v = _fileStream->readByte();
+ uint32 chunkSize = (v << 16 ) | _fileStream->readUint16BE();
+ if (frameType != AUDIO) {
+ _fileStream->seek(currentPos + chunkSize);
+ continue;
+ }
+ uint16 header = _fileStream->readUint16BE();
+ _fileStream->readUint16BE();
+ index = (header >> 10) & 7;
+ break;
+ }
+ _fileStream->seek(startPos);
+
+ return samplingRates[index];
+}
+
const Common::List<Common::Rect> *PacoDecoder::getDirtyRects() const {
const Track *track = getTrack(0);
@@ -146,22 +193,6 @@ Graphics::PixelFormat PacoDecoder::PacoVideoTrack::getPixelFormat() const {
return _surface->format;
}
-
-enum frameTypes {
- NOP = 0, // nop
- // 1 - old initialisation data?
- PALLETE = 2, // - new initialisation data (usually 0x30 0x00 0x00 ... meaning 8-bit with default QuickTime palette)
- DELAY = 3, // - delay information
- AUDIO = 4, // - audio data (8-bit unsigned PCM)
- // 5 - should not be present
- // 6 - should not be present
- // 7 - unknown
- VIDEO = 8, // - video frame
- // 9 - unknown
- // 10 - dummy?
- EOC = 11 // - end of chunk marker
-};
-
void PacoDecoder::readNextPacket() {
uint32 nextFrame = _fileStream->pos() + _frameSizes[_curFrame];
@@ -178,7 +209,7 @@ void PacoDecoder::readNextPacket() {
switch (frameType) {
case AUDIO:
- warning("PacoDecode::decodeFrame(): Audio not implemented");
+ _audioTrack->queueSound(_fileStream, chunkSize - 4);
break;
case VIDEO:
_videoTrack->handleFrame(_fileStream, chunkSize - 4, _curFrame);
@@ -529,4 +560,24 @@ void PacoDecoder::PacoVideoTrack::copyDirtyRectsToBuffer(uint8 *dst, uint pitch)
clearDirtyRects();
}
+PacoDecoder::PacoAudioTrack::PacoAudioTrack(int samplingRate)
+ : AudioTrack(Audio::Mixer::kPlainSoundType) {
+ _samplingRate = samplingRate;
+ byte audioFlags = Audio::FLAG_UNSIGNED;
+ _packetStream = Audio::makePacketizedRawStream(samplingRate, audioFlags);
+}
+
+void PacoDecoder::PacoAudioTrack::queueSound(Common::SeekableReadStream *fileStream, uint32 chunkSize) {
+ const Common::Array<int> samplingRates = {5563, 7418, 11127, 22254};
+ uint16 header = fileStream->readUint16BE();
+ fileStream->readUint16BE();
+ int index = (header >> 10) & 7;
+ int currentRate = samplingRates[index];
+ if ( currentRate != _samplingRate)
+ warning("PacoDecoder::PacoAudioTrack: Sampling rate differs from first frame: %i != %i", currentRate, _samplingRate);
+
+ _packetStream->queuePacket(fileStream->readStream(chunkSize - 4));
+}
+
+
} // End of namespace Video
diff --git a/video/paco_decoder.h b/video/paco_decoder.h
index 387da2cc409..1ee803c9d52 100644
--- a/video/paco_decoder.h
+++ b/video/paco_decoder.h
@@ -22,6 +22,7 @@
#ifndef VIDEO_PACODECODER_H
#define VIDEO_PACODECODER_H
+#include "audio/audiostream.h"
#include "common/list.h"
#include "common/rect.h"
#include "video/video_decoder.h"
@@ -98,12 +99,26 @@ protected:
Common::List<Common::Rect> _dirtyRects;
};
+ class PacoAudioTrack : public AudioTrack {
+ public:
+ PacoAudioTrack(int samplingRate);
+ void queueSound(Common::SeekableReadStream *fileStream, uint32 chunkSize);
+
+ protected:
+ Audio::AudioStream *getAudioStream() const { return _packetStream; }
+
+ private:
+ Audio::PacketizedAudioStream *_packetStream;
+ int _samplingRate;
+ };
+
private:
PacoVideoTrack *_videoTrack;
+ PacoAudioTrack *_audioTrack;
Common::SeekableReadStream *_fileStream;
int _curFrame = 0;
int _frameSizes[65536]; // can be done differently?
-
+ int getAudioSamplingRate();
};
} // End of namespace Video
More information about the Scummvm-git-logs
mailing list