diff options
-rw-r--r-- | engines/sci/engine/kevent.cpp | 2 | ||||
-rw-r--r-- | engines/sci/graphics/controls32.cpp | 1 | ||||
-rw-r--r-- | engines/sci/graphics/frameout.cpp | 25 | ||||
-rw-r--r-- | engines/sci/graphics/frameout.h | 21 | ||||
-rw-r--r-- | engines/sci/graphics/transitions32.cpp | 2 | ||||
-rw-r--r-- | engines/sci/graphics/video32.cpp | 10 | ||||
-rw-r--r-- | engines/sci/sci.cpp | 2 |
7 files changed, 43 insertions, 20 deletions
diff --git a/engines/sci/engine/kevent.cpp b/engines/sci/engine/kevent.cpp index 389277b9bc..b240c947bf 100644 --- a/engines/sci/engine/kevent.cpp +++ b/engines/sci/engine/kevent.cpp @@ -101,7 +101,7 @@ reg_t kGetEvent(EngineState *s, int argc, reg_t *argv) { // one of these ugly loops and should be updating the screen & // throttling the VM. if (++s->_eventCounter > 2) { - g_system->updateScreen(); + g_sci->_gfxFrameout->updateScreen(); s->speedThrottler(10); // 10ms is an arbitrary value s->_throttleTrigger = true; } diff --git a/engines/sci/graphics/controls32.cpp b/engines/sci/graphics/controls32.cpp index 0cd924b38d..7080c108b3 100644 --- a/engines/sci/graphics/controls32.cpp +++ b/engines/sci/graphics/controls32.cpp @@ -299,7 +299,6 @@ reg_t GfxControls32::kernelEditText(const reg_t controlObject) { } g_sci->_gfxFrameout->frameOut(true); - g_sci->getSciDebugger()->onFrame(); g_sci->_gfxFrameout->throttle(); } diff --git a/engines/sci/graphics/frameout.cpp b/engines/sci/graphics/frameout.cpp index c969f91c71..390cc81779 100644 --- a/engines/sci/graphics/frameout.cpp +++ b/engines/sci/graphics/frameout.cpp @@ -68,7 +68,8 @@ GfxFrameout::GfxFrameout(SegManager *segMan, GfxPalette32 *palette, GfxTransitio _throttleState(0), _remapOccurred(false), _overdrawThreshold(0), - _palMorphIsOn(false) { + _palMorphIsOn(false), + _lastScreenUpdateTick(0) { if (g_sci->getGameId() == GID_PHANTASMAGORIA) { _currentBuffer = Buffer(630, 450, nullptr); @@ -1008,7 +1009,7 @@ void GfxFrameout::mergeToShowList(const Common::Rect &drawRect, RectList &showLi void GfxFrameout::showBits() { if (!_showList.size()) { - g_system->updateScreen(); + updateScreen(); return; } @@ -1050,7 +1051,7 @@ void GfxFrameout::showBits() { _cursor->donePainting(); _showList.clear(); - g_system->updateScreen(); + updateScreen(); } void GfxFrameout::alterVmap(const Palette &palette1, const Palette &palette2, const int8 style, const int8 *const styleRanges) { @@ -1123,6 +1124,20 @@ void GfxFrameout::alterVmap(const Palette &palette1, const Palette &palette2, co } } +void GfxFrameout::updateScreen(const int delta) { + // using OSystem::getMillis instead of Sci::getTickCount because these + // values need to be monotonically increasing for the duration of the + // GfxFrameout object or else the screen will stop updating + const uint32 now = g_system->getMillis() * 60 / 1000; + if (now <= _lastScreenUpdateTick + delta) { + return; + } + + _lastScreenUpdateTick = now; + g_system->updateScreen(); + g_sci->getSciDebugger()->onFrame(); +} + void GfxFrameout::kernelFrameOut(const bool shouldShowBits) { if (_transitions->hasShowStyles()) { _transitions->processShowStyles(); @@ -1166,14 +1181,14 @@ void GfxFrameout::shakeScreen(int16 numShakes, const ShakeDirection direction) { g_system->setShakePos(_isHiRes ? 8 : 4); } - g_system->updateScreen(); + updateScreen(); g_sci->getEngineState()->wait(3); if (direction & kShakeVertical) { g_system->setShakePos(0); } - g_system->updateScreen(); + updateScreen(); g_sci->getEngineState()->wait(3); } } diff --git a/engines/sci/graphics/frameout.h b/engines/sci/graphics/frameout.h index e706f141b2..ab58f41144 100644 --- a/engines/sci/graphics/frameout.h +++ b/engines/sci/graphics/frameout.h @@ -155,6 +155,11 @@ public: #pragma mark - #pragma mark Rendering private: + /** + * The last time the hardware screen was updated. + */ + uint32 _lastScreenUpdateTick; + GfxTransitions32 *_transitions; /** @@ -255,8 +260,8 @@ private: void mergeToShowList(const Common::Rect &drawRect, RectList &showList, const int overdrawThreshold); /** - * Writes the internal frame buffer out to hardware and - * clears the show list. + * Sends all dirty rects from the internal frame buffer to the backend, + * then updates the hardware screen. */ void showBits(); @@ -285,6 +290,18 @@ private: } public: + /** + * Updates the hardware screen, no more than once per tick. + * + * @param delta An additional number of ticks that should elapse + * since the last time the screen was updated before it gets updated now. + * This is used for updating the screen within run_vm, where we normally + * expect that a call to kFrameOut will occur later during the current + * frame, but if it does not, then update the screen on the second frame + * anyway since the game is doing something bad. + */ + void updateScreen(const int delta = 0); + void setPixelFormat(const Graphics::PixelFormat &format) const { initGraphics(_currentBuffer.screenWidth, _currentBuffer.screenHeight, _isHiRes, &format); } diff --git a/engines/sci/graphics/transitions32.cpp b/engines/sci/graphics/transitions32.cpp index 6da1772c48..b5e498528d 100644 --- a/engines/sci/graphics/transitions32.cpp +++ b/engines/sci/graphics/transitions32.cpp @@ -83,7 +83,6 @@ void GfxTransitions32::addShowRect(const Common::Rect &rect) { void GfxTransitions32::sendShowRects() { g_sci->_gfxFrameout->showBits(); - g_sci->getSciDebugger()->onFrame(); clearShowRects(); throttle(); } @@ -126,7 +125,6 @@ void GfxTransitions32::processShowStyles() { if (doFrameOut) { g_sci->_gfxFrameout->frameOut(true); - g_sci->getSciDebugger()->onFrame(); throttle(); } } while(continueProcessing && doFrameOut); diff --git a/engines/sci/graphics/video32.cpp b/engines/sci/graphics/video32.cpp index 8b804cfa40..f4b15517fe 100644 --- a/engines/sci/graphics/video32.cpp +++ b/engines/sci/graphics/video32.cpp @@ -145,7 +145,6 @@ void SEQPlayer::renderFrame(SciBitmap &bitmap) const { g_sci->_gfxFrameout->updateScreenItem(*_screenItem); g_sci->_gfxFrameout->frameOut(true); - g_sci->getSciDebugger()->onFrame(); } #pragma mark - @@ -419,7 +418,6 @@ void AVIPlayer::renderFrame() const { g_sci->_gfxFrameout->updateScreenItem(*_screenItem); g_sci->_gfxFrameout->frameOut(true); - g_sci->getSciDebugger()->onFrame(); } else { assert(surface->format.bytesPerPixel == 4); @@ -455,8 +453,7 @@ void AVIPlayer::renderFrame() const { g_system->copyRectToScreen(surface->getPixels(), surface->pitch, drawRect.left, drawRect.top, surface->w, surface->h); } - g_system->updateScreen(); - g_sci->getSciDebugger()->onFrame(); + g_sci->_gfxFrameout->updateScreen(); } } @@ -885,7 +882,6 @@ void VMDPlayer::renderFrame() const { g_sci->_gfxPalette32->submit(palette); g_sci->_gfxFrameout->updateScreenItem(*_screenItem); g_sci->_gfxFrameout->frameOut(true); - g_sci->getSciDebugger()->onFrame(); #if SCI_VMD_BLACK_PALETTE if (_blackPalette) { @@ -898,7 +894,6 @@ void VMDPlayer::renderFrame() const { } else { g_sci->_gfxFrameout->updateScreenItem(*_screenItem); g_sci->_gfxFrameout->frameOut(true); - g_sci->getSciDebugger()->onFrame(); } } @@ -1164,8 +1159,7 @@ void DuckPlayer::renderFrame() const { g_system->copyRectToScreen(surface->getPixels(), surface->pitch, _drawRect.left, _drawRect.top, surface->w, surface->h); } - g_system->updateScreen(); - g_sci->getSciDebugger()->onFrame(); + g_sci->_gfxFrameout->updateScreen(); } } // End of namespace Sci diff --git a/engines/sci/sci.cpp b/engines/sci/sci.cpp index a84f50ea2b..634652cd3f 100644 --- a/engines/sci/sci.cpp +++ b/engines/sci/sci.cpp @@ -849,7 +849,7 @@ void SciEngine::sleep(uint32 msecs) { // movement is still occurring and the screen needs to be updated to // reflect it if (getSciVersion() >= SCI_VERSION_2) { - g_system->updateScreen(); + g_sci->_gfxFrameout->updateScreen(); } #endif time = g_system->getMillis(); |