1/*
2 * Copyright (C) 2012 Google 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 *
8 * 1.  Redistributions of source code must retain the above copyright
9 *     notice, this list of conditions and the following disclaimer.
10 * 2.  Redistributions in binary form must reproduce the above copyright
11 *     notice, this list of conditions and the following disclaimer in the
12 *     documentation and/or other materials provided with the distribution.
13 *
14 * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
15 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
16 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17 * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
18 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
19 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
20 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
21 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
23 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24 */
25
26#include "config.h"
27#include "platform/graphics/DecodingImageGenerator.h"
28
29#include "SkData.h"
30#include "SkImageInfo.h"
31#include "platform/PlatformInstrumentation.h"
32#include "platform/RuntimeEnabledFeatures.h"
33#include "platform/SharedBuffer.h"
34#include "platform/TraceEvent.h"
35#include "platform/graphics/ImageFrameGenerator.h"
36
37namespace blink {
38
39DecodingImageGenerator::DecodingImageGenerator(PassRefPtr<ImageFrameGenerator> frameGenerator, const SkImageInfo& info, size_t index)
40    : m_frameGenerator(frameGenerator)
41    , m_imageInfo(info)
42    , m_frameIndex(index)
43    , m_generationId(0)
44{
45}
46
47DecodingImageGenerator::~DecodingImageGenerator()
48{
49}
50
51SkData* DecodingImageGenerator::onRefEncodedData()
52{
53    // FIXME: If the image has been clipped or scaled, do not return the original
54    // encoded data, since on playback it will not be known how the clipping/scaling
55    // was done.
56    RefPtr<SharedBuffer> buffer = nullptr;
57    bool allDataReceived = false;
58    m_frameGenerator->copyData(&buffer, &allDataReceived);
59    if (buffer && allDataReceived)
60        return SkData::NewWithCopy(buffer->data(), buffer->size());
61    return 0;
62}
63
64bool DecodingImageGenerator::onGetInfo(SkImageInfo* info)
65{
66    *info = m_imageInfo;
67    return true;
68}
69
70bool DecodingImageGenerator::onGetPixels(const SkImageInfo& info, void* pixels, size_t rowBytes, SkPMColor ctable[], int* ctableCount)
71{
72    TRACE_EVENT1("blink", "DecodingImageGenerator::getPixels", "index", static_cast<int>(m_frameIndex));
73
74    // Implementation doesn't support scaling yet so make sure we're not given a different size.
75    if (info.width() != m_imageInfo.width() || info.height() != m_imageInfo.height() || info.colorType() != m_imageInfo.colorType()) {
76        // ImageFrame may have changed the owning SkBitmap to kOpaque_SkAlphaType after sniffing the encoded data, so if we see a request
77        // for opaque, that is ok even if our initial alphatype was not opaque.
78        return false;
79    }
80
81    PlatformInstrumentation::willDecodeLazyPixelRef(m_generationId);
82    bool decoded = m_frameGenerator->decodeAndScale(m_imageInfo, m_frameIndex, pixels, rowBytes);
83    PlatformInstrumentation::didDecodeLazyPixelRef();
84    return decoded;
85}
86
87bool DecodingImageGenerator::onGetYUV8Planes(SkISize sizes[3], void* planes[3], size_t rowBytes[3], SkYUVColorSpace* colorSpace)
88{
89    if (!RuntimeEnabledFeatures::decodeToYUVEnabled())
90        return false;
91
92    if (!planes || !planes[0])
93        return m_frameGenerator->getYUVComponentSizes(sizes);
94
95    TRACE_EVENT0("blink", "DecodingImageGenerator::onGetYUV8Planes");
96    PlatformInstrumentation::willDecodeLazyPixelRef(m_generationId);
97    bool decoded = m_frameGenerator->decodeToYUV(sizes, planes, rowBytes);
98    PlatformInstrumentation::didDecodeLazyPixelRef();
99    if (colorSpace)
100        *colorSpace = kJPEG_SkYUVColorSpace;
101    return decoded;
102}
103
104} // namespace blink
105