From 1e5f5d694738a0edd37291930bf040a772e70138 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Einar=20Johan=20Tr=C3=B8an=20S=C3=B8ma=CC=8Aen?= Date: Sun, 1 Feb 2015 16:06:15 +0100 Subject: [PATCH] HACK: Add support for playing Theora-videos from the SmushPlayer, when playback of SMUSH-fails, this should perhaps result in a new class for handling codecs dynamically (so that we can resolve both the Aspyr-logo and Theora/Smush-juggling in a consistent way). Also hack the scaling for 1080p-videos for now. --- engines/grim/gfx_opengl.cpp | 20 +++++++++++++++ engines/grim/movie/smush.cpp | 50 ++++++++++++++++++++++++++++-------- engines/grim/movie/smush.h | 8 +++++- 3 files changed, 66 insertions(+), 12 deletions(-) diff --git a/engines/grim/gfx_opengl.cpp b/engines/grim/gfx_opengl.cpp index 374cb1728af..963b1e7a6ce 100644 --- a/engines/grim/gfx_opengl.cpp +++ b/engines/grim/gfx_opengl.cpp @@ -1630,6 +1630,14 @@ void GfxOpenGL::prepareMovieFrame(Graphics::Surface *frame) { int width = frame->w; byte *bitmap = (byte *)frame->getPixels(); + double scaleW = _scaleW; + double scaleH = _scaleH; + // Remastered hack, don't scale full-screen videos for now. + if (height == 1080) { + _scaleW = 1.0f; + _scaleH = 1.0f; + } + GLenum format; GLenum dataType; int bytesPerPixel = frame->format.bytesPerPixel; @@ -1692,9 +1700,18 @@ void GfxOpenGL::prepareMovieFrame(Graphics::Surface *frame) { glPixelStorei(GL_UNPACK_ROW_LENGTH, 0); _smushWidth = (int)(width * _scaleW); _smushHeight = (int)(height * _scaleH); + _scaleW = scaleW; + _scaleH = scaleH; } void GfxOpenGL::drawMovieFrame(int offsetX, int offsetY) { + double scaleW = _scaleW; + double scaleH = _scaleH; + // Remastered hack, don't scale full-screen videos for now. + if (_smushHeight == 1080) { + _scaleW = 1.0f; + _scaleH = 1.0f; + } // prepare view glMatrixMode(GL_PROJECTION); glLoadIdentity(); @@ -1741,6 +1758,9 @@ void GfxOpenGL::drawMovieFrame(int offsetX, int offsetY) { glDepthMask(GL_TRUE); glEnable(GL_DEPTH_TEST); glEnable(GL_LIGHTING); + + _scaleW = scaleW; + _scaleH = scaleH; } void GfxOpenGL::releaseMovieFrame() { diff --git a/engines/grim/movie/smush.cpp b/engines/grim/movie/smush.cpp index 1451d85b6f8..251887ac960 100644 --- a/engines/grim/movie/smush.cpp +++ b/engines/grim/movie/smush.cpp @@ -23,6 +23,8 @@ #include "engines/grim/movie/codecs/smush_decoder.h" #include "engines/grim/movie/smush.h" +#include "video/theora_decoder.h" + #include "engines/grim/resource.h" #include "engines/grim/grim.h" @@ -32,25 +34,49 @@ MoviePlayer *CreateSmushPlayer(bool demo) { return new SmushPlayer(demo); } +SmushPlayer::~SmushPlayer() { + delete _theoraDecoder; +} + SmushPlayer::SmushPlayer(bool demo) : MoviePlayer(), _demo(demo) { _smushDecoder = new SmushDecoder(); _videoDecoder = _smushDecoder; + _theoraDecoder = new Video::TheoraDecoder(); //_smushDecoder->setDemo(_demo); } bool SmushPlayer::loadFile(const Common::String &filename) { + warning("Play video %s\n", filename.c_str()); + bool success = false; + _videoDecoder = _smushDecoder; if (!_demo) - return _videoDecoder->loadStream(g_resourceloader->openNewStreamFile(filename.c_str())); + success = _videoDecoder->loadStream(g_resourceloader->openNewStreamFile(filename.c_str())); else - return _videoDecoder->loadFile(filename); + success = _videoDecoder->loadFile(filename); + + if (!success) { + Common::String theoraFilename = "MoviesHD/" + filename; + theoraFilename.erase(theoraFilename.size() - 4); + theoraFilename += ".ogv"; + warning("Trying to open %s", theoraFilename.c_str()); + success = _theoraDecoder->loadFile(theoraFilename); + _videoDecoder = _theoraDecoder; + _currentVideoIsTheora = true; + } else { + _videoDecoder = _smushDecoder; + _currentVideoIsTheora = false; + } + return success; } void SmushPlayer::init() { - if (_demo) { - _x = _smushDecoder->getX(); - _y = _smushDecoder->getY(); - } else { - _smushDecoder->setLooping(_videoLooping); + if (!_currentVideoIsTheora) { + if (_demo) { + _x = _smushDecoder->getX(); + _y = _smushDecoder->getY(); + } else { + _smushDecoder->setLooping(_videoLooping); + } } MoviePlayer::init(); } @@ -65,21 +91,23 @@ void SmushPlayer::handleFrame() { deinit(); return; } else { - _smushDecoder->rewind(); // This doesnt handle if looping fails. - _smushDecoder->start(); + if (!_currentVideoIsTheora) { + _smushDecoder->rewind(); // This doesnt handle if looping fails. + _smushDecoder->start(); + } } } } void SmushPlayer::postHandleFrame() { - if (_demo) { + if (_demo && !_currentVideoIsTheora) { _x = _smushDecoder->getX(); _y = _smushDecoder->getY(); } } void SmushPlayer::restore(SaveGame *state) { - if (isPlaying()) { + if (isPlaying() && !_currentVideoIsTheora) { _smushDecoder->seek((uint32)_movieTime); _smushDecoder->start(); timerCallback(this); diff --git a/engines/grim/movie/smush.h b/engines/grim/movie/smush.h index ffe702f1c47..5bcca187d2f 100644 --- a/engines/grim/movie/smush.h +++ b/engines/grim/movie/smush.h @@ -25,6 +25,10 @@ #include "engines/grim/movie/movie.h" +namespace Video { + class TheoraDecoder; +} + namespace Grim { class SmushDecoder; @@ -32,7 +36,7 @@ class SmushDecoder; class SmushPlayer : public MoviePlayer { public: SmushPlayer(bool demo); - + virtual ~SmushPlayer(); void restore(SaveGame *state) override; private: @@ -41,7 +45,9 @@ private: void postHandleFrame() override; void init() override; bool _demo; + bool _currentVideoIsTheora; SmushDecoder *_smushDecoder; + Video::TheoraDecoder *_theoraDecoder; // HACK for now, move to other class later? }; } // end of namespace Grim