diff options
author | 2017-05-23 09:37:21 -0400 | |
---|---|---|
committer | 2017-05-23 15:28:37 +0000 | |
commit | 557fbbe05ba48bcc20be684d11fe0edfc24c87ba (patch) | |
tree | de83760e6e67a0866578056b4091091cef29cc53 /src/codec/SkWebpCodec.h | |
parent | e980174d0f3af8e497d9c38851114cc6a3c02e9a (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.h | 59 |
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 |