Home | History | Annotate | Download | only in gif
      1 /*
      2  * Copyright (C) 2006 Apple Computer, Inc.  All rights reserved.
      3  *
      4  * Redistribution and use in source and binary forms, with or without
      5  * modification, are permitted provided that the following conditions
      6  * are met:
      7  * 1. Redistributions of source code must retain the above copyright
      8  *    notice, this list of conditions and the following disclaimer.
      9  * 2. Redistributions in binary form must reproduce the above copyright
     10  *    notice, this list of conditions and the following disclaimer in the
     11  *    documentation and/or other materials provided with the distribution.
     12  *
     13  * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
     14  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
     15  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
     16  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE COMPUTER, INC. OR
     17  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
     18  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
     19  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
     20  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
     21  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     22  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     23  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     24  */
     25 
     26 #include "config.h"
     27 #include "core/platform/image-decoders/gif/GIFImageDecoder.h"
     28 
     29 #include <limits>
     30 #include "core/platform/PlatformInstrumentation.h"
     31 #include "core/platform/image-decoders/gif/GIFImageReader.h"
     32 #include "wtf/NotFound.h"
     33 #include "wtf/PassOwnPtr.h"
     34 
     35 namespace WebCore {
     36 
     37 GIFImageDecoder::GIFImageDecoder(ImageSource::AlphaOption alphaOption,
     38                                  ImageSource::GammaAndColorProfileOption gammaAndColorProfileOption)
     39     : ImageDecoder(alphaOption, gammaAndColorProfileOption)
     40     , m_repetitionCount(cAnimationLoopOnce)
     41 {
     42 }
     43 
     44 GIFImageDecoder::~GIFImageDecoder()
     45 {
     46 }
     47 
     48 void GIFImageDecoder::setData(SharedBuffer* data, bool allDataReceived)
     49 {
     50     if (failed())
     51         return;
     52 
     53     ImageDecoder::setData(data, allDataReceived);
     54     if (m_reader)
     55         m_reader->setData(data);
     56 }
     57 
     58 bool GIFImageDecoder::isSizeAvailable()
     59 {
     60     if (!ImageDecoder::isSizeAvailable())
     61         parse(GIFSizeQuery);
     62 
     63     return ImageDecoder::isSizeAvailable();
     64 }
     65 
     66 size_t GIFImageDecoder::frameCount()
     67 {
     68     parse(GIFFrameCountQuery);
     69     return m_frameBufferCache.size();
     70 }
     71 
     72 int GIFImageDecoder::repetitionCount() const
     73 {
     74     // This value can arrive at any point in the image data stream.  Most GIFs
     75     // in the wild declare it near the beginning of the file, so it usually is
     76     // set by the time we've decoded the size, but (depending on the GIF and the
     77     // packets sent back by the webserver) not always.  If the reader hasn't
     78     // seen a loop count yet, it will return cLoopCountNotSeen, in which case we
     79     // should default to looping once (the initial value for
     80     // |m_repetitionCount|).
     81     //
     82     // There are some additional wrinkles here. First, ImageSource::clear()
     83     // may destroy the reader, making the result from the reader _less_
     84     // authoritative on future calls if the recreated reader hasn't seen the
     85     // loop count.  We don't need to special-case this because in this case the
     86     // new reader will once again return cLoopCountNotSeen, and we won't
     87     // overwrite the cached correct value.
     88     //
     89     // Second, a GIF might never set a loop count at all, in which case we
     90     // should continue to treat it as a "loop once" animation.  We don't need
     91     // special code here either, because in this case we'll never change
     92     // |m_repetitionCount| from its default value.
     93     //
     94     // Third, we use the same GIFImageReader for counting frames and we might
     95     // see the loop count and then encounter a decoding error which happens
     96     // later in the stream. It is also possible that no frames are in the
     97     // stream. In these cases we should just loop once.
     98     if (failed() || (m_reader && (!m_reader->imagesCount())))
     99         m_repetitionCount = cAnimationLoopOnce;
    100     else if (m_reader && m_reader->loopCount() != cLoopCountNotSeen)
    101         m_repetitionCount = m_reader->loopCount();
    102     return m_repetitionCount;
    103 }
    104 
    105 ImageFrame* GIFImageDecoder::frameBufferAtIndex(size_t index)
    106 {
    107     if (index >= frameCount())
    108         return 0;
    109 
    110     ImageFrame& frame = m_frameBufferCache[index];
    111     if (frame.status() != ImageFrame::FrameComplete) {
    112         PlatformInstrumentation::willDecodeImage("GIF");
    113         decode(index);
    114         PlatformInstrumentation::didDecodeImage();
    115     }
    116     return &frame;
    117 }
    118 
    119 bool GIFImageDecoder::frameIsCompleteAtIndex(size_t index) const
    120 {
    121     return m_reader && (index < m_reader->imagesCount()) && m_reader->frameContext(index)->isComplete();
    122 }
    123 
    124 float GIFImageDecoder::frameDurationAtIndex(size_t index) const
    125 {
    126     return (m_reader && (index < m_reader->imagesCount()) &&
    127         m_reader->frameContext(index)->isHeaderDefined()) ?
    128         m_reader->frameContext(index)->delayTime() : 0;
    129 }
    130 
    131 bool GIFImageDecoder::setFailed()
    132 {
    133     m_reader.clear();
    134     return ImageDecoder::setFailed();
    135 }
    136 
    137 // FIXME: Can the intermediate |rowBuffer| be avoided?
    138 bool GIFImageDecoder::haveDecodedRow(size_t frameIndex, const Vector<unsigned char>& rowBuffer, size_t width, size_t rowNumber, unsigned repeatCount, bool writeTransparentPixels)
    139 {
    140     const GIFFrameContext* frameContext = m_reader->frameContext(frameIndex);
    141     // The pixel data and coordinates supplied to us are relative to the frame's
    142     // origin within the entire image size, i.e.
    143     // (frameContext->xOffset, frameContext->yOffset). There is no guarantee
    144     // that width == (size().width() - frameContext->xOffset), so
    145     // we must ensure we don't run off the end of either the source data or the
    146     // row's X-coordinates.
    147     const int xBegin = frameContext->xOffset();
    148     const int yBegin = frameContext->yOffset() + rowNumber;
    149     const int xEnd = std::min(static_cast<int>(frameContext->xOffset() + width), size().width());
    150     const int yEnd = std::min(static_cast<int>(frameContext->yOffset() + rowNumber + repeatCount), size().height());
    151     if (rowBuffer.isEmpty() || (xBegin < 0) || (yBegin < 0) || (xEnd <= xBegin) || (yEnd <= yBegin))
    152         return true;
    153 
    154     const GIFColorMap::Table& colorTable = frameContext->localColorMap().isDefined() ? frameContext->localColorMap().table() : m_reader->globalColorMap().table();
    155 
    156     if (colorTable.isEmpty())
    157         return true;
    158 
    159     GIFColorMap::Table::const_iterator colorTableIter = colorTable.begin();
    160 
    161     // Initialize the frame if necessary.
    162     ImageFrame& buffer = m_frameBufferCache[frameIndex];
    163     if ((buffer.status() == ImageFrame::FrameEmpty) && !initFrameBuffer(frameIndex))
    164         return false;
    165 
    166     const size_t transparentPixel = frameContext->transparentPixel();
    167     Vector<unsigned char>::const_iterator rowBegin = rowBuffer.begin();
    168     Vector<unsigned char>::const_iterator rowEnd = rowBegin + (xEnd - xBegin);
    169     ImageFrame::PixelData* currentAddress = buffer.getAddr(xBegin, yBegin);
    170 
    171     // We may or may not need to write transparent pixels to the buffer.
    172     // If we're compositing against a previous image, it's wrong, and if
    173     // we're writing atop a cleared, fully transparent buffer, it's
    174     // unnecessary; but if we're decoding an interlaced gif and
    175     // displaying it "Haeberli"-style, we must write these for passes
    176     // beyond the first, or the initial passes will "show through" the
    177     // later ones.
    178     //
    179     // The loops below are almost identical. One writes a transparent pixel
    180     // and one doesn't based on the value of |writeTransparentPixels|.
    181     // The condition check is taken out of the loop to enhance performance.
    182     // This optimization reduces decoding time by about 15% for a 3MB image.
    183     if (writeTransparentPixels) {
    184         for (; rowBegin != rowEnd; ++rowBegin, ++currentAddress) {
    185             const size_t sourceValue = *rowBegin;
    186             if ((sourceValue != transparentPixel) && (sourceValue < colorTable.size())) {
    187                 *currentAddress = colorTableIter[sourceValue];
    188             } else {
    189                 *currentAddress = 0;
    190                 m_currentBufferSawAlpha = true;
    191             }
    192         }
    193     } else {
    194         for (; rowBegin != rowEnd; ++rowBegin, ++currentAddress) {
    195             const size_t sourceValue = *rowBegin;
    196             if ((sourceValue != transparentPixel) && (sourceValue < colorTable.size()))
    197                 *currentAddress = colorTableIter[sourceValue];
    198             else
    199                 m_currentBufferSawAlpha = true;
    200         }
    201     }
    202 
    203     // Tell the frame to copy the row data if need be.
    204     if (repeatCount > 1)
    205         buffer.copyRowNTimes(xBegin, xEnd, yBegin, yEnd);
    206 
    207     return true;
    208 }
    209 
    210 bool GIFImageDecoder::parseCompleted() const
    211 {
    212     return m_reader && m_reader->parseCompleted();
    213 }
    214 
    215 bool GIFImageDecoder::frameComplete(size_t frameIndex)
    216 {
    217     // Initialize the frame if necessary.  Some GIFs insert do-nothing frames,
    218     // in which case we never reach haveDecodedRow() before getting here.
    219     ImageFrame& buffer = m_frameBufferCache[frameIndex];
    220     if ((buffer.status() == ImageFrame::FrameEmpty) && !initFrameBuffer(frameIndex))
    221         return false; // initFrameBuffer() has already called setFailed().
    222 
    223     buffer.setStatus(ImageFrame::FrameComplete);
    224 
    225     if (!m_currentBufferSawAlpha) {
    226         // The whole frame was non-transparent, so it's possible that the entire
    227         // resulting buffer was non-transparent, and we can setHasAlpha(false).
    228         if (buffer.originalFrameRect().contains(IntRect(IntPoint(), size()))) {
    229             buffer.setHasAlpha(false);
    230             buffer.setRequiredPreviousFrameIndex(notFound);
    231         } else if (buffer.requiredPreviousFrameIndex() != notFound) {
    232             // Tricky case.  This frame does not have alpha only if everywhere
    233             // outside its rect doesn't have alpha.  To know whether this is
    234             // true, we check the start state of the frame -- if it doesn't have
    235             // alpha, we're safe.
    236             const ImageFrame* prevBuffer = &m_frameBufferCache[buffer.requiredPreviousFrameIndex()];
    237             ASSERT(prevBuffer->disposalMethod() != ImageFrame::DisposeOverwritePrevious);
    238 
    239             // Now, if we're at a DisposeNotSpecified or DisposeKeep frame, then
    240             // we can say we have no alpha if that frame had no alpha.  But
    241             // since in initFrameBuffer() we already copied that frame's alpha
    242             // state into the current frame's, we need do nothing at all here.
    243             //
    244             // The only remaining case is a DisposeOverwriteBgcolor frame.  If
    245             // it had no alpha, and its rect is contained in the current frame's
    246             // rect, we know the current frame has no alpha.
    247             if ((prevBuffer->disposalMethod() == ImageFrame::DisposeOverwriteBgcolor) && !prevBuffer->hasAlpha() && buffer.originalFrameRect().contains(prevBuffer->originalFrameRect()))
    248                 buffer.setHasAlpha(false);
    249         }
    250     }
    251 
    252     return true;
    253 }
    254 
    255 size_t GIFImageDecoder::clearCacheExceptFrame(size_t clearExceptFrame)
    256 {
    257     // We need to preserve frames such that:
    258     //  1. We don't clear |clearExceptFrame|;
    259     //  2. We don't clear any frame from which a future initFrameBuffer() call
    260     //     will copy bitmap data.
    261     // All other frames can be cleared.
    262     while ((clearExceptFrame < m_frameBufferCache.size()) && (m_frameBufferCache[clearExceptFrame].status() == ImageFrame::FrameEmpty))
    263         clearExceptFrame = m_frameBufferCache[clearExceptFrame].requiredPreviousFrameIndex();
    264 
    265     return ImageDecoder::clearCacheExceptFrame(clearExceptFrame);
    266 }
    267 
    268 void GIFImageDecoder::clearFrameBuffer(size_t frameIndex)
    269 {
    270     if (m_reader && m_frameBufferCache[frameIndex].status() == ImageFrame::FramePartial) {
    271         // Reset the state of the partial frame in the reader so that the frame
    272         // can be decoded again when requested.
    273         m_reader->clearDecodeState(frameIndex);
    274     }
    275     ImageDecoder::clearFrameBuffer(frameIndex);
    276 }
    277 
    278 void GIFImageDecoder::parse(GIFParseQuery query)
    279 {
    280     if (failed())
    281         return;
    282 
    283     if (!m_reader) {
    284         m_reader = adoptPtr(new GIFImageReader(this));
    285         m_reader->setData(m_data);
    286     }
    287 
    288     if (!m_reader->parse(query)) {
    289         setFailed();
    290         return;
    291     }
    292 
    293     const size_t oldSize = m_frameBufferCache.size();
    294     m_frameBufferCache.resize(m_reader->imagesCount());
    295 
    296     for (size_t i = oldSize; i < m_reader->imagesCount(); ++i) {
    297         ImageFrame& buffer = m_frameBufferCache[i];
    298         const GIFFrameContext* frameContext = m_reader->frameContext(i);
    299         buffer.setPremultiplyAlpha(m_premultiplyAlpha);
    300         buffer.setRequiredPreviousFrameIndex(findRequiredPreviousFrame(i));
    301         buffer.setDuration(frameContext->delayTime());
    302         buffer.setDisposalMethod(frameContext->disposalMethod());
    303 
    304         // Initialize the frame rect in our buffer.
    305         IntRect frameRect = frameContext->frameRect();
    306 
    307         // Make sure the frameRect doesn't extend outside the buffer.
    308         if (frameRect.maxX() > size().width())
    309             frameRect.setWidth(size().width() - frameRect.x());
    310         if (frameRect.maxY() > size().height())
    311             frameRect.setHeight(size().height() - frameRect.y());
    312 
    313         buffer.setOriginalFrameRect(frameRect);
    314     }
    315 }
    316 
    317 void GIFImageDecoder::decode(size_t frameIndex)
    318 {
    319     parse(GIFFrameCountQuery);
    320 
    321     if (failed())
    322         return;
    323 
    324     Vector<size_t> framesToDecode;
    325     size_t frameToDecode = frameIndex;
    326     do {
    327         framesToDecode.append(frameToDecode);
    328         frameToDecode = m_frameBufferCache[frameToDecode].requiredPreviousFrameIndex();
    329     } while (frameToDecode != notFound && m_frameBufferCache[frameToDecode].status() != ImageFrame::FrameComplete);
    330 
    331     for (size_t i = framesToDecode.size(); i > 0; --i) {
    332         size_t frameIndex = framesToDecode[i - 1];
    333         if (!m_reader->decode(frameIndex)) {
    334             setFailed();
    335             return;
    336         }
    337 
    338         // We need more data to continue decoding.
    339         if (m_frameBufferCache[frameIndex].status() != ImageFrame::FrameComplete)
    340             break;
    341     }
    342 
    343     // It is also a fatal error if all data is received and we have decoded all
    344     // frames available but the file is truncated.
    345     if (frameIndex >= m_frameBufferCache.size() - 1 && isAllDataReceived() && m_reader && !m_reader->parseCompleted())
    346         setFailed();
    347 }
    348 
    349 bool GIFImageDecoder::initFrameBuffer(size_t frameIndex)
    350 {
    351     // Initialize the frame rect in our buffer.
    352     const GIFFrameContext* frameContext = m_reader->frameContext(frameIndex);
    353     ImageFrame* const buffer = &m_frameBufferCache[frameIndex];
    354 
    355     size_t requiredPreviousFrameIndex = buffer->requiredPreviousFrameIndex();
    356     if (requiredPreviousFrameIndex == notFound) {
    357         // This frame doesn't rely on any previous data.
    358         if (!buffer->setSize(size().width(), size().height()))
    359             return setFailed();
    360     } else {
    361         const ImageFrame* prevBuffer = &m_frameBufferCache[requiredPreviousFrameIndex];
    362         ASSERT(prevBuffer->status() == ImageFrame::FrameComplete);
    363 
    364         // Preserve the last frame as the starting state for this frame.
    365         if (!buffer->copyBitmapData(*prevBuffer))
    366             return setFailed();
    367 
    368         if (prevBuffer->disposalMethod() == ImageFrame::DisposeOverwriteBgcolor) {
    369             // We want to clear the previous frame to transparent, without
    370             // affecting pixels in the image outside of the frame.
    371             const IntRect& prevRect = prevBuffer->originalFrameRect();
    372             ASSERT(!prevRect.contains(IntRect(IntPoint(), size())));
    373             buffer->zeroFillFrameRect(prevRect);
    374         }
    375     }
    376 
    377     // Update our status to be partially complete.
    378     buffer->setStatus(ImageFrame::FramePartial);
    379 
    380     // Reset the alpha pixel tracker for this frame.
    381     m_currentBufferSawAlpha = false;
    382     return true;
    383 }
    384 
    385 } // namespace WebCore
    386