Bug 590252 - part 2 - Make decoder implementations use the Decoder superclass invalidation framework.r=joe,a=blocker
authorBobby Holley <bobbyholley@gmail.com>
Tue, 24 Aug 2010 17:12:04 -0400
changeset 51592 5875f7dbf9c66bb6e2574624d3a743acd7d52ac4
parent 51591 24ae66f16d4499cc171c5796e1e9d9304b76f179
child 51593 9cf06ffbf06e2cad0a00f5af33efbd805a1c68d3
push idunknown
push userunknown
push dateunknown
reviewersjoe, blocker
bugs590252
milestone2.0b5pre
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 590252 - part 2 - Make decoder implementations use the Decoder superclass invalidation framework.r=joe,a=blocker
modules/libpr0n/decoders/nsBMPDecoder.cpp
modules/libpr0n/decoders/nsGIFDecoder2.cpp
modules/libpr0n/decoders/nsICODecoder.cpp
modules/libpr0n/decoders/nsIconDecoder.cpp
modules/libpr0n/decoders/nsJPEGDecoder.cpp
modules/libpr0n/decoders/nsPNGDecoder.cpp
modules/libpr0n/src/RasterImage.cpp
modules/libpr0n/src/RasterImage.h
--- a/modules/libpr0n/decoders/nsBMPDecoder.cpp
+++ b/modules/libpr0n/decoders/nsBMPDecoder.cpp
@@ -579,25 +579,22 @@ nsBMPDecoder::WriteInternal(const char* 
                     break;
                 }
             }
         }
     }
     
     const PRUint32 rows = mOldLine - mCurLine;
     if (rows) {
+
+        // Invalidate
         nsIntRect r(0, mBIH.height < 0 ? -mBIH.height - mOldLine : mCurLine,
                     mBIH.width, rows);
+        PostInvalidation(r);
 
-        // Tell the image that its data has been updated
-        rv = mImage->FrameUpdated(0, r); 
-        NS_ENSURE_SUCCESS(rv, rv);
-
-        if (mObserver)
-            mObserver->OnDataAvailable(nsnull, PR_TRUE, &r);
         mOldLine = mCurLine;
     }
 
     return NS_OK;
 }
 
 void nsBMPDecoder::ProcessFileHeader()
 {
--- a/modules/libpr0n/decoders/nsGIFDecoder2.cpp
+++ b/modules/libpr0n/decoders/nsGIFDecoder2.cpp
@@ -158,29 +158,18 @@ nsGIFDecoder2::FinishInternal()
 
 // Push any new rows according to mCurrentPass/mLastFlushedPass and
 // mCurrentRow/mLastFlushedRow.  Note: caller is responsible for
 // updating mlastFlushed{Row,Pass}.
 nsresult
 nsGIFDecoder2::FlushImageData(PRUint32 fromRow, PRUint32 rows)
 {
   nsIntRect r(mGIFStruct.x_offset, mGIFStruct.y_offset + fromRow, mGIFStruct.width, rows);
-
-  // Update image  
-  nsresult rv = mImage->FrameUpdated(mGIFStruct.images_decoded, r);
-  if (NS_FAILED(rv)) {
-    return rv;
-  }
+  PostInvalidation(r);
 
-  // Offset to the frame position
-  // Only notify observer(s) for first frame
-  if (!mGIFStruct.images_decoded && mObserver) {
-    PRUint32 imgCurFrame = mImage->GetCurrentFrameIndex();
-    mObserver->OnDataAvailable(nsnull, imgCurFrame == PRUint32(mGIFStruct.images_decoded), &r);
-  }
   return NS_OK;
 }
 
 nsresult
 nsGIFDecoder2::FlushImageData()
 {
   nsresult rv = NS_OK;
 
@@ -280,32 +269,16 @@ void nsGIFDecoder2::EndGIF(PRBool aSucce
 
   mGIFOpen = PR_FALSE;
   mEnded = PR_TRUE;
 }
 
 //******************************************************************************
 nsresult nsGIFDecoder2::BeginImageFrame(gfx_depth aDepth)
 {
-  if (!mGIFStruct.images_decoded) {
-    // Send a onetime OnDataAvailable (Display Refresh) for the first frame
-    // if it has a y-axis offset.  Otherwise, the area may never be refreshed
-    // and the placeholder will remain on the screen. (Bug 37589)
-    if (mGIFStruct.y_offset > 0) {
-      PRInt32 imgWidth;
-      mImage->GetWidth(&imgWidth);
-      PRUint32 imgCurFrame = mImage->GetCurrentFrameIndex();
-      nsIntRect r(0, 0, imgWidth, mGIFStruct.y_offset);
-      if (mObserver)
-        mObserver->OnDataAvailable(nsnull,
-                                   imgCurFrame == PRUint32(mGIFStruct.images_decoded),
-                                   &r);
-    }
-  }
-
   PRUint32 imageDataLength;
   nsresult rv;
   gfxASurface::gfxImageFormat format;
   if (mGIFStruct.is_transparent)
     format = gfxASurface::ImageFormatARGB32;
   else
     format = gfxASurface::ImageFormatRGB24;
 
@@ -328,42 +301,50 @@ nsresult nsGIFDecoder2::BeginImageFrame(
     return rv;
 
   mImage->SetFrameDisposalMethod(mGIFStruct.images_decoded,
                                  mGIFStruct.disposal_method);
 
   // Tell the superclass we're starting a frame
   PostFrameStart();
 
+  if (!mGIFStruct.images_decoded) {
+    // Send a onetime invalidation for the first frame if it has a y-axis offset. 
+    // Otherwise, the area may never be refreshed and the placeholder will remain
+    // on the screen. (Bug 37589)
+    if (mGIFStruct.y_offset > 0) {
+      PRInt32 imgWidth;
+      mImage->GetWidth(&imgWidth);
+      nsIntRect r(0, 0, imgWidth, mGIFStruct.y_offset);
+      PostInvalidation(r);
+    }
+  }
+
   mCurrentFrame = mGIFStruct.images_decoded;
   return NS_OK;
 }
 
 
 //******************************************************************************
 void nsGIFDecoder2::EndImageFrame()
 {
   // First flush all pending image data 
   if (!mGIFStruct.images_decoded) {
     // Only need to flush first frame
     (void) FlushImageData();
 
-    // If the first frame is smaller in height than the entire image, send a
-    // OnDataAvailable (Display Refresh) for the area it does not have data for.
+    // If the first frame is smaller in height than the entire image, send an
+    // invalidation for the area it does not have data for.
     // This will clear the remaining bits of the placeholder. (Bug 37589)
     const PRUint32 realFrameHeight = mGIFStruct.height + mGIFStruct.y_offset;
     if (realFrameHeight < mGIFStruct.screen_height) {
-      PRUint32 imgCurFrame = mImage->GetCurrentFrameIndex();
       nsIntRect r(0, realFrameHeight,
                   mGIFStruct.screen_width,
                   mGIFStruct.screen_height - realFrameHeight);
-      if (mObserver)
-        mObserver->OnDataAvailable(nsnull,
-                                  imgCurFrame == PRUint32(mGIFStruct.images_decoded),
-                                  &r);
+      PostInvalidation(r);
     }
     // This transparency check is only valid for first frame
     if (mGIFStruct.is_transparent && !mSawTransparency) {
       mImage->SetFrameHasNoAlpha(mGIFStruct.images_decoded);
     }
   }
   mCurrentRow = mLastFlushedRow = -1;
   mCurrentPass = mLastFlushedPass = 0;
--- a/modules/libpr0n/decoders/nsICODecoder.cpp
+++ b/modules/libpr0n/decoders/nsICODecoder.cpp
@@ -116,24 +116,21 @@ nsICODecoder::FinishInternal()
 {
   nsresult rv = NS_OK;
 
   // We should never make multiple frames
   NS_ABORT_IF_FALSE(GetFrameCount() <= 1, "Multiple ICO frames?");
 
   // Send notifications if appropriate
   if (!IsSizeDecode() && !mError && (GetFrameCount() == 1)) {
-    // Tell the image that it's data has been updated 
-    nsIntRect r(0, 0, mDirEntry.mWidth, mDirEntry.mHeight);
-    rv = mImage->FrameUpdated(0, r);
 
+    // Invalidate
+    nsIntRect r(0, 0, mDirEntry.mWidth, mDirEntry.mHeight);
+    PostInvalidation(r);
 
-    if (mObserver) {
-      mObserver->OnDataAvailable(nsnull, PR_TRUE, &r);
-    }
     PostFrameStop();
     mImage->DecodingComplete();
     if (mObserver) {
       mObserver->OnStopContainer(nsnull, 0);
       mObserver->OnStopDecode(nsnull, NS_OK, nsnull);
     }
   }
 
--- a/modules/libpr0n/decoders/nsIconDecoder.cpp
+++ b/modules/libpr0n/decoders/nsIconDecoder.cpp
@@ -149,24 +149,18 @@ nsIconDecoder::WriteInternal(const char 
       case iconStateReadPixels:
 
         // How many bytes are we reading?
         bytesToRead = PR_MIN(aCount, mPixBytesTotal - mPixBytesRead);
 
         // Copy the bytes
         memcpy(mImageData + mPixBytesRead, aBuffer, bytesToRead);
 
-        // Notify
-        rv = mImage->FrameUpdated(0, r);
-        if (NS_FAILED(rv)) {
-          mState = iconStateError;
-          return rv;
-        }
-        if (mObserver)
-          mObserver->OnDataAvailable(nsnull, PR_TRUE, &r);
+        // Invalidate
+        PostInvalidation(r);
 
         // Book Keeping
         aBuffer += bytesToRead;
         aCount -= bytesToRead;
         mPixBytesRead += bytesToRead;
 
         // If we've got all the pixel bytes, we're finished
         if (mPixBytesRead == mPixBytesTotal) {
--- a/modules/libpr0n/decoders/nsJPEGDecoder.cpp
+++ b/modules/libpr0n/decoders/nsJPEGDecoder.cpp
@@ -669,19 +669,17 @@ nsJPEGDecoder::OutputScanlines(PRBool* s
         // 32-bit read of final pixel will exceed buffer, so read bytes
         *imageRow++ = GFX_PACKED_PIXEL(0xFF, sampleRow[0], sampleRow[1], sampleRow[2]);
         sampleRow += 3;
       }
   }
 
   if (top != mInfo.output_scanline) {
       nsIntRect r(0, top, mInfo.output_width, mInfo.output_scanline-top);
-      rv = mImage->FrameUpdated(0, r);
-      if (mObserver)
-        mObserver->OnDataAvailable(nsnull, PR_TRUE, &r);
+      PostInvalidation(r);
   }
 
   return rv;
 }
 
 
 /* Override the standard error method in the IJG JPEG decoder code. */
 METHODDEF(void)
--- a/modules/libpr0n/decoders/nsPNGDecoder.cpp
+++ b/modules/libpr0n/decoders/nsPNGDecoder.cpp
@@ -199,24 +199,17 @@ void nsPNGDecoder::EndImageFrame()
   numFrames = mImage->GetNumFrames();
 
   // We can't use mPNG->num_frames_read as it may be one ahead.
   if (numFrames > 1) {
     // Tell the image renderer that the frame is complete
     if (mFrameHasNoAlpha)
       mImage->SetFrameHasNoAlpha(numFrames - 1);
 
-    if (NS_FAILED(mImage->FrameUpdated(numFrames - 1, mFrameRect))) {
-      mError = PR_TRUE;
-      // allow the call out to the observers.
-    }
-    PRUint32 curFrame = mImage->GetCurrentFrameIndex();
-    if (mObserver)
-      mObserver->OnDataAvailable(nsnull, curFrame == numFrames - 1,
-                                 &mFrameRect);
+    PostInvalidation(mFrameRect);
   }
 #endif
 
   mImage->EndFrameDecode(numFrames - 1);
   PostFrameStop();
 }
 
 nsresult
@@ -804,25 +797,19 @@ nsPNGDecoder::row_callback(png_structp p
     }
 
     if (!rowHasNoAlpha)
       decoder->mFrameHasNoAlpha = PR_FALSE;
 
     PRUint32 numFrames = decoder->mImage->GetNumFrames();
     if (numFrames <= 1) {
       // Only do incremental image display for the first frame
+      // XXXbholley - this check should be handled in the superclass
       nsIntRect r(0, row_num, width, 1);
-      if (NS_FAILED(decoder->mImage->FrameUpdated(numFrames - 1, r))) {
-        decoder->mError = PR_TRUE;  /* bail */
-        return;
-      }
-      PRUint32 curFrame = decoder->mImage->GetCurrentFrameIndex();
-      if (decoder->mObserver)
-        decoder->mObserver->OnDataAvailable(nsnull,
-                                            curFrame == numFrames - 1, &r);
+      decoder->PostInvalidation(r);
     }
   }
 }
 
 // got the header of a new frame that's coming
 void
 nsPNGDecoder::frame_info_callback(png_structp png_ptr, png_uint_32 frame_num)
 {
--- a/modules/libpr0n/src/RasterImage.cpp
+++ b/modules/libpr0n/src/RasterImage.cpp
@@ -922,29 +922,25 @@ RasterImage::EnsureCleanFrame(PRUint32 a
 
   // We can re-use the frame.
   frame->GetImageData(imageData, imageLength);
 
   return NS_OK;
 }
 
 
-nsresult
+void
 RasterImage::FrameUpdated(PRUint32 aFrameNum, nsIntRect &aUpdatedRect)
 {
   NS_ABORT_IF_FALSE(aFrameNum < mFrames.Length(), "Invalid frame index!");
 
   imgFrame *frame = GetImgFrame(aFrameNum);
   NS_ABORT_IF_FALSE(frame, "Calling FrameUpdated on frame that doesn't exist!");
 
   frame->ImageUpdated(aUpdatedRect);
-
-  // XXXbholley - this should turn into a void method as soon the decoders
-  // stop using it
-  return NS_OK;
 }
 
 nsresult
 RasterImage::SetFrameDisposalMethod(PRUint32 aFrameNum,
                                     PRInt32 aDisposalMethod)
 {
   if (mError)
     return NS_ERROR_FAILURE;
--- a/modules/libpr0n/src/RasterImage.h
+++ b/modules/libpr0n/src/RasterImage.h
@@ -221,17 +221,17 @@ public:
                                PRInt32 aWidth, PRInt32 aHeight,
                                gfxASurface::gfxImageFormat aFormat,
                                PRUint8 aPaletteDepth,
                                PRUint8**  imageData,
                                PRUint32*  imageLength,
                                PRUint32** paletteData,
                                PRUint32*  paletteLength);
 
-  nsresult FrameUpdated(PRUint32 aFrameNum, nsIntRect& aUpdatedRect);
+  void FrameUpdated(PRUint32 aFrameNum, nsIntRect& aUpdatedRect);
 
   /* notification when the current frame is done decoding */
   nsresult EndFrameDecode(PRUint32 aFrameNum);
 
   /* notification that the entire image has been decoded */
   nsresult DecodingComplete();
 
   /**