15c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)/*
25267f701546148b83dfbe1d151cb184385bb5c22Torne (Richard Coles) * Copyright (C) 2013 Google Inc. All rights reserved.
35267f701546148b83dfbe1d151cb184385bb5c22Torne (Richard Coles) *
45c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * Redistribution and use in source and binary forms, with or without
55c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * modification, are permitted provided that the following conditions are
65c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * met:
75267f701546148b83dfbe1d151cb184385bb5c22Torne (Richard Coles) *
85c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) *     * Redistributions of source code must retain the above copyright
95c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * notice, this list of conditions and the following disclaimer.
105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) *     * Redistributions in binary form must reproduce the above
115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * copyright notice, this list of conditions and the following disclaimer
125c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * in the documentation and/or other materials provided with the
135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * distribution.
145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) *     * Neither the name of Google Inc. nor the names of its
155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * contributors may be used to endorse or promote products derived from
165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * this software without specific prior written permission.
175267f701546148b83dfbe1d151cb184385bb5c22Torne (Richard Coles) *
185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
275c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
295c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) */
305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
31bfe3590b1806e3ff18f46ee3af5d4b83078f305aTorne (Richard Coles)#include "config.h"
32f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)#include "core/animation/CompositorAnimations.h"
335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
347242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci#include "core/animation/AnimationNode.h"
3509380295ba73501a205346becac22c6978e4671dTorne (Richard Coles)#include "core/animation/AnimationTranslationUtil.h"
3651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)#include "core/animation/CompositorAnimationsImpl.h"
37197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch#include "core/animation/animatable/AnimatableDouble.h"
38197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch#include "core/animation/animatable/AnimatableFilterOperations.h"
39197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch#include "core/animation/animatable/AnimatableTransform.h"
40197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch#include "core/animation/animatable/AnimatableValue.h"
41f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)#include "core/rendering/RenderBoxModelObject.h"
42f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)#include "core/rendering/RenderLayer.h"
43f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)#include "core/rendering/RenderObject.h"
44d5428f32f5d1719f774f62e19147104ca245a3abTorne (Richard Coles)#include "core/rendering/compositing/CompositedLayerMapping.h"
45197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch#include "platform/geometry/FloatBox.h"
46f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)#include "public/platform/Platform.h"
479e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)#include "public/platform/WebCompositorAnimation.h"
48f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)#include "public/platform/WebCompositorSupport.h"
4951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)#include "public/platform/WebFilterAnimationCurve.h"
5051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)#include "public/platform/WebFilterKeyframe.h"
51f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)#include "public/platform/WebFloatAnimationCurve.h"
52f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)#include "public/platform/WebFloatKeyframe.h"
5351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)#include "public/platform/WebTransformAnimationCurve.h"
5451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)#include "public/platform/WebTransformKeyframe.h"
5551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
5651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)#include <algorithm>
5751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)#include <cmath>
585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
59c1847b1379d12d0e05df27436bf19a9b1bf12deaTorne (Richard Coles)namespace blink {
60bfe3590b1806e3ff18f46ee3af5d4b83078f305aTorne (Richard Coles)
6151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)namespace {
6251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
637242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tuccivoid getKeyframeValuesForProperty(const KeyframeEffectModelBase* effect, CSSPropertyID id, double scale, PropertySpecificKeyframeVector& values)
64bfe3590b1806e3ff18f46ee3af5d4b83078f305aTorne (Richard Coles){
6551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    ASSERT(values.isEmpty());
66a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch    const PropertySpecificKeyframeVector& group = effect->getPropertySpecificKeyframes(id);
6751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
687242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci    for (size_t i = 0; i < group.size(); ++i) {
697242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        double offset = group[i]->offset() * scale;
707242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        values.append(group[i]->cloneWithOffset(offset));
7151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    }
7251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)}
7351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
7451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)}
7551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
76197021e6b966cfb06891637935ef33fff06433d1Ben Murdochbool CompositorAnimations::getAnimatedBoundingBox(FloatBox& box, const AnimationEffect& effect, double minValue, double maxValue) const
77197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch{
78197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch    const KeyframeEffectModelBase& keyframeEffect = toKeyframeEffectModelBase(effect);
79197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch
80197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch    PropertySet properties = keyframeEffect.properties();
81197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch
82197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch    if (properties.isEmpty())
83197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch        return true;
84197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch
85197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch    minValue = std::min(minValue, 0.0);
86197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch    maxValue = std::max(maxValue, 1.0);
87197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch
88197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch    for (PropertySet::const_iterator it = properties.begin(); it != properties.end(); ++it) {
89197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch        // TODO: Add the ability to get expanded bounds for filters as well.
90197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch        if (*it != CSSPropertyTransform && *it != CSSPropertyWebkitTransform)
91197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            continue;
92197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch
93197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch        const PropertySpecificKeyframeVector& frames = keyframeEffect.getPropertySpecificKeyframes(*it);
94197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch        if (frames.isEmpty() || frames.size() < 2)
95197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            continue;
96197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch
97197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch        FloatBox originalBox(box);
98197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch
99197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch        for (size_t j = 0; j < frames.size() - 1; ++j) {
100197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            const AnimatableTransform* startTransform = toAnimatableTransform(frames[j]->getAnimatableValue().get());
101197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            const AnimatableTransform* endTransform = toAnimatableTransform(frames[j+1]->getAnimatableValue().get());
102197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            // TODO: Add support for inflating modes other than Replace.
103197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            if (frames[j]->composite() != AnimationEffect::CompositeReplace)
104197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch                return false;
105197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch
1067242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            const TimingFunction& timing = frames[j]->easing();
107197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            double min = 0;
108197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            double max = 1;
109197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            if (j == 0) {
110197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch                float frameLength = frames[j+1]->offset();
111197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch                if (frameLength > 0) {
112197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch                    min = minValue / frameLength;
113197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch                }
114197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            }
115197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch
116197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            if (j == frames.size() - 2) {
117197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch                float frameLength = frames[j+1]->offset() - frames[j]->offset();
118197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch                if (frameLength > 0) {
119197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch                    max = 1 + (maxValue - 1) / frameLength;
120197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch                }
121197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            }
122197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch
123197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            FloatBox bounds;
1247242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            timing.range(&min, &max);
125197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            if (!endTransform->transformOperations().blendedBoundsForBox(originalBox, startTransform->transformOperations(), min, max, &bounds))
126197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch                return false;
127197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            box.expandTo(bounds);
128197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch        }
129197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch    }
130197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch    return true;
131197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch}
132197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch
13351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)// -----------------------------------------------------------------------
13451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)// CompositorAnimations public API
13551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)// -----------------------------------------------------------------------
13651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
1377242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tuccibool CompositorAnimations::isCandidateForAnimationOnCompositor(const Timing& timing, const AnimationEffect& effect, double playerPlaybackRate)
13851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles){
139197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch    const KeyframeEffectModelBase& keyframeEffect = toKeyframeEffectModelBase(effect);
14051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
141a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch    PropertySet properties = keyframeEffect.properties();
142a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)
143a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch    if (properties.isEmpty())
144a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch        return false;
145a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)
146a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch    for (PropertySet::const_iterator it = properties.begin(); it != properties.end(); ++it) {
147a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch        const PropertySpecificKeyframeVector& frames = keyframeEffect.getPropertySpecificKeyframes(*it);
148a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch        ASSERT(frames.size() >= 2);
149a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch        for (size_t i = 0; i < frames.size(); ++i) {
150a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch            const Keyframe::PropertySpecificKeyframe *frame = frames[i].get();
151d6cdb82654e8f3343a693ca752d5c4cee0324e17Torne (Richard Coles)            // FIXME: Determine candidacy based on the CSSValue instead of a snapshot AnimatableValue.
152d6cdb82654e8f3343a693ca752d5c4cee0324e17Torne (Richard Coles)            if (frame->composite() != AnimationEffect::CompositeReplace || !frame->getAnimatableValue())
153a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch                return false;
154a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)
155a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            switch (*it) {
156a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            case CSSPropertyOpacity:
157a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch                break;
158aafa69cb17c9d6606c07663ade5f81388a2c5986Ben Murdoch            case CSSPropertyTransform:
159a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch                if (toAnimatableTransform(frame->getAnimatableValue().get())->transformOperations().dependsOnBoxSize())
160a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)                    return false;
161a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch                break;
162a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            case CSSPropertyWebkitFilter: {
163a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch                const FilterOperations& operations = toAnimatableFilterOperations(frame->getAnimatableValue().get())->operations();
164a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)                if (operations.hasFilterThatMovesPixels())
165a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)                    return false;
166a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch                break;
167a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            }
168a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            default:
169a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)                return false;
170a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            }
171a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch
172a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch            // FIXME: Remove this check when crbug.com/229405 is resolved
1737242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            if (i < frames.size() - 1 && frame->easing().type() == TimingFunction::StepsFunction)
174a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch                return false;
175a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)        }
176a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    }
177a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)
178a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    CompositorAnimationsImpl::CompositorTiming out;
1797242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci    if (!CompositorAnimationsImpl::convertTimingForCompositor(timing, 0, out, playerPlaybackRate))
180a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)        return false;
181a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)
1827242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci    if (timing.timingFunction->type() != TimingFunction::LinearFunction) {
1837242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        // Checks the of size of KeyframeVector instead of PropertySpecificKeyframeVector.
1847242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        const KeyframeVector& keyframes = keyframeEffect.getFrames();
1857242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        if (keyframes.size() == 2 && keyframes[0]->easing().type() == TimingFunction::LinearFunction && timing.timingFunction->type() != TimingFunction::StepsFunction)
1867242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            return true;
1877242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci
1887242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        // FIXME: Support non-linear timing functions in the compositor for
1897242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        // more than two keyframes and step timing functions in the compositor.
190a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)        return false;
1917242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci    }
192a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)
193a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    return true;
19451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)}
19551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
19651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)bool CompositorAnimations::canStartAnimationOnCompositor(const Element& element)
19751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles){
19851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    return element.renderer() && element.renderer()->compositingState() == PaintsIntoOwnBacking;
19951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)}
20051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
2017242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tuccibool CompositorAnimations::startAnimationOnCompositor(const Element& element, double startTime, double timeOffset, const Timing& timing, const AnimationEffect& effect, Vector<int>& startedAnimationIds, double playerPlaybackRate)
20251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles){
20351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    ASSERT(startedAnimationIds.isEmpty());
2047242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci    ASSERT(isCandidateForAnimationOnCompositor(timing, effect, playerPlaybackRate));
20551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    ASSERT(canStartAnimationOnCompositor(element));
20651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
207197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch    const KeyframeEffectModelBase& keyframeEffect = toKeyframeEffectModelBase(effect);
20851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
20951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    RenderLayer* layer = toRenderBoxModelObject(element.renderer())->layer();
21051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    ASSERT(layer);
21151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
2129e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)    Vector<OwnPtr<WebCompositorAnimation> > animations;
2137242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci    CompositorAnimationsImpl::getAnimationOnCompositor(timing, startTime, timeOffset, keyframeEffect, animations, playerPlaybackRate);
214a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    ASSERT(!animations.isEmpty());
21551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    for (size_t i = 0; i < animations.size(); ++i) {
21651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        int id = animations[i]->id();
21751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        if (!layer->compositedLayerMapping()->mainGraphicsLayer()->addAnimation(animations[i].release())) {
21851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            // FIXME: We should know ahead of time whether these animations can be started.
21951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            for (size_t j = 0; j < startedAnimationIds.size(); ++j)
22051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)                cancelAnimationOnCompositor(element, startedAnimationIds[j]);
22151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            startedAnimationIds.clear();
22251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            return false;
22351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        }
22451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        startedAnimationIds.append(id);
22551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    }
226a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    ASSERT(!startedAnimationIds.isEmpty());
22751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    return true;
22851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)}
22951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
23051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)void CompositorAnimations::cancelAnimationOnCompositor(const Element& element, int id)
23151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles){
232a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    if (!canStartAnimationOnCompositor(element)) {
23343e7502580f146aa5b3db8267ba6dbb5c733a489Torne (Richard Coles)        // When an element is being detached, we cancel any associated
23443e7502580f146aa5b3db8267ba6dbb5c733a489Torne (Richard Coles)        // AnimationPlayers for CSS animations. But by the time we get
23543e7502580f146aa5b3db8267ba6dbb5c733a489Torne (Richard Coles)        // here the mapping will have been removed.
23643e7502580f146aa5b3db8267ba6dbb5c733a489Torne (Richard Coles)        // FIXME: Defer remove/pause operations until after the
23743e7502580f146aa5b3db8267ba6dbb5c733a489Torne (Richard Coles)        // compositing update.
23851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        return;
239a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    }
24051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    toRenderBoxModelObject(element.renderer())->layer()->compositedLayerMapping()->mainGraphicsLayer()->removeAnimation(id);
24151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)}
24251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
24351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)void CompositorAnimations::pauseAnimationForTestingOnCompositor(const Element& element, int id, double pauseTime)
24451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles){
24509380295ba73501a205346becac22c6978e4671dTorne (Richard Coles)    // FIXME: canStartAnimationOnCompositor queries compositingState, which is not necessarily up to date.
24609380295ba73501a205346becac22c6978e4671dTorne (Richard Coles)    // https://code.google.com/p/chromium/issues/detail?id=339847
24709380295ba73501a205346becac22c6978e4671dTorne (Richard Coles)    DisableCompositingQueryAsserts disabler;
24809380295ba73501a205346becac22c6978e4671dTorne (Richard Coles)
249a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    if (!canStartAnimationOnCompositor(element)) {
250a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)        ASSERT_NOT_REACHED();
251a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)        return;
25251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    }
253a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    toRenderBoxModelObject(element.renderer())->layer()->compositedLayerMapping()->mainGraphicsLayer()->pauseAnimation(id, pauseTime);
25451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)}
25551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
256a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)// -----------------------------------------------------------------------
257a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)// CompositorAnimationsImpl
258a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)// -----------------------------------------------------------------------
259926b001d589ce2f10facb93dd4b87578ea35a855Torne (Richard Coles)
2607242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tuccibool CompositorAnimationsImpl::convertTimingForCompositor(const Timing& timing, double timeOffset, CompositorTiming& out, double playerPlaybackRate)
261bfe3590b1806e3ff18f46ee3af5d4b83078f305aTorne (Richard Coles){
26251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    timing.assertValid();
26351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
26451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    // All fill modes are supported (the calling code handles them).
26551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
2669e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)    if (timing.iterationCount <= 0)
26751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        return false;
26851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
26909380295ba73501a205346becac22c6978e4671dTorne (Richard Coles)    if (std::isnan(timing.iterationDuration) || !timing.iterationDuration)
27051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        return false;
27151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
27251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    // All directions are supported.
27351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
27451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    // Now attempt an actual conversion
27551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    out.scaledDuration = timing.iterationDuration;
27651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    ASSERT(out.scaledDuration > 0);
27751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
27851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    double scaledStartDelay = timing.startDelay;
279a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    if (scaledStartDelay > 0 && scaledStartDelay > out.scaledDuration * timing.iterationCount)
28051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        return false;
28151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
2827242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci    out.direction = timing.direction;
28351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
28451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    if (!std::isfinite(timing.iterationCount)) {
28551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        out.adjustedIterationCount = -1;
28651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    } else {
2879e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)        out.adjustedIterationCount = timing.iterationCount;
28851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        ASSERT(out.adjustedIterationCount > 0);
28951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    }
29051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
291a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    // Compositor's time offset is positive for seeking into the animation.
2927242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci    out.scaledTimeOffset = -scaledStartDelay + timeOffset;
2937242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci    out.playbackRate = timing.playbackRate * playerPlaybackRate;
2947242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci    out.fillMode = timing.fillMode == Timing::FillModeAuto ? Timing::FillModeNone : timing.fillMode;
2957242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci    out.iterationStart = timing.iterationStart;
2967242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci
29751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    return true;
298bfe3590b1806e3ff18f46ee3af5d4b83078f305aTorne (Richard Coles)}
2995c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
30051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)namespace {
30151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
30251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)template<typename PlatformAnimationCurveType, typename PlatformAnimationKeyframeType>
30351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)void addKeyframeWithTimingFunction(PlatformAnimationCurveType& curve, const PlatformAnimationKeyframeType& keyframe, const TimingFunction* timingFunction)
30451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles){
30551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    if (!timingFunction) {
30651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        curve.add(keyframe);
30751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        return;
30851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    }
30951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
31051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    switch (timingFunction->type()) {
31151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    case TimingFunction::LinearFunction:
3129e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)        curve.add(keyframe, WebCompositorAnimationCurve::TimingFunctionTypeLinear);
31351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        return;
31451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
31551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    case TimingFunction::CubicBezierFunction: {
31651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        const CubicBezierTimingFunction* cubic = toCubicBezierTimingFunction(timingFunction);
31751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
31851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        if (cubic->subType() == CubicBezierTimingFunction::Custom) {
31951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            curve.add(keyframe, cubic->x1(), cubic->y1(), cubic->x2(), cubic->y2());
32051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        } else {
32151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
3229e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            WebCompositorAnimationCurve::TimingFunctionType easeType;
32351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            switch (cubic->subType()) {
32451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            case CubicBezierTimingFunction::Ease:
3259e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)                easeType = WebCompositorAnimationCurve::TimingFunctionTypeEase;
32651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)                break;
32751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            case CubicBezierTimingFunction::EaseIn:
3289e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)                easeType = WebCompositorAnimationCurve::TimingFunctionTypeEaseIn;
32951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)                break;
33051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            case CubicBezierTimingFunction::EaseOut:
3319e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)                easeType = WebCompositorAnimationCurve::TimingFunctionTypeEaseOut;
33251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)                break;
33351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            case CubicBezierTimingFunction::EaseInOut:
3349e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)                easeType = WebCompositorAnimationCurve::TimingFunctionTypeEaseInOut;
33551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)                break;
33651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
33751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            // Custom Bezier are handled seperately.
33851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            case CubicBezierTimingFunction::Custom:
33951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            default:
34051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)                ASSERT_NOT_REACHED();
34151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)                return;
34251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            }
34351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
34451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            curve.add(keyframe, easeType);
34551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        }
34651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        return;
34751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    }
34851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
34951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    case TimingFunction::StepsFunction:
35051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    default:
35151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        ASSERT_NOT_REACHED();
35251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        return;
35351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    }
35451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)}
35551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
35651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)} // namespace anoymous
35751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
3587242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tuccivoid CompositorAnimationsImpl::addKeyframesToCurve(WebCompositorAnimationCurve& curve, const PropertySpecificKeyframeVector& keyframes, const Timing& timing)
35951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles){
36051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    for (size_t i = 0; i < keyframes.size(); i++) {
36151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        const TimingFunction* keyframeTimingFunction = 0;
362d5428f32f5d1719f774f62e19147104ca245a3abTorne (Richard Coles)        if (i < keyframes.size() - 1) { // Ignore timing function of last frame.
3637242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            if (keyframes.size() == 2 && keyframes[0]->easing().type() == TimingFunction::LinearFunction) {
3647242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci                keyframeTimingFunction = timing.timingFunction.get();
365d5428f32f5d1719f774f62e19147104ca245a3abTorne (Richard Coles)            } else {
3667242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci                keyframeTimingFunction = &keyframes[i]->easing();
36751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            }
36851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        }
36951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
370a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch        // FIXME: This relies on StringKeyframes being eagerly evaluated, which will
371a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch        // not happen eventually. Instead we should extract the CSSValue here
372a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch        // and convert using another set of toAnimatableXXXOperations functions.
373a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch        const AnimatableValue* value = keyframes[i]->getAnimatableValue().get();
374a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)
375a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)        switch (curve.type()) {
3769e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)        case WebCompositorAnimationCurve::AnimationCurveTypeFilter: {
3779e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            OwnPtr<WebFilterOperations> ops = adoptPtr(Platform::current()->compositorSupport()->createFilterOperations());
378197021e6b966cfb06891637935ef33fff06433d1Ben Murdoch            toWebFilterOperations(toAnimatableFilterOperations(value)->operations(), ops.get());
379a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)
3809e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            WebFilterKeyframe filterKeyframe(keyframes[i]->offset(), ops.release());
3819e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            WebFilterAnimationCurve* filterCurve = static_cast<WebFilterAnimationCurve*>(&curve);
382a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            addKeyframeWithTimingFunction(*filterCurve, filterKeyframe, keyframeTimingFunction);
383a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            break;
384a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)        }
3859e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)        case WebCompositorAnimationCurve::AnimationCurveTypeFloat: {
3869e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            WebFloatKeyframe floatKeyframe(keyframes[i]->offset(), toAnimatableDouble(value)->toDouble());
3879e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            WebFloatAnimationCurve* floatCurve = static_cast<WebFloatAnimationCurve*>(&curve);
388a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            addKeyframeWithTimingFunction(*floatCurve, floatKeyframe, keyframeTimingFunction);
389a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            break;
390a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)        }
3919e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)        case WebCompositorAnimationCurve::AnimationCurveTypeTransform: {
3929e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            OwnPtr<WebTransformOperations> ops = adoptPtr(Platform::current()->compositorSupport()->createTransformOperations());
39343e7502580f146aa5b3db8267ba6dbb5c733a489Torne (Richard Coles)            toWebTransformOperations(toAnimatableTransform(value)->transformOperations(), ops.get());
394a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)
3959e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            WebTransformKeyframe transformKeyframe(keyframes[i]->offset(), ops.release());
3969e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            WebTransformAnimationCurve* transformCurve = static_cast<WebTransformAnimationCurve*>(&curve);
397a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            addKeyframeWithTimingFunction(*transformCurve, transformKeyframe, keyframeTimingFunction);
398a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            break;
399a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)        }
400a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)        default:
401a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)            ASSERT_NOT_REACHED();
402a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)        }
40351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    }
40451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)}
40551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
4067242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tuccivoid CompositorAnimationsImpl::getAnimationOnCompositor(const Timing& timing, double startTime, double timeOffset, const KeyframeEffectModelBase& effect, Vector<OwnPtr<WebCompositorAnimation> >& animations, double playerPlaybackRate)
40751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles){
408a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    ASSERT(animations.isEmpty());
40951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    CompositorTiming compositorTiming;
4107242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci    bool timingValid = convertTimingForCompositor(timing, timeOffset, compositorTiming, playerPlaybackRate);
41151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    ASSERT_UNUSED(timingValid, timingValid);
41251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
41351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    PropertySet properties = effect.properties();
414a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    ASSERT(!properties.isEmpty());
41551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    for (PropertySet::iterator it = properties.begin(); it != properties.end(); ++it) {
41651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
417a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch        PropertySpecificKeyframeVector values;
4187242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        getKeyframeValuesForProperty(&effect, *it, compositorTiming.scaledDuration, values);
41951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
4209e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)        WebCompositorAnimation::TargetProperty targetProperty;
4219e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)        OwnPtr<WebCompositorAnimationCurve> curve;
42251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        switch (*it) {
42351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        case CSSPropertyOpacity: {
4249e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            targetProperty = WebCompositorAnimation::TargetPropertyOpacity;
425a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)
4269e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            WebFloatAnimationCurve* floatCurve = Platform::current()->compositorSupport()->createFloatAnimationCurve();
4277242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            addKeyframesToCurve(*floatCurve, values, timing);
42851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            curve = adoptPtr(floatCurve);
42951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            break;
43051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        }
43151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        case CSSPropertyWebkitFilter: {
4329e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            targetProperty = WebCompositorAnimation::TargetPropertyFilter;
4339e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            WebFilterAnimationCurve* filterCurve = Platform::current()->compositorSupport()->createFilterAnimationCurve();
4347242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            addKeyframesToCurve(*filterCurve, values, timing);
43551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            curve = adoptPtr(filterCurve);
43651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            break;
43751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        }
438aafa69cb17c9d6606c07663ade5f81388a2c5986Ben Murdoch        case CSSPropertyTransform: {
4399e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            targetProperty = WebCompositorAnimation::TargetPropertyTransform;
4409e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)            WebTransformAnimationCurve* transformCurve = Platform::current()->compositorSupport()->createTransformAnimationCurve();
4417242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            addKeyframesToCurve(*transformCurve, values, timing);
44251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            curve = adoptPtr(transformCurve);
44351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            break;
44451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        }
44551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        default:
44651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            ASSERT_NOT_REACHED();
44751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)            continue;
44851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        }
44951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        ASSERT(curve.get());
45051b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
4519e12abdf8c3a23d52091ea54ebb6a04d327f9300Torne (Richard Coles)        OwnPtr<WebCompositorAnimation> animation = adoptPtr(Platform::current()->compositorSupport()->createAnimation(*curve, targetProperty));
45251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
453a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch        if (!std::isnan(startTime))
454a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch            animation->setStartTime(startTime);
455a9984bf9ddc3cf73fdae3f29134a2bab379e7029Ben Murdoch
45651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        animation->setIterations(compositorTiming.adjustedIterationCount);
4577242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        animation->setIterationStart(compositorTiming.iterationStart);
45851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        animation->setTimeOffset(compositorTiming.scaledTimeOffset);
45951b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
4607242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        switch (compositorTiming.direction) {
4617242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        case Timing::PlaybackDirectionNormal:
4627242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            animation->setDirection(blink::WebCompositorAnimation::DirectionNormal);
4637242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            break;
4647242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        case Timing::PlaybackDirectionReverse:
4657242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            animation->setDirection(blink::WebCompositorAnimation::DirectionReverse);
4667242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            break;
4677242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        case Timing::PlaybackDirectionAlternate:
4687242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            animation->setDirection(blink::WebCompositorAnimation::DirectionAlternate);
4697242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            break;
4707242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        case Timing::PlaybackDirectionAlternateReverse:
4717242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            animation->setDirection(blink::WebCompositorAnimation::DirectionAlternateReverse);
4727242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            break;
4737242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        default:
4747242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            ASSERT_NOT_REACHED();
4757242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        }
4767242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        animation->setPlaybackRate(compositorTiming.playbackRate);
4777242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci
4787242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        switch (compositorTiming.fillMode) {
4797242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        case Timing::FillModeNone:
4807242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            animation->setFillMode(blink::WebCompositorAnimation::FillModeNone);
4817242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            break;
4827242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        case Timing::FillModeForwards:
4837242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            animation->setFillMode(blink::WebCompositorAnimation::FillModeForwards);
4847242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            break;
4857242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        case Timing::FillModeBackwards:
4867242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            animation->setFillMode(blink::WebCompositorAnimation::FillModeBackwards);
4877242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            break;
4887242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        case Timing::FillModeBoth:
4897242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            animation->setFillMode(blink::WebCompositorAnimation::FillModeBoth);
4907242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            break;
4917242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        default:
4927242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci            ASSERT_NOT_REACHED();
4937242dc3dbeb210b5e876a3c42d1ec1a667fc621aPrimiano Tucci        }
49451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)        animations.append(animation.release());
49551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    }
496a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    ASSERT(!animations.isEmpty());
49751b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)}
49851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)
499c1847b1379d12d0e05df27436bf19a9b1bf12deaTorne (Richard Coles)} // namespace blink
500