Bug 1291054 (Part 4) - Add Decoder convenience methods for the common case of frame rects that cover the whole image. r=edwin
authorSeth Fowler <mark.seth.fowler@gmail.com>
Fri, 29 Jul 2016 14:26:23 -0700
changeset 307670 21260281d5013a679b80f1fe7103c1337347a736
parent 307669 a2f8694f12c890db95ccfecd929a201d03ddb99d
child 307671 b617b61db290b61a34ad0471460989b816e8142b
push id80158
push userseth.bugzilla@blackhail.net
push dateTue, 02 Aug 2016 11:11:09 +0000
treeherdermozilla-inbound@8248ff77be0f [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersedwin
bugs1291054
milestone51.0a1
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 1291054 (Part 4) - Add Decoder convenience methods for the common case of frame rects that cover the whole image. r=edwin
image/Decoder.h
image/decoders/nsBMPDecoder.cpp
image/decoders/nsIconDecoder.cpp
image/decoders/nsJPEGDecoder.cpp
image/decoders/nsPNGDecoder.cpp
--- a/image/Decoder.h
+++ b/image/Decoder.h
@@ -268,28 +268,56 @@ public:
    */
   gfx::IntSize Size() const
   {
     MOZ_ASSERT(HasSize());
     return mImageMetadata.GetSize();
   }
 
   /**
+   * @return an IntRect which covers the entire area of this image at its
+   * intrinsic size, appropriate for use as a frame rect when the image itself
+   * does not specify one.
+   *
+   * Illegal to call if HasSize() returns false.
+   */
+  gfx::IntRect FullFrame() const
+  {
+    return gfx::IntRect(gfx::IntPoint(), Size());
+  }
+
+  /**
    * @return the output size of this decoder. If this is different than the
    * intrinsic size, then the image will be downscaled during the decoding
    * process.
    *
    * Illegal to call if HasSize() returns false.
    */
   gfx::IntSize OutputSize() const
   {
     return mDownscaler ? mDownscaler->TargetSize()
                        : Size();
   }
 
+  /**
+   * @return an IntRect which covers the entire area of this image at its size
+   * after scaling - that is, at its output size.
+   *
+   * XXX(seth): This is only used for decoders which are using the old
+   * Downscaler code instead of SurfacePipe, since the old AllocateFrame() and
+   * Downscaler APIs required that the frame rect be specified in output space.
+   * We should remove this once all decoders use SurfacePipe.
+   *
+   * Illegal to call if HasSize() returns false.
+   */
+  gfx::IntRect FullOutputFrame() const
+  {
+    return gfx::IntRect(gfx::IntPoint(), OutputSize());
+  }
+
   virtual Telemetry::ID SpeedHistogram();
 
   ImageMetadata& GetImageMetadata() { return mImageMetadata; }
 
   /**
    * @return a weak pointer to the image associated with this decoder. Illegal
    * to call if this decoder is not associated with an image.
    */
@@ -406,18 +434,17 @@ protected:
   nsresult AllocateFrame(uint32_t aFrameNum,
                          const nsIntSize& aTargetSize,
                          const nsIntRect& aFrameRect,
                          gfx::SurfaceFormat aFormat,
                          uint8_t aPaletteDepth = 0);
 
   /// Helper method for decoders which only have 'basic' frame allocation needs.
   nsresult AllocateBasicFrame() {
-    return AllocateFrame(0, Size(), gfx::IntRect(gfx::IntPoint(), Size()),
-                         gfx::SurfaceFormat::B8G8R8A8);
+    return AllocateFrame(0, Size(), FullFrame(), gfx::SurfaceFormat::B8G8R8A8);
   }
 
 private:
   /// Report that an error was encountered while decoding.
   void PostError();
 
   /**
    * CompleteDecode() finishes up the decoding process after Decode() determines
--- a/image/decoders/nsBMPDecoder.cpp
+++ b/image/decoders/nsBMPDecoder.cpp
@@ -670,18 +670,17 @@ nsBMPDecoder::ReadBitfields(const char* 
     memset(mColors.get(), 0, 256 * sizeof(ColorTableEntry));
 
     // OS/2 Bitmaps have no padding byte.
     mBytesPerColor = (mH.mBIHSize == InfoHeaderLength::WIN_V2) ? 3 : 4;
   }
 
   MOZ_ASSERT(!mImageData, "Already have a buffer allocated?");
   nsresult rv = AllocateFrame(/* aFrameNum = */ 0, OutputSize(),
-                              IntRect(IntPoint(), OutputSize()),
-                              SurfaceFormat::B8G8R8A8);
+                              FullOutputFrame(), SurfaceFormat::B8G8R8A8);
   if (NS_FAILED(rv)) {
     return Transition::TerminateFailure();
   }
   MOZ_ASSERT(mImageData, "Should have a buffer now");
 
   if (mDownscaler) {
     // BMPs store their rows in reverse order, so the downscaler needs to
     // reverse them again when writing its output. Unless the height is
--- a/image/decoders/nsIconDecoder.cpp
+++ b/image/decoders/nsIconDecoder.cpp
@@ -66,18 +66,17 @@ nsIconDecoder::ReadHeader(const char* aD
   // If we're doing a metadata decode, we're done.
   if (IsMetadataDecode()) {
     return Transition::TerminateSuccess();
   }
 
   MOZ_ASSERT(!mImageData, "Already have a buffer allocated?");
   Maybe<SurfacePipe> pipe =
     SurfacePipeFactory::CreateSurfacePipe(this, 0, Size(), OutputSize(),
-                                          IntRect(IntPoint(), Size()),
-                                          SurfaceFormat::B8G8R8A8,
+                                          FullFrame(), SurfaceFormat::B8G8R8A8,
                                           SurfacePipeFlags());
   if (!pipe) {
     return Transition::TerminateFailure();
   }
 
   mPipe = Move(*pipe);
 
   MOZ_ASSERT(mImageData, "Should have a buffer now");
--- a/image/decoders/nsJPEGDecoder.cpp
+++ b/image/decoders/nsJPEGDecoder.cpp
@@ -384,18 +384,17 @@ nsJPEGDecoder::ReadJPEGData(const char* 
 
     // Don't allocate a giant and superfluous memory buffer
     // when not doing a progressive decode.
     mInfo.buffered_image = mDecodeStyle == PROGRESSIVE &&
                            jpeg_has_multiple_scans(&mInfo);
 
     MOZ_ASSERT(!mImageData, "Already have a buffer allocated?");
     nsresult rv = AllocateFrame(/* aFrameNum = */ 0, OutputSize(),
-                                IntRect(IntPoint(), OutputSize()),
-                                SurfaceFormat::B8G8R8A8);
+                                FullOutputFrame(), SurfaceFormat::B8G8R8A8);
     if (NS_FAILED(rv)) {
       mState = JPEG_ERROR;
       MOZ_LOG(sJPEGDecoderAccountingLog, LogLevel::Debug,
              ("} (could not initialize image frame)"));
       return Transition::TerminateFailure();
     }
 
     MOZ_ASSERT(mImageData, "Should have a buffer now");
--- a/image/decoders/nsPNGDecoder.cpp
+++ b/image/decoders/nsPNGDecoder.cpp
@@ -146,17 +146,17 @@ nsPNGDecoder::~nsPNGDecoder()
 nsPNGDecoder::TransparencyType
 nsPNGDecoder::GetTransparencyType(SurfaceFormat aFormat,
                                   const IntRect& aFrameRect)
 {
   // Check if the image has a transparent color in its palette.
   if (aFormat == SurfaceFormat::B8G8R8A8) {
     return TransparencyType::eAlpha;
   }
-  if (!IntRect(IntPoint(), Size()).IsEqualEdges(aFrameRect)) {
+  if (!aFrameRect.IsEqualEdges(FullFrame())) {
     MOZ_ASSERT(HasAnimation());
     return TransparencyType::eFrameRect;
   }
 
   return TransparencyType::eNone;
 }
 
 void