aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/codec/SkWebpCodec.h
diff options
context:
space:
mode:
authorGravatar Leon Scroggins III <scroggo@google.com>2017-05-23 09:37:21 -0400
committerGravatar Skia Commit-Bot <skia-commit-bot@chromium.org>2017-05-23 15:28:37 +0000
commit557fbbe05ba48bcc20be684d11fe0edfc24c87ba (patch)
treede83760e6e67a0866578056b4091091cef29cc53 /src/codec/SkWebpCodec.h
parente980174d0f3af8e497d9c38851114cc6a3c02e9a (diff)
Add animation support to SkWebpCodec
TBR=reed@google.com (No change to the public API, but changed a header file) SkWebpCodec: - Implement onGetFrameCount, onGetFrameInfo, and onGetRepetitionCount - Respect the alpha reported by libwebp. Although the spec states that it is only a hint, the libwebp encoder uses it properly. Respecting allows us to draw opaque images faster and decode them to 565. This also matches other SkCodecs (and Chromium). - onGetPixels: - Decode the frame requested, recursively decoding required frame if necessary - When blending with a prior frame, use SkRasterPipeline SkCodec: - Move check for negative index to getFrameInfo - Reset the colorXform if one is not needed SkCodecAnimation: - Add new blend enum, for WebP's (and APNG's) non-blending option SkFrameHolder: - New base classes for frames and the owner of the frames, allowing code sharing between SkWebpCodec and SkGifCodec (particularly for determining whether a frame has alpha and what frame it depends on) - When moving items from SkGIFFrameContext, use Skia conventions (i.e. int instead of unsigned) - Rename "delay time" to "duration", to match e.g. SkFrameInfo:: fDuration SkGifImageReader: - Move pieces to SkFrameHolder, and adapt to changes made in the process - Make setAlphaAndRequiredFrame (now on the base class SkFrameHolder) more general to support webp, and add support for frames that do not blend - Change SkGIFFrameContext from a struct to a class, to match how we use the distinction elsewhere (i.e. struct is a small object with public fields) - Rework hasTransparentPixel (now hasTransparency, since it returns true in some cases where there is not a transparent pixel) to better fit with the modified setAlphaAndRequiredFrame. Also be more consistent when there is no transparent pixel but no color map. - Simplify an if condition that was previously simplified in 2d61e717 but accidentally got reverted in a4db9be6 CodecAnimTest: - Test new animated webp files - Rearrange the test to more cleanly print alpha type mismatches for the first frame resources: - webp-animated.webp - animated webp from Chromium - blendBG.webp - new webp file using bits of webp-animated-semitransparent4.webp from Chromium - tests required frame and alpha when using the non-blending mode - frames have the following properties: - Frame 0: no alpha, fills screen - Frame 1: alpha, fills screen - Frame 2: no alpha, fills screen - Frame 3: alpha, fills screen, blendBG - Frame 4: no alpha, fills screen, blendBG - Frame 5: alpha, blendBG - Frame 6: covers 4, has alpha, blendBG - also used to test decoding to 565 if the new frame data has alpha but blends onto an opaque frame DM.cpp: - Test animated images to non-native 8888 and unpremul DMSrcSink.cpp: - Do not test non-native 8888 decodes to f16 dst - Test unpremul decodes to f16 - Copy a frame of an animated image prior to drawing, since in unpremul mode, the DM code will premultiply first. Bug: skia: 3315 Change-Id: I4e55ae2ee5bc095b37a743bdcfac644be603b980 Reviewed-on: https://skia-review.googlesource.com/16707 Commit-Queue: Mike Reed <reed@google.com> Reviewed-by: Mike Reed <reed@google.com> Reviewed-by: Leon Scroggins <scroggo@google.com> Reviewed-by: Matt Sarett <msarett@google.com>
Diffstat (limited to 'src/codec/SkWebpCodec.h')
-rw-r--r--src/codec/SkWebpCodec.h59
1 files changed, 59 insertions, 0 deletions
diff --git a/src/codec/SkWebpCodec.h b/src/codec/SkWebpCodec.h
index 93b60f646e..f4c7910ee6 100644
--- a/src/codec/SkWebpCodec.h
+++ b/src/codec/SkWebpCodec.h
@@ -11,9 +11,12 @@
#include "SkCodec.h"
#include "SkColorSpace.h"
#include "SkEncodedImageFormat.h"
+#include "SkFrameHolder.h"
#include "SkImageInfo.h"
#include "SkTypes.h"
+#include <vector>
+
class SkStream;
extern "C" {
struct WebPDemuxer;
@@ -37,6 +40,11 @@ protected:
bool onDimensionsSupported(const SkISize&) override;
bool onGetValidSubset(SkIRect* /* desiredSubset */) const override;
+
+ int onGetFrameCount() override;
+ bool onGetFrameInfo(int, FrameInfo*) const override;
+ int onGetRepetitionCount() override;
+
private:
SkWebpCodec(int width, int height, const SkEncodedInfo&, sk_sp<SkColorSpace>, SkStream*,
WebPDemuxer*, sk_sp<SkData>);
@@ -47,6 +55,57 @@ private:
// This should not be freed until the decode is completed.
sk_sp<SkData> fData;
+ class Frame : public SkFrame {
+ public:
+ Frame(int i, bool alpha)
+ : INHERITED(i)
+ , fReportsAlpha(alpha)
+ {}
+ Frame(Frame&& other)
+ : INHERITED(other.frameId())
+ , fReportsAlpha(other.fReportsAlpha)
+ {}
+
+ protected:
+ bool onReportsAlpha() const override {
+ return fReportsAlpha;
+ }
+
+ private:
+ const bool fReportsAlpha;
+
+ typedef SkFrame INHERITED;
+ };
+
+ class FrameHolder : public SkFrameHolder {
+ public:
+ ~FrameHolder() override {}
+ void setScreenSize(int w, int h) {
+ fScreenWidth = w;
+ fScreenHeight = h;
+ }
+ Frame* appendNewFrame(bool hasAlpha);
+ const Frame* frame(int i) const;
+ int size() const {
+ return static_cast<int>(fFrames.size());
+ }
+ void reserve(int size) {
+ fFrames.reserve(size);
+ }
+
+ protected:
+ const SkFrame* onGetFrame(int i) const override;
+
+ private:
+ std::vector<Frame> fFrames;
+ };
+
+ FrameHolder fFrameHolder;
+ // Set to true if WebPDemuxGetFrame fails. This only means
+ // that we will cap the frame count to the frames that
+ // succeed.
+ bool fFailed;
+
typedef SkCodec INHERITED;
};
#endif // SkWebpCodec_DEFINED