diff --git a/stella/src/common/FrameBufferGL.cxx b/stella/src/common/FrameBufferGL.cxx index 54023d96a..c771a7038 100644 --- a/stella/src/common/FrameBufferGL.cxx +++ b/stella/src/common/FrameBufferGL.cxx @@ -13,7 +13,7 @@ // See the file "license" for information on usage and redistribution of // this file, and for a DISCLAIMER OF ALL WARRANTIES. // -// $Id: FrameBufferGL.cxx,v 1.104 2008-06-19 12:01:30 stephena Exp $ +// $Id: FrameBufferGL.cxx,v 1.105 2008-08-04 11:56:11 stephena Exp $ //============================================================================ #ifdef DISPLAY_OPENGL @@ -385,7 +385,7 @@ void FrameBufferGL::drawMediaSource() uInt8 v = currentFrame[bufofs]; uInt8 w = previousFrame[bufofs]; - if(v != w || theRedrawTIAIndicator) + if(v != w || myRedrawEntireFrame) { // If we ever get to this point, we know the current and previous // buffers differ. In that case, make sure the changes are @@ -403,7 +403,7 @@ void FrameBufferGL::drawMediaSource() else { // Phosphor mode always implies a dirty update, - // so we don't care about theRedrawTIAIndicator + // so we don't care about myRedrawEntireFrame myDirtyFlag = true; uInt32 bufofsY = 0; @@ -462,7 +462,7 @@ void FrameBufferGL::enablePhosphor(bool enable, int blend) myUsePhosphor = enable; myPhosphorBlend = blend; - theRedrawTIAIndicator = true; + myRedrawEntireFrame = true; } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -488,7 +488,7 @@ void FrameBufferGL::toggleFilter() p_glTexParameteri(myBuffer.target, GL_TEXTURE_MIN_FILTER, myBuffer.filter); // The filtering has changed, so redraw the entire screen - theRedrawTIAIndicator = true; + myRedrawEntireFrame = true; } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/stella/src/common/FrameBufferSoft.cxx b/stella/src/common/FrameBufferSoft.cxx index 874c3dd71..572f43a47 100644 --- a/stella/src/common/FrameBufferSoft.cxx +++ b/stella/src/common/FrameBufferSoft.cxx @@ -13,7 +13,7 @@ // See the file "license" for information on usage and redistribution of // this file, and for a DISCLAIMER OF ALL WARRANTIES. // -// $Id: FrameBufferSoft.cxx,v 1.81 2008-07-04 14:27:17 stephena Exp $ +// $Id: FrameBufferSoft.cxx,v 1.82 2008-08-04 11:56:11 stephena Exp $ //============================================================================ #include @@ -35,6 +35,8 @@ FrameBufferSoft::FrameBufferSoft(OSystem* osystem) : FrameBuffer(osystem), myRenderType(kSoftZoom_16), + myTiaDirty(false), + myInUIMode(false), myRectList(NULL) { } @@ -131,8 +133,6 @@ void FrameBufferSoft::drawMediaSource() uInt32 width = mediasrc.width(); uInt32 height = mediasrc.height(); - bool tiaChanged = false; - switch(myRenderType) { case kSoftZoom_16: @@ -155,14 +155,14 @@ void FrameBufferSoft::drawMediaSource() uInt8 v = currentFrame[bufofs]; uInt8 w = previousFrame[bufofs]; - if(v != w || theRedrawTIAIndicator) + if(v != w || myRedrawEntireFrame) { while(xstride--) { buffer[pos++] = (uInt16) myDefPalette[v]; buffer[pos++] = (uInt16) myDefPalette[v]; } - tiaChanged = true; + myTiaDirty = true; } else pos += xstride + xstride; @@ -195,7 +195,7 @@ void FrameBufferSoft::drawMediaSource() uInt8 v = currentFrame[bufofs]; uInt8 w = previousFrame[bufofs]; - if(v != w || theRedrawTIAIndicator) + if(v != w || myRedrawEntireFrame) { uInt32 pixel = myDefPalette[v]; uInt8 r = (pixel & myFormat->Rmask) >> myFormat->Rshift; @@ -207,7 +207,7 @@ void FrameBufferSoft::drawMediaSource() buffer[pos++] = r; buffer[pos++] = g; buffer[pos++] = b; buffer[pos++] = r; buffer[pos++] = g; buffer[pos++] = b; } - tiaChanged = true; + myTiaDirty = true; } else // try to eliminate multply whereever possible pos += xstride + xstride + xstride + xstride + xstride + xstride; @@ -240,14 +240,14 @@ void FrameBufferSoft::drawMediaSource() uInt8 v = currentFrame[bufofs]; uInt8 w = previousFrame[bufofs]; - if(v != w || theRedrawTIAIndicator) + if(v != w || myRedrawEntireFrame) { while(xstride--) { buffer[pos++] = (uInt32) myDefPalette[v]; buffer[pos++] = (uInt32) myDefPalette[v]; } - tiaChanged = true; + myTiaDirty = true; } else pos += xstride + xstride; @@ -291,7 +291,7 @@ void FrameBufferSoft::drawMediaSource() bufofsY += width; } SDL_UnlockSurface(myScreen); - tiaChanged = true; + myTiaDirty = true; break; // kPhosphor_16 } @@ -330,7 +330,7 @@ void FrameBufferSoft::drawMediaSource() bufofsY += width; } SDL_UnlockSurface(myScreen); - tiaChanged = true; + myTiaDirty = true; break; // kPhosphor_24 } @@ -365,16 +365,25 @@ void FrameBufferSoft::drawMediaSource() bufofsY += width; } SDL_UnlockSurface(myScreen); - tiaChanged = true; + myTiaDirty = true; break; // kPhosphor_32 } } +} - if(tiaChanged) +// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +void FrameBufferSoft::postFrameUpdate() +{ + if(myTiaDirty && !myInUIMode) { SDL_Flip(myScreen); - tiaChanged = false; + myTiaDirty = false; } + else if(myRectList->numRects() > 0) + { + SDL_UpdateRects(myScreen, myRectList->numRects(), myRectList->rects()); + } + myRectList->start(); } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -392,6 +401,9 @@ void FrameBufferSoft::stateChanged(EventHandler::State state) if(!myScreen) return; + myInUIMode = (state == EventHandler::S_LAUNCHER || + state == EventHandler::S_DEBUGGER); + // Make sure drawMediaSource() knows which renderer to use switch(myBytesPerPixel) { @@ -683,6 +695,10 @@ void FBSurfaceSoft::addDirtyRect(uInt32 x, uInt32 y, uInt32 w, uInt32 h) } else { + SDL_Rect temp; + temp.x = myXOrig; temp.y = myYOrig; temp.w = myWidth; temp.h = myHeight; + myFB.myRectList->add(&temp); + // Indicate that at least one dirty rect has been added // This is an optimization for the update() method mySurfaceIsDirty = true; @@ -751,15 +767,7 @@ void FBSurfaceSoft::update() { // Since this method is called each frame, we only blit the surfaces when // absolutely necessary - if(myIsBaseSurface) - { - if(myFB.myRectList->numRects() > 0) - { - SDL_UpdateRects(mySurface, myFB.myRectList->numRects(), myFB.myRectList->rects()); - myFB.myRectList->start(); - } - } - else if(mySurfaceIsDirty /* && !myIsBaseSurface */) + if(mySurfaceIsDirty /* && !myIsBaseSurface */) { SDL_Rect srcrect; srcrect.x = 0; @@ -772,17 +780,8 @@ void FBSurfaceSoft::update() dstrect.y = myYOrig; dstrect.w = myWidth; dstrect.h = myHeight; -/* - cerr << "blit sub-surface:" << endl - << " src x = " << dstrect.x << endl - << " src y = " << dstrect.y << endl - << " dst w = " << dstrect.w << endl - << " dst h = " << dstrect.h << endl - << endl; -*/ - SDL_BlitSurface(mySurface, &srcrect, myFB.myScreen, &dstrect); - SDL_UpdateRect(myFB.myScreen, myXOrig, myYOrig, myWidth, myHeight); + SDL_BlitSurface(mySurface, &srcrect, myFB.myScreen, &dstrect); mySurfaceIsDirty = false; } } diff --git a/stella/src/common/FrameBufferSoft.hxx b/stella/src/common/FrameBufferSoft.hxx index 05ab91177..87b85a279 100644 --- a/stella/src/common/FrameBufferSoft.hxx +++ b/stella/src/common/FrameBufferSoft.hxx @@ -13,7 +13,7 @@ // See the file "license" for information on usage and redistribution of // this file, and for a DISCLAIMER OF ALL WARRANTIES. // -// $Id: FrameBufferSoft.hxx,v 1.53 2008-08-01 12:15:57 stephena Exp $ +// $Id: FrameBufferSoft.hxx,v 1.54 2008-08-04 11:56:11 stephena Exp $ //============================================================================ #ifndef FRAMEBUFFER_SOFT_HXX @@ -33,7 +33,7 @@ class RectList; This class implements an SDL software framebuffer. @author Stephen Anthony - @version $Id: FrameBufferSoft.hxx,v 1.53 2008-08-01 12:15:57 stephena Exp $ + @version $Id: FrameBufferSoft.hxx,v 1.54 2008-08-04 11:56:11 stephena Exp $ */ class FrameBufferSoft : public FrameBuffer { @@ -127,6 +127,11 @@ class FrameBufferSoft : public FrameBuffer */ void drawMediaSource(); + /** + This method is called after any drawing is done (per-frame). + */ + void postFrameUpdate(); + /** This method is called to provide information about the FrameBuffer. */ @@ -154,6 +159,12 @@ class FrameBufferSoft : public FrameBuffer }; RenderType myRenderType; + // Indicates if the TIA image has been modified + bool myTiaDirty; + + // Indicates if we're in a purely UI mode + bool myInUIMode; + // Used in the dirty update of rectangles in non-TIA modes RectList* myRectList; }; @@ -162,7 +173,7 @@ class FrameBufferSoft : public FrameBuffer A surface suitable for software rendering mode. @author Stephen Anthony - @version $Id: FrameBufferSoft.hxx,v 1.53 2008-08-01 12:15:57 stephena Exp $ + @version $Id: FrameBufferSoft.hxx,v 1.54 2008-08-04 11:56:11 stephena Exp $ */ class FBSurfaceSoft : public FBSurface { diff --git a/stella/src/emucore/FrameBuffer.cxx b/stella/src/emucore/FrameBuffer.cxx index 7358af6b1..715d43023 100644 --- a/stella/src/emucore/FrameBuffer.cxx +++ b/stella/src/emucore/FrameBuffer.cxx @@ -13,7 +13,7 @@ // See the file "license" for information on usage and redistribution of // this file, and for a DISCLAIMER OF ALL WARRANTIES. // -// $Id: FrameBuffer.cxx,v 1.138 2008-08-01 12:15:59 stephena Exp $ +// $Id: FrameBuffer.cxx,v 1.139 2008-08-04 11:56:12 stephena Exp $ //============================================================================ #include @@ -42,7 +42,7 @@ FrameBuffer::FrameBuffer(OSystem* osystem) : myOSystem(osystem), myScreen(0), - theRedrawTIAIndicator(true), + myRedrawEntireFrame(true), myUsePhosphor(false), myPhosphorBlend(77), myInitializedCount(0), @@ -168,7 +168,7 @@ void FrameBuffer::update() myStatsMsg.surface->fillRect(0, 0, myStatsMsg.w, myStatsMsg.h, kBGColor); myStatsMsg.surface->drawString(&myOSystem->consoleFont(), msg, 0, 0, myStatsMsg.w, myStatsMsg.color, kTextAlignLeft); - myStatsMsg.surface->addDirtyRect(0, 0, 0, 0); + myStatsMsg.surface->addDirtyRect(0, 0, 0, 0); // force a full draw myStatsMsg.surface->setPos(myImageRect.x() + 3, myImageRect.y() + 3); myStatsMsg.surface->update(); } @@ -178,7 +178,7 @@ void FrameBuffer::update() case EventHandler::S_PAUSE: { // Only update the screen if it's been invalidated - if(theRedrawTIAIndicator) + if(myRedrawEntireFrame) drawMediaSource(); // Show a pause message every 5 seconds @@ -193,7 +193,7 @@ void FrameBuffer::update() case EventHandler::S_MENU: { // Only update the screen if it's been invalidated - if(theRedrawTIAIndicator) + if(myRedrawEntireFrame) drawMediaSource(); myOSystem->menu().draw(); @@ -203,7 +203,7 @@ void FrameBuffer::update() case EventHandler::S_CMDMENU: { // Only update the screen if it's been invalidated - if(theRedrawTIAIndicator) + if(myRedrawEntireFrame) drawMediaSource(); myOSystem->commandMenu().draw(); @@ -233,8 +233,11 @@ void FrameBuffer::update() if(myMsg.counter > 0) drawMessage(); + // Do any post-frame stuff + postFrameUpdate(); + // The frame doesn't need to be completely redrawn anymore - theRedrawTIAIndicator = false; + myRedrawEntireFrame = false; } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -244,7 +247,7 @@ void FrameBuffer::showMessage(const string& message, MessagePosition position, // Erase old messages on the screen if(myMsg.counter > 0) { - theRedrawTIAIndicator = true; + myRedrawEntireFrame = true; myOSystem->eventHandler().refreshDisplay(); } @@ -359,7 +362,7 @@ inline void FrameBuffer::drawMessage() myOSystem->eventHandler().refreshDisplay(true); else { - myMsg.surface->addDirtyRect(0, 0, 0, 0); + myMsg.surface->addDirtyRect(0, 0, 0, 0); // force a full draw myMsg.surface->update(); } } @@ -367,7 +370,7 @@ inline void FrameBuffer::drawMessage() // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - void FrameBuffer::refresh() { - theRedrawTIAIndicator = true; + myRedrawEntireFrame = true; } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -405,7 +408,7 @@ void FrameBuffer::setTIAPalette(const uInt32* palette) } } - theRedrawTIAIndicator = true; + myRedrawEntireFrame = true; } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/stella/src/emucore/FrameBuffer.hxx b/stella/src/emucore/FrameBuffer.hxx index e33f1b53d..ba3a9307b 100644 --- a/stella/src/emucore/FrameBuffer.hxx +++ b/stella/src/emucore/FrameBuffer.hxx @@ -13,7 +13,7 @@ // See the file "license" for information on usage and redistribution of // this file, and for a DISCLAIMER OF ALL WARRANTIES. // -// $Id: FrameBuffer.hxx,v 1.103 2008-08-01 12:16:00 stephena Exp $ +// $Id: FrameBuffer.hxx,v 1.104 2008-08-04 11:56:12 stephena Exp $ //============================================================================ #ifndef FRAMEBUFFER_HXX @@ -90,7 +90,7 @@ enum { turn drawn here as well. @author Stephen Anthony - @version $Id: FrameBuffer.hxx,v 1.103 2008-08-01 12:16:00 stephena Exp $ + @version $Id: FrameBuffer.hxx,v 1.104 2008-08-04 11:56:12 stephena Exp $ */ class FrameBuffer { @@ -354,6 +354,11 @@ class FrameBuffer */ virtual void drawMediaSource() = 0; + /** + This method is called after any drawing is done (per-frame). + */ + virtual void postFrameUpdate() = 0; + /** This method is called to provide information about the FrameBuffer. */ @@ -369,8 +374,8 @@ class FrameBuffer // SDL initialization flags uInt32 mySDLFlags; - // Indicates if the TIA area should be redrawn - bool theRedrawTIAIndicator; + // Indicates if the entire frame need to redrawn + bool myRedrawEntireFrame; // Use phosphor effect (aka no flicker on 30Hz screens) bool myUsePhosphor; @@ -511,7 +516,7 @@ class FrameBuffer FrameBuffer type. @author Stephen Anthony - @version $Id: FrameBuffer.hxx,v 1.103 2008-08-01 12:16:00 stephena Exp $ + @version $Id: FrameBuffer.hxx,v 1.104 2008-08-04 11:56:12 stephena Exp $ */ // Text alignment modes for drawString() enum TextAlignment {