18e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project/* 20bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch * Copyright (C) 2007, 2008, 2009 Apple Inc. All rights reserved. 38e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 48e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * Redistribution and use in source and binary forms, with or without 58e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * modification, are permitted provided that the following conditions 68e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * are met: 78e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 88e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 1. Redistributions of source code must retain the above copyright 98e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * notice, this list of conditions and the following disclaimer. 108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 2. Redistributions in binary form must reproduce the above copyright 118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * notice, this list of conditions and the following disclaimer in the 128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * documentation and/or other materials provided with the distribution. 138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of 148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * its contributors may be used to endorse or promote products derived 158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * from this software without specific prior written permission. 168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY 188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY 218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project */ 288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "config.h" 308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "AnimationBase.h" 318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 328f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#include "AnimationControllerPrivate.h" 33635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project#include "CSSMutableStyleDeclaration.h" 34635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project#include "CSSPropertyLonghand.h" 358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "CSSPropertyNames.h" 368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "CompositeAnimation.h" 378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "Document.h" 388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "EventNames.h" 398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "FloatConversion.h" 408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "Frame.h" 418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "IdentityTransformOperation.h" 428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "ImplicitAnimation.h" 438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "KeyframeAnimation.h" 448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "MatrixTransformOperation.h" 458f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#include "Matrix3DTransformOperation.h" 468f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#include "RenderBox.h" 470bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch#include "RenderLayer.h" 480bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch#include "RenderLayerBacking.h" 498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "RenderStyle.h" 508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "UnitBezier.h" 518f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#include <algorithm> 52cad810f21b803229eb11403f9209855525a25d57Steve Block#include <wtf/CurrentTime.h> 538f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 548f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qianusing namespace std; 558f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectnamespace WebCore { 578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project// The epsilon value we pass to UnitBezier::solve given that the animation is going to run over |dur| seconds. The longer the 598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project// animation, the more precision we need in the timing function result to avoid ugly discontinuities. 608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic inline double solveEpsilon(double duration) 618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return 1.0 / (200.0 * duration); 638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic inline double solveCubicBezierFunction(double p1x, double p1y, double p2x, double p2y, double t, double duration) 668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Convert from input time to parametric value in curve, then from 688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // that to output time. 698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project UnitBezier bezier(p1x, p1y, p2x, p2y); 708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return bezier.solve(t, solveEpsilon(duration)); 718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 735abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrickstatic inline double solveStepsFunction(int numSteps, bool stepAtStart, double t) 745abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick{ 755abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick if (stepAtStart) 765abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick return min(1.0, (floor(numSteps * t) + 1) / numSteps); 775abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick return floor(numSteps * t) / numSteps; 785abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick} 795abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick 80635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectstatic inline int blendFunc(const AnimationBase*, int from, int to, double progress) 818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return int(from + (to - from) * progress); 838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 85635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectstatic inline double blendFunc(const AnimationBase*, double from, double to, double progress) 868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return from + (to - from) * progress; 888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 90635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectstatic inline float blendFunc(const AnimationBase*, float from, float to, double progress) 918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return narrowPrecisionToFloat(from + (to - from) * progress); 938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic inline Color blendFunc(const AnimationBase* anim, const Color& from, const Color& to, double progress) 96635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project{ 97635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // We need to preserve the state of the valid flag at the end of the animation 98635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (progress == 1 && !to.isValid()) 99635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return Color(); 100635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 101d0825bca7fe65beaee391d30da42e937db621564Steve Block // Contrary to the name, RGBA32 actually stores ARGB, so we can initialize Color directly from premultipliedARGBFromColor(). 102d0825bca7fe65beaee391d30da42e937db621564Steve Block // Also, premultipliedARGBFromColor() bails on zero alpha, so special-case that. 103d0825bca7fe65beaee391d30da42e937db621564Steve Block Color premultFrom = from.alpha() ? premultipliedARGBFromColor(from) : 0; 104d0825bca7fe65beaee391d30da42e937db621564Steve Block Color premultTo = to.alpha() ? premultipliedARGBFromColor(to) : 0; 105d0825bca7fe65beaee391d30da42e937db621564Steve Block 106d0825bca7fe65beaee391d30da42e937db621564Steve Block Color premultBlended(blendFunc(anim, premultFrom.red(), premultTo.red(), progress), 107d0825bca7fe65beaee391d30da42e937db621564Steve Block blendFunc(anim, premultFrom.green(), premultTo.green(), progress), 108d0825bca7fe65beaee391d30da42e937db621564Steve Block blendFunc(anim, premultFrom.blue(), premultTo.blue(), progress), 109d0825bca7fe65beaee391d30da42e937db621564Steve Block blendFunc(anim, premultFrom.alpha(), premultTo.alpha(), progress)); 110d0825bca7fe65beaee391d30da42e937db621564Steve Block 111d0825bca7fe65beaee391d30da42e937db621564Steve Block return Color(colorFromPremultipliedARGB(premultBlended.rgb())); 1128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 114635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectstatic inline Length blendFunc(const AnimationBase*, const Length& from, const Length& to, double progress) 1158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1162bde8e466a4451c7319e3a072d118917957d6554Steve Block return to.blend(from, narrowPrecisionToFloat(progress)); 1178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1195f1ab04193ad0130ca8204aadaceae083aca9881Feng Qianstatic inline LengthSize blendFunc(const AnimationBase* anim, const LengthSize& from, const LengthSize& to, double progress) 1205f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian{ 1215f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian return LengthSize(blendFunc(anim, from.width(), to.width(), progress), 1225f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian blendFunc(anim, from.height(), to.height(), progress)); 1235f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian} 1245f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian 1258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic inline IntSize blendFunc(const AnimationBase* anim, const IntSize& from, const IntSize& to, double progress) 1268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return IntSize(blendFunc(anim, from.width(), to.width(), progress), 1288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project blendFunc(anim, from.height(), to.height(), progress)); 1298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1310bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdochstatic inline ShadowStyle blendFunc(const AnimationBase* anim, ShadowStyle from, ShadowStyle to, double progress) 1320bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch{ 1330bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch if (from == to) 1340bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch return to; 1350bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 1360bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch double fromVal = from == Normal ? 1 : 0; 1370bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch double toVal = to == Normal ? 1 : 0; 1380bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch double result = blendFunc(anim, fromVal, toVal, progress); 1390bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch return result > 0 ? Normal : Inset; 1400bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch} 1410bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 1428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic inline ShadowData* blendFunc(const AnimationBase* anim, const ShadowData* from, const ShadowData* to, double progress) 1438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(from && to); 1452daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch if (from->style() != to->style()) 1462daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch return new ShadowData(*to); 1472daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch 148cad810f21b803229eb11403f9209855525a25d57Steve Block return new ShadowData(blendFunc(anim, from->x(), to->x(), progress), 149cad810f21b803229eb11403f9209855525a25d57Steve Block blendFunc(anim, from->y(), to->y(), progress), 150cad810f21b803229eb11403f9209855525a25d57Steve Block blendFunc(anim, from->blur(), to->blur(), progress), 151cad810f21b803229eb11403f9209855525a25d57Steve Block blendFunc(anim, from->spread(), to->spread(), progress), 152cad810f21b803229eb11403f9209855525a25d57Steve Block blendFunc(anim, from->style(), to->style(), progress), 153cad810f21b803229eb11403f9209855525a25d57Steve Block from->isWebkitBoxShadow(), 154cad810f21b803229eb11403f9209855525a25d57Steve Block blendFunc(anim, from->color(), to->color(), progress)); 1558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic inline TransformOperations blendFunc(const AnimationBase* anim, const TransformOperations& from, const TransformOperations& to, double progress) 1588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project TransformOperations result; 1608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // If we have a transform function list, use that to do a per-function animation. Otherwise do a Matrix animation 1628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (anim->isTransformFunctionListValid()) { 1638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project unsigned fromSize = from.operations().size(); 1648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project unsigned toSize = to.operations().size(); 1658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project unsigned size = max(fromSize, toSize); 1668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project for (unsigned i = 0; i < size; i++) { 1678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project RefPtr<TransformOperation> fromOp = (i < fromSize) ? from.operations()[i].get() : 0; 1688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project RefPtr<TransformOperation> toOp = (i < toSize) ? to.operations()[i].get() : 0; 1698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project RefPtr<TransformOperation> blendedOp = toOp ? toOp->blend(fromOp.get(), progress) : (fromOp ? fromOp->blend(0, progress, true) : 0); 1708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (blendedOp) 1718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project result.operations().append(blendedOp); 1728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project else { 1738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project RefPtr<TransformOperation> identityOp = IdentityTransformOperation::create(); 1748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (progress > 0.5) 1758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project result.operations().append(toOp ? toOp : identityOp); 1768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project else 1778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project result.operations().append(fromOp ? fromOp : identityOp); 1788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 1798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 1808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else { 1818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Convert the TransformOperations into matrices 182635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project IntSize size = anim->renderer()->isBox() ? toRenderBox(anim->renderer())->borderBoxRect().size() : IntSize(); 183635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project TransformationMatrix fromT; 184635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project TransformationMatrix toT; 1858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project from.apply(size, fromT); 1868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project to.apply(size, toT); 1878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project toT.blend(fromT, progress); 1898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Append the result 1918f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian result.operations().append(Matrix3DTransformOperation::create(toT)); 1928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 1938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return result; 1948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic inline EVisibility blendFunc(const AnimationBase* anim, EVisibility from, EVisibility to, double progress) 1978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Any non-zero result means we consider the object to be visible. Only at 0 do we consider the object to be 1998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // invisible. The invisible value we use (HIDDEN vs. COLLAPSE) depends on the specified from/to values. 2008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project double fromVal = from == VISIBLE ? 1. : 0.; 2018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project double toVal = to == VISIBLE ? 1. : 0.; 2028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (fromVal == toVal) 2038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return to; 2048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project double result = blendFunc(anim, fromVal, toVal, progress); 2058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return result > 0. ? VISIBLE : (to != VISIBLE ? to : from); 2068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 20806ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsenstatic inline LengthBox blendFunc(const AnimationBase* anim, const LengthBox& from, const LengthBox& to, double progress) 20906ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen{ 21006ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen // Length types have to match to animate 21106ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen if (from.top().type() != to.top().type() 21206ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen || from.right().type() != to.right().type() 21306ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen || from.bottom().type() != to.bottom().type() 21406ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen || from.left().type() != to.left().type()) 21506ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen return to; 21606ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen 21706ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen LengthBox result(blendFunc(anim, from.top(), to.top(), progress), 21806ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen blendFunc(anim, from.right(), to.right(), progress), 21906ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen blendFunc(anim, from.bottom(), to.bottom(), progress), 22006ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen blendFunc(anim, from.left(), to.left(), progress)); 22106ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen return result; 22206ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen} 22306ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen 224635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectclass PropertyWrapperBase; 225635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 226635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectstatic void addShorthandProperties(); 227635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectstatic PropertyWrapperBase* wrapperForProperty(int propertyID); 228635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 229ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdochclass PropertyWrapperBase { 230ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch WTF_MAKE_NONCOPYABLE(PropertyWrapperBase); WTF_MAKE_FAST_ALLOCATED; 2318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectpublic: 2328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project PropertyWrapperBase(int prop) 2338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project : m_prop(prop) 2348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project { 2358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 2368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project virtual ~PropertyWrapperBase() { } 238635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 239635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project virtual bool isShorthandWrapper() const { return false; } 2408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project virtual bool equals(const RenderStyle* a, const RenderStyle* b) const = 0; 2418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project virtual void blend(const AnimationBase* anim, RenderStyle* dst, const RenderStyle* a, const RenderStyle* b, double progress) const = 0; 2428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int property() const { return m_prop; } 2448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2458f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#if USE(ACCELERATED_COMPOSITING) 2468f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian virtual bool animationIsAccelerated() const { return false; } 2478f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#endif 2488f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 2498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectprivate: 2508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int m_prop; 2518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project}; 2528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projecttemplate <typename T> 2548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectclass PropertyWrapperGetter : public PropertyWrapperBase { 2558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectpublic: 2568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project PropertyWrapperGetter(int prop, T (RenderStyle::*getter)() const) 2578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project : PropertyWrapperBase(prop) 2588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_getter(getter) 2598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project { 2608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 2618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project virtual bool equals(const RenderStyle* a, const RenderStyle* b) const 2638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project { 2648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // If the style pointers are the same, don't bother doing the test. 2658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // If either is null, return false. If both are null, return true. 2668f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian if ((!a && !b) || a == b) 2678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return true; 2688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!a || !b) 2698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 2708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return (a->*m_getter)() == (b->*m_getter)(); 2718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 2728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectprotected: 2748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project T (RenderStyle::*m_getter)() const; 2758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project}; 2768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projecttemplate <typename T> 2788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectclass PropertyWrapper : public PropertyWrapperGetter<T> { 2798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectpublic: 2808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project PropertyWrapper(int prop, T (RenderStyle::*getter)() const, void (RenderStyle::*setter)(T)) 2818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project : PropertyWrapperGetter<T>(prop, getter) 2828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_setter(setter) 2838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project { 2848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 2858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project virtual void blend(const AnimationBase* anim, RenderStyle* dst, const RenderStyle* a, const RenderStyle* b, double progress) const 2878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project { 2888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project (dst->*m_setter)(blendFunc(anim, (a->*PropertyWrapperGetter<T>::m_getter)(), (b->*PropertyWrapperGetter<T>::m_getter)(), progress)); 2898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 2908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectprotected: 2928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project void (RenderStyle::*m_setter)(T); 2938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project}; 2948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2958f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#if USE(ACCELERATED_COMPOSITING) 2968f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qianclass PropertyWrapperAcceleratedOpacity : public PropertyWrapper<float> { 2978f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qianpublic: 2988f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian PropertyWrapperAcceleratedOpacity() 2998f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian : PropertyWrapper<float>(CSSPropertyOpacity, &RenderStyle::opacity, &RenderStyle::setOpacity) 3008f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian { 3018f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian } 3028f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 3038f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian virtual bool animationIsAccelerated() const { return true; } 3048f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 3058f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian virtual void blend(const AnimationBase* anim, RenderStyle* dst, const RenderStyle* a, const RenderStyle* b, double progress) const 3068f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian { 3078f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian float fromOpacity = a->opacity(); 3088f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 3098f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian // This makes sure we put the object being animated into a RenderLayer during the animation 3108f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian dst->setOpacity(blendFunc(anim, (fromOpacity == 1) ? 0.999999f : fromOpacity, b->opacity(), progress)); 3118f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian } 3128f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian}; 3138f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 3148f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qianclass PropertyWrapperAcceleratedTransform : public PropertyWrapper<const TransformOperations&> { 3158f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qianpublic: 3168f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian PropertyWrapperAcceleratedTransform() 3178f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian : PropertyWrapper<const TransformOperations&>(CSSPropertyWebkitTransform, &RenderStyle::transform, &RenderStyle::setTransform) 3188f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian { 3198f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian } 3208f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 3218f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian virtual bool animationIsAccelerated() const { return true; } 3228f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 3238f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian virtual void blend(const AnimationBase* anim, RenderStyle* dst, const RenderStyle* a, const RenderStyle* b, double progress) const 3248f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian { 3258f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian dst->setTransform(blendFunc(anim, a->transform(), b->transform(), progress)); 3268f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian } 3278f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian}; 3288f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#endif // USE(ACCELERATED_COMPOSITING) 3298f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 330dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Blockclass PropertyWrapperShadow : public PropertyWrapperBase { 3318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectpublic: 332dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block PropertyWrapperShadow(int prop, const ShadowData* (RenderStyle::*getter)() const, void (RenderStyle::*setter)(ShadowData*, bool)) 333dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block : PropertyWrapperBase(prop) 334dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block , m_getter(getter) 3358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_setter(setter) 3368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project { 3378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 3388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project virtual bool equals(const RenderStyle* a, const RenderStyle* b) const 3408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project { 341dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block const ShadowData* shadowA = (a->*m_getter)(); 342dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block const ShadowData* shadowB = (b->*m_getter)(); 343231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 344231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block while (true) { 345231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block if (!shadowA && !shadowB) // end of both lists 346231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block return true; 347231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 348231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block if (!shadowA || !shadowB) // end of just one of the lists 349231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block return false; 350231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 351231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block if (*shadowA != *shadowB) 352231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block return false; 353231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 354dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block shadowA = shadowA->next(); 355dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block shadowB = shadowB->next(); 356231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 3578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return true; 3598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 3608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project virtual void blend(const AnimationBase* anim, RenderStyle* dst, const RenderStyle* a, const RenderStyle* b, double progress) const 3628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project { 363dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block const ShadowData* shadowA = (a->*m_getter)(); 364dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block const ShadowData* shadowB = (b->*m_getter)(); 365cad810f21b803229eb11403f9209855525a25d57Steve Block ShadowData defaultShadowData(0, 0, 0, 0, Normal, property() == CSSPropertyWebkitBoxShadow, Color::transparent); 3662daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch ShadowData defaultInsetShadowData(0, 0, 0, 0, Inset, property() == CSSPropertyWebkitBoxShadow, Color::transparent); 3678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 368231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block ShadowData* newShadowData = 0; 369f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch ShadowData* lastShadow = 0; 370231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 371231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block while (shadowA || shadowB) { 3722daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch const ShadowData* srcShadow = shadowA ? shadowA : (shadowB->style() == Inset ? &defaultInsetShadowData : &defaultShadowData); 3732daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch const ShadowData* dstShadow = shadowB ? shadowB : (shadowA->style() == Inset ? &defaultInsetShadowData : &defaultShadowData); 3742daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch 375f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch ShadowData* blendedShadow = blendFunc(anim, srcShadow, dstShadow, progress); 376f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch if (!lastShadow) 377f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch newShadowData = blendedShadow; 378231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block else 379f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch lastShadow->setNext(blendedShadow); 380f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 381f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch lastShadow = blendedShadow; 382231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 383dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block shadowA = shadowA ? shadowA->next() : 0; 384dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block shadowB = shadowB ? shadowB->next() : 0; 385231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 386231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 387231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block (dst->*m_setter)(newShadowData, false); 3888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 3898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectprivate: 391dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block const ShadowData* (RenderStyle::*m_getter)() const; 3928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project void (RenderStyle::*m_setter)(ShadowData*, bool); 3938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project}; 3948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectclass PropertyWrapperMaybeInvalidColor : public PropertyWrapperBase { 3968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectpublic: 3978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project PropertyWrapperMaybeInvalidColor(int prop, const Color& (RenderStyle::*getter)() const, void (RenderStyle::*setter)(const Color&)) 3988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project : PropertyWrapperBase(prop) 3998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_getter(getter) 4008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_setter(setter) 4018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project { 4028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project virtual bool equals(const RenderStyle* a, const RenderStyle* b) const 4058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project { 4068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project Color fromColor = (a->*m_getter)(); 4078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project Color toColor = (b->*m_getter)(); 408231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 409231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block if (!fromColor.isValid() && !toColor.isValid()) 410231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block return true; 411231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 4128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!fromColor.isValid()) 4138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project fromColor = a->color(); 4148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!toColor.isValid()) 4158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project toColor = b->color(); 4168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return fromColor == toColor; 4188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project virtual void blend(const AnimationBase* anim, RenderStyle* dst, const RenderStyle* a, const RenderStyle* b, double progress) const 4218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project { 4228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project Color fromColor = (a->*m_getter)(); 4238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project Color toColor = (b->*m_getter)(); 424231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 425231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block if (!fromColor.isValid() && !toColor.isValid()) 426231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block return; 427231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 4288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!fromColor.isValid()) 4298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project fromColor = a->color(); 4308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!toColor.isValid()) 4318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project toColor = b->color(); 4328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project (dst->*m_setter)(blendFunc(anim, fromColor, toColor, progress)); 4338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectprivate: 4368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project const Color& (RenderStyle::*m_getter)() const; 4378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project void (RenderStyle::*m_setter)(const Color&); 4388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project}; 4398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 440231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block// Wrapper base class for an animatable property in a FillLayer 441231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blockclass FillLayerPropertyWrapperBase { 442231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blockpublic: 443231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block FillLayerPropertyWrapperBase() 444231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block { 445231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 446231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 447231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block virtual ~FillLayerPropertyWrapperBase() { } 448231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 449231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block virtual bool equals(const FillLayer* a, const FillLayer* b) const = 0; 450231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block virtual void blend(const AnimationBase* anim, FillLayer* dst, const FillLayer* a, const FillLayer* b, double progress) const = 0; 451231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block}; 452231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 453231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blocktemplate <typename T> 454ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdochclass FillLayerPropertyWrapperGetter : public FillLayerPropertyWrapperBase { 455ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch WTF_MAKE_NONCOPYABLE(FillLayerPropertyWrapperGetter); 456231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blockpublic: 457231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block FillLayerPropertyWrapperGetter(T (FillLayer::*getter)() const) 458231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block : m_getter(getter) 459231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block { 460231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 461231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 462231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block virtual bool equals(const FillLayer* a, const FillLayer* b) const 463231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block { 464231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block // If the style pointers are the same, don't bother doing the test. 465231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block // If either is null, return false. If both are null, return true. 466231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block if ((!a && !b) || a == b) 467231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block return true; 468231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block if (!a || !b) 469231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block return false; 470231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block return (a->*m_getter)() == (b->*m_getter)(); 471231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 472231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 473231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blockprotected: 474231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block T (FillLayer::*m_getter)() const; 475231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block}; 476231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 477231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blocktemplate <typename T> 478231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blockclass FillLayerPropertyWrapper : public FillLayerPropertyWrapperGetter<T> { 479231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blockpublic: 480231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block FillLayerPropertyWrapper(T (FillLayer::*getter)() const, void (FillLayer::*setter)(T)) 481231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block : FillLayerPropertyWrapperGetter<T>(getter) 482231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block , m_setter(setter) 483231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block { 484231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 485231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 486231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block virtual void blend(const AnimationBase* anim, FillLayer* dst, const FillLayer* a, const FillLayer* b, double progress) const 487231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block { 488231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block (dst->*m_setter)(blendFunc(anim, (a->*FillLayerPropertyWrapperGetter<T>::m_getter)(), (b->*FillLayerPropertyWrapperGetter<T>::m_getter)(), progress)); 489231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 490231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 491231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blockprotected: 492231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block void (FillLayer::*m_setter)(T); 493231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block}; 494231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 495231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 496231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blockclass FillLayersPropertyWrapper : public PropertyWrapperBase { 497231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blockpublic: 498231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block typedef const FillLayer* (RenderStyle::*LayersGetter)() const; 499231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block typedef FillLayer* (RenderStyle::*LayersAccessor)(); 500231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 501231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block FillLayersPropertyWrapper(int prop, LayersGetter getter, LayersAccessor accessor) 502231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block : PropertyWrapperBase(prop) 503231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block , m_layersGetter(getter) 504231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block , m_layersAccessor(accessor) 505231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block { 506231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block switch (prop) { 507231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case CSSPropertyBackgroundPositionX: 508231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case CSSPropertyWebkitMaskPositionX: 509231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block m_fillLayerPropertyWrapper = new FillLayerPropertyWrapper<Length>(&FillLayer::xPosition, &FillLayer::setXPosition); 510231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block break; 511231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case CSSPropertyBackgroundPositionY: 512231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case CSSPropertyWebkitMaskPositionY: 513231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block m_fillLayerPropertyWrapper = new FillLayerPropertyWrapper<Length>(&FillLayer::yPosition, &FillLayer::setYPosition); 514231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block break; 515231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case CSSPropertyBackgroundSize: 516cac0f67c402d107cdb10971b95719e2ff9c7c76bSteve Block case CSSPropertyWebkitBackgroundSize: 517231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block case CSSPropertyWebkitMaskSize: 518231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block m_fillLayerPropertyWrapper = new FillLayerPropertyWrapper<LengthSize>(&FillLayer::sizeLength, &FillLayer::setSizeLength); 519231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block break; 520231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 521231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 522231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 523231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block virtual bool equals(const RenderStyle* a, const RenderStyle* b) const 524231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block { 525231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block const FillLayer* fromLayer = (a->*m_layersGetter)(); 526231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block const FillLayer* toLayer = (b->*m_layersGetter)(); 527231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 528231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block while (fromLayer && toLayer) { 529231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block if (!m_fillLayerPropertyWrapper->equals(fromLayer, toLayer)) 530231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block return false; 531231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 532231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block fromLayer = fromLayer->next(); 533231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block toLayer = toLayer->next(); 534231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 535231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 536231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block return true; 537231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 538231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 539231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block virtual void blend(const AnimationBase* anim, RenderStyle* dst, const RenderStyle* a, const RenderStyle* b, double progress) const 540231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block { 541231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block const FillLayer* aLayer = (a->*m_layersGetter)(); 542231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block const FillLayer* bLayer = (b->*m_layersGetter)(); 543231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block FillLayer* dstLayer = (dst->*m_layersAccessor)(); 544231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 545231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block while (aLayer && bLayer && dstLayer) { 546231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block m_fillLayerPropertyWrapper->blend(anim, dstLayer, aLayer, bLayer, progress); 547231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block aLayer = aLayer->next(); 548231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block bLayer = bLayer->next(); 549231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block dstLayer = dstLayer->next(); 550231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 551231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 552231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 553231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blockprivate: 554231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block FillLayerPropertyWrapperBase* m_fillLayerPropertyWrapper; 555231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 556231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block LayersGetter m_layersGetter; 557231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block LayersAccessor m_layersAccessor; 558231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block}; 559231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 560635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectclass ShorthandPropertyWrapper : public PropertyWrapperBase { 561635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectpublic: 562635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project ShorthandPropertyWrapper(int property, const CSSPropertyLonghand& longhand) 563635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project : PropertyWrapperBase(property) 564635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project { 565635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project for (unsigned i = 0; i < longhand.length(); ++i) { 566635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project PropertyWrapperBase* wrapper = wrapperForProperty(longhand.properties()[i]); 567635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (wrapper) 568635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_propertyWrappers.append(wrapper); 569635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 570635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 571635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 572635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project virtual bool isShorthandWrapper() const { return true; } 573635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 574635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project virtual bool equals(const RenderStyle* a, const RenderStyle* b) const 575635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project { 576635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project Vector<PropertyWrapperBase*>::const_iterator end = m_propertyWrappers.end(); 577635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project for (Vector<PropertyWrapperBase*>::const_iterator it = m_propertyWrappers.begin(); it != end; ++it) { 578635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (!(*it)->equals(a, b)) 579635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return false; 580635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 581635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return true; 582635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 583635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 584635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project virtual void blend(const AnimationBase* anim, RenderStyle* dst, const RenderStyle* a, const RenderStyle* b, double progress) const 585635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project { 586635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project Vector<PropertyWrapperBase*>::const_iterator end = m_propertyWrappers.end(); 587635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project for (Vector<PropertyWrapperBase*>::const_iterator it = m_propertyWrappers.begin(); it != end; ++it) 588635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project (*it)->blend(anim, dst, a, b, progress); 589635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 590635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 591f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch const Vector<PropertyWrapperBase*> propertyWrappers() const { return m_propertyWrappers; } 592f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 593635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectprivate: 594635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project Vector<PropertyWrapperBase*> m_propertyWrappers; 595635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project}; 596635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 597635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 5988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic Vector<PropertyWrapperBase*>* gPropertyWrappers = 0; 5998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic int gPropertyWrapperMap[numCSSProperties]; 6008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 601635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectstatic const int cInvalidPropertyWrapperIndex = -1; 602635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 603635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 604e78cbe89e6f337f2f1fe40315be88f742b547151Steve Blockvoid AnimationBase::ensurePropertyMap() 6058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 6068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // FIXME: This data is never destroyed. Maybe we should ref count it and toss it when the last AnimationController is destroyed? 6078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (gPropertyWrappers == 0) { 6088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers = new Vector<PropertyWrapperBase*>(); 6098e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 6108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // build the list of property wrappers to do the comparisons and blends 6118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyLeft, &RenderStyle::left, &RenderStyle::setLeft)); 6128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyRight, &RenderStyle::right, &RenderStyle::setRight)); 6138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyTop, &RenderStyle::top, &RenderStyle::setTop)); 6148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyBottom, &RenderStyle::bottom, &RenderStyle::setBottom)); 6150bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 6168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyWidth, &RenderStyle::width, &RenderStyle::setWidth)); 6170bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyMinWidth, &RenderStyle::minWidth, &RenderStyle::setMinWidth)); 6180bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyMaxWidth, &RenderStyle::maxWidth, &RenderStyle::setMaxWidth)); 6190bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 6208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyHeight, &RenderStyle::height, &RenderStyle::setHeight)); 6210bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyMinHeight, &RenderStyle::minHeight, &RenderStyle::setMinHeight)); 6220bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyMaxHeight, &RenderStyle::maxHeight, &RenderStyle::setMaxHeight)); 6230bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 6248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<unsigned short>(CSSPropertyBorderLeftWidth, &RenderStyle::borderLeftWidth, &RenderStyle::setBorderLeftWidth)); 6258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<unsigned short>(CSSPropertyBorderRightWidth, &RenderStyle::borderRightWidth, &RenderStyle::setBorderRightWidth)); 6268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<unsigned short>(CSSPropertyBorderTopWidth, &RenderStyle::borderTopWidth, &RenderStyle::setBorderTopWidth)); 6278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<unsigned short>(CSSPropertyBorderBottomWidth, &RenderStyle::borderBottomWidth, &RenderStyle::setBorderBottomWidth)); 6288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyMarginLeft, &RenderStyle::marginLeft, &RenderStyle::setMarginLeft)); 6298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyMarginRight, &RenderStyle::marginRight, &RenderStyle::setMarginRight)); 6308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyMarginTop, &RenderStyle::marginTop, &RenderStyle::setMarginTop)); 6318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyMarginBottom, &RenderStyle::marginBottom, &RenderStyle::setMarginBottom)); 6328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyPaddingLeft, &RenderStyle::paddingLeft, &RenderStyle::setPaddingLeft)); 6338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyPaddingRight, &RenderStyle::paddingRight, &RenderStyle::setPaddingRight)); 6348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyPaddingTop, &RenderStyle::paddingTop, &RenderStyle::setPaddingTop)); 6358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyPaddingBottom, &RenderStyle::paddingBottom, &RenderStyle::setPaddingBottom)); 6368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<const Color&>(CSSPropertyColor, &RenderStyle::color, &RenderStyle::setColor)); 6375f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian 6388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<const Color&>(CSSPropertyBackgroundColor, &RenderStyle::backgroundColor, &RenderStyle::setBackgroundColor)); 6395f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian 640231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block gPropertyWrappers->append(new FillLayersPropertyWrapper(CSSPropertyBackgroundPositionX, &RenderStyle::backgroundLayers, &RenderStyle::accessBackgroundLayers)); 641231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block gPropertyWrappers->append(new FillLayersPropertyWrapper(CSSPropertyBackgroundPositionY, &RenderStyle::backgroundLayers, &RenderStyle::accessBackgroundLayers)); 642231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block gPropertyWrappers->append(new FillLayersPropertyWrapper(CSSPropertyBackgroundSize, &RenderStyle::backgroundLayers, &RenderStyle::accessBackgroundLayers)); 643cac0f67c402d107cdb10971b95719e2ff9c7c76bSteve Block gPropertyWrappers->append(new FillLayersPropertyWrapper(CSSPropertyWebkitBackgroundSize, &RenderStyle::backgroundLayers, &RenderStyle::accessBackgroundLayers)); 644231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 645231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block gPropertyWrappers->append(new FillLayersPropertyWrapper(CSSPropertyWebkitMaskPositionX, &RenderStyle::maskLayers, &RenderStyle::accessMaskLayers)); 646231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block gPropertyWrappers->append(new FillLayersPropertyWrapper(CSSPropertyWebkitMaskPositionY, &RenderStyle::maskLayers, &RenderStyle::accessMaskLayers)); 647231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block gPropertyWrappers->append(new FillLayersPropertyWrapper(CSSPropertyWebkitMaskSize, &RenderStyle::maskLayers, &RenderStyle::accessMaskLayers)); 6485f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian 6498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<int>(CSSPropertyFontSize, &RenderStyle::fontSize, &RenderStyle::setBlendedFontSize)); 6508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<unsigned short>(CSSPropertyWebkitColumnRuleWidth, &RenderStyle::columnRuleWidth, &RenderStyle::setColumnRuleWidth)); 6518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<float>(CSSPropertyWebkitColumnGap, &RenderStyle::columnGap, &RenderStyle::setColumnGap)); 6528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<unsigned short>(CSSPropertyWebkitColumnCount, &RenderStyle::columnCount, &RenderStyle::setColumnCount)); 6538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<float>(CSSPropertyWebkitColumnWidth, &RenderStyle::columnWidth, &RenderStyle::setColumnWidth)); 6548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<short>(CSSPropertyWebkitBorderHorizontalSpacing, &RenderStyle::horizontalBorderSpacing, &RenderStyle::setHorizontalBorderSpacing)); 6558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<short>(CSSPropertyWebkitBorderVerticalSpacing, &RenderStyle::verticalBorderSpacing, &RenderStyle::setVerticalBorderSpacing)); 6568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<int>(CSSPropertyZIndex, &RenderStyle::zIndex, &RenderStyle::setZIndex)); 6578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyLineHeight, &RenderStyle::lineHeight, &RenderStyle::setLineHeight)); 6588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<int>(CSSPropertyOutlineOffset, &RenderStyle::outlineOffset, &RenderStyle::setOutlineOffset)); 6598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<unsigned short>(CSSPropertyOutlineWidth, &RenderStyle::outlineWidth, &RenderStyle::setOutlineWidth)); 6608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<int>(CSSPropertyLetterSpacing, &RenderStyle::letterSpacing, &RenderStyle::setLetterSpacing)); 6618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<int>(CSSPropertyWordSpacing, &RenderStyle::wordSpacing, &RenderStyle::setWordSpacing)); 6620bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyTextIndent, &RenderStyle::textIndent, &RenderStyle::setTextIndent)); 6630bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 6648f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian gPropertyWrappers->append(new PropertyWrapper<float>(CSSPropertyWebkitPerspective, &RenderStyle::perspective, &RenderStyle::setPerspective)); 6658f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyWebkitPerspectiveOriginX, &RenderStyle::perspectiveOriginX, &RenderStyle::setPerspectiveOriginX)); 6668f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyWebkitPerspectiveOriginY, &RenderStyle::perspectiveOriginY, &RenderStyle::setPerspectiveOriginY)); 6678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyWebkitTransformOriginX, &RenderStyle::transformOriginX, &RenderStyle::setTransformOriginX)); 6688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<Length>(CSSPropertyWebkitTransformOriginY, &RenderStyle::transformOriginY, &RenderStyle::setTransformOriginY)); 6698f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian gPropertyWrappers->append(new PropertyWrapper<float>(CSSPropertyWebkitTransformOriginZ, &RenderStyle::transformOriginZ, &RenderStyle::setTransformOriginZ)); 6705ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen gPropertyWrappers->append(new PropertyWrapper<const LengthSize&>(CSSPropertyBorderTopLeftRadius, &RenderStyle::borderTopLeftRadius, &RenderStyle::setBorderTopLeftRadius)); 6715ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen gPropertyWrappers->append(new PropertyWrapper<const LengthSize&>(CSSPropertyBorderTopRightRadius, &RenderStyle::borderTopRightRadius, &RenderStyle::setBorderTopRightRadius)); 6725ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen gPropertyWrappers->append(new PropertyWrapper<const LengthSize&>(CSSPropertyBorderBottomLeftRadius, &RenderStyle::borderBottomLeftRadius, &RenderStyle::setBorderBottomLeftRadius)); 6735ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen gPropertyWrappers->append(new PropertyWrapper<const LengthSize&>(CSSPropertyBorderBottomRightRadius, &RenderStyle::borderBottomRightRadius, &RenderStyle::setBorderBottomRightRadius)); 6748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<EVisibility>(CSSPropertyVisibility, &RenderStyle::visibility, &RenderStyle::setVisibility)); 6758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<float>(CSSPropertyZoom, &RenderStyle::zoom, &RenderStyle::setZoom)); 67606ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen 67706ea8e899e48f1f2f396b70e63fae369f2f23232Kristian Monsen gPropertyWrappers->append(new PropertyWrapper<LengthBox>(CSSPropertyClip, &RenderStyle::clip, &RenderStyle::setClip)); 6788f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 6798f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#if USE(ACCELERATED_COMPOSITING) 6808f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian gPropertyWrappers->append(new PropertyWrapperAcceleratedOpacity()); 6818f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian gPropertyWrappers->append(new PropertyWrapperAcceleratedTransform()); 6828f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#else 6838f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian gPropertyWrappers->append(new PropertyWrapper<float>(CSSPropertyOpacity, &RenderStyle::opacity, &RenderStyle::setOpacity)); 6848f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian gPropertyWrappers->append(new PropertyWrapper<const TransformOperations&>(CSSPropertyWebkitTransform, &RenderStyle::transform, &RenderStyle::setTransform)); 6858f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#endif 6868f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 6878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapperMaybeInvalidColor(CSSPropertyWebkitColumnRuleColor, &RenderStyle::columnRuleColor, &RenderStyle::setColumnRuleColor)); 6888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapperMaybeInvalidColor(CSSPropertyWebkitTextStrokeColor, &RenderStyle::textStrokeColor, &RenderStyle::setTextStrokeColor)); 6898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapperMaybeInvalidColor(CSSPropertyWebkitTextFillColor, &RenderStyle::textFillColor, &RenderStyle::setTextFillColor)); 6908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapperMaybeInvalidColor(CSSPropertyBorderLeftColor, &RenderStyle::borderLeftColor, &RenderStyle::setBorderLeftColor)); 6918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapperMaybeInvalidColor(CSSPropertyBorderRightColor, &RenderStyle::borderRightColor, &RenderStyle::setBorderRightColor)); 6928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapperMaybeInvalidColor(CSSPropertyBorderTopColor, &RenderStyle::borderTopColor, &RenderStyle::setBorderTopColor)); 6938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapperMaybeInvalidColor(CSSPropertyBorderBottomColor, &RenderStyle::borderBottomColor, &RenderStyle::setBorderBottomColor)); 6948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapperMaybeInvalidColor(CSSPropertyOutlineColor, &RenderStyle::outlineColor, &RenderStyle::setOutlineColor)); 6958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 696cad810f21b803229eb11403f9209855525a25d57Steve Block gPropertyWrappers->append(new PropertyWrapperShadow(CSSPropertyBoxShadow, &RenderStyle::boxShadow, &RenderStyle::setBoxShadow)); 697231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block gPropertyWrappers->append(new PropertyWrapperShadow(CSSPropertyWebkitBoxShadow, &RenderStyle::boxShadow, &RenderStyle::setBoxShadow)); 6988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapperShadow(CSSPropertyTextShadow, &RenderStyle::textShadow, &RenderStyle::setTextShadow)); 6998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 7008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#if ENABLE(SVG) 7018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<float>(CSSPropertyFillOpacity, &RenderStyle::fillOpacity, &RenderStyle::setFillOpacity)); 7028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<float>(CSSPropertyFloodOpacity, &RenderStyle::floodOpacity, &RenderStyle::setFloodOpacity)); 7038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrappers->append(new PropertyWrapper<float>(CSSPropertyStrokeOpacity, &RenderStyle::strokeOpacity, &RenderStyle::setStrokeOpacity)); 7048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#endif 7058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 706635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // TODO: 707635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // 708635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // CSSPropertyVerticalAlign 709635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // 710635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Compound properties that have components that should be animatable: 711635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // 712635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // CSSPropertyWebkitColumns 713635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // CSSPropertyWebkitBoxReflect 714635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 7158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Make sure unused slots have a value 716635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project for (unsigned int i = 0; i < static_cast<unsigned int>(numCSSProperties); ++i) 717635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project gPropertyWrapperMap[i] = cInvalidPropertyWrapperIndex; 7188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 719635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // First we put the non-shorthand property wrappers into the map, so the shorthand-building 720635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // code can find them. 7218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t n = gPropertyWrappers->size(); 7228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project for (unsigned int i = 0; i < n; ++i) { 7238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT((*gPropertyWrappers)[i]->property() - firstCSSProperty < numCSSProperties); 7248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project gPropertyWrapperMap[(*gPropertyWrappers)[i]->property() - firstCSSProperty] = i; 7258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 726635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 727635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Now add the shorthand wrappers. 728635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project addShorthandProperties(); 7298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 7308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 7318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 732635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectstatic void addPropertyWrapper(int propertyID, PropertyWrapperBase* wrapper) 733635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project{ 734635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project int propIndex = propertyID - firstCSSProperty; 735635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 736635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project ASSERT(gPropertyWrapperMap[propIndex] == cInvalidPropertyWrapperIndex); 737635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 738635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project unsigned wrapperIndex = gPropertyWrappers->size(); 739635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project gPropertyWrappers->append(wrapper); 740635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project gPropertyWrapperMap[propIndex] = wrapperIndex; 741635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project} 742635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 743635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectstatic void addShorthandProperties() 744635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project{ 745635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project static const int animatableShorthandProperties[] = { 7465f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian CSSPropertyBackground, // for background-color, background-position 7475f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian CSSPropertyBackgroundPosition, 7485f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian CSSPropertyWebkitMask, // for mask-position 7495f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian CSSPropertyWebkitMaskPosition, 750635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyBorderTop, CSSPropertyBorderRight, CSSPropertyBorderBottom, CSSPropertyBorderLeft, 751f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch CSSPropertyBorderColor, 752f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch CSSPropertyBorderRadius, 753635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyBorderWidth, 754635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyBorder, 755635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyBorderSpacing, 756635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyMargin, 757635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyOutline, 758635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyPadding, 759635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyWebkitTextStroke, 760635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyWebkitColumnRule, 761635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyWebkitBorderRadius, 762635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyWebkitTransformOrigin 763635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project }; 764635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 7654576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang for (size_t i = 0; i < WTF_ARRAY_LENGTH(animatableShorthandProperties); ++i) { 766635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project int propertyID = animatableShorthandProperties[i]; 767635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyLonghand longhand = longhandForProperty(propertyID); 768635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (longhand.length() > 0) 769635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project addPropertyWrapper(propertyID, new ShorthandPropertyWrapper(propertyID, longhand)); 770635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 771635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 772635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // 'font' is not in the shorthand map. 773635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project static const int animatableFontProperties[] = { 774635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyFontSize, 775635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project CSSPropertyFontWeight 776635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project }; 777635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 7784576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang CSSPropertyLonghand fontLonghand(animatableFontProperties, WTF_ARRAY_LENGTH(animatableFontProperties)); 779635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project addPropertyWrapper(CSSPropertyFont, new ShorthandPropertyWrapper(CSSPropertyFont, fontLonghand)); 780635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project} 781635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 782635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectstatic PropertyWrapperBase* wrapperForProperty(int propertyID) 783635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project{ 784635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project int propIndex = propertyID - firstCSSProperty; 785635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (propIndex >= 0 && propIndex < numCSSProperties) { 786635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project int wrapperIndex = gPropertyWrapperMap[propIndex]; 787635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (wrapperIndex >= 0) 788635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return (*gPropertyWrappers)[wrapperIndex]; 789635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 790635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return 0; 791635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project} 792635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 7938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectAnimationBase::AnimationBase(const Animation* transition, RenderObject* renderer, CompositeAnimation* compAnim) 7948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project : m_animState(AnimationStateNew) 7958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_isAnimating(false) 7968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_startTime(0) 7978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_pauseTime(-1) 798635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project , m_requestedStartTime(0) 7998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_object(renderer) 8008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_animation(const_cast<Animation*>(transition)) 8018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_compAnim(compAnim) 802967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch , m_isAccelerated(false) 8038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project , m_transformFunctionListValid(false) 804635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project , m_nextIterationDuration(-1) 8058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 806635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Compute the total duration 807635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_totalDuration = -1; 808635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (m_animation->iterationCount() > 0) 809635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_totalDuration = m_animation->duration() * m_animation->iterationCount(); 8108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 8118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectbool AnimationBase::propertiesEqual(int prop, const RenderStyle* a, const RenderStyle* b) 8138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 8148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ensurePropertyMap(); 8158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (prop == cAnimateAll) { 8168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t n = gPropertyWrappers->size(); 8178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project for (unsigned int i = 0; i < n; ++i) { 818635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project PropertyWrapperBase* wrapper = (*gPropertyWrappers)[i]; 819635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // No point comparing shorthand wrappers for 'all'. 820635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (!wrapper->isShorthandWrapper() && !wrapper->equals(a, b)) 8218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 8228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 8238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else { 824635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project PropertyWrapperBase* wrapper = wrapperForProperty(prop); 825635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (wrapper) 826635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return wrapper->equals(a, b); 8278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 8288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return true; 8298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 8308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 831635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectint AnimationBase::getPropertyAtIndex(int i, bool& isShorthand) 8328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 8338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ensurePropertyMap(); 8348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (i < 0 || i >= static_cast<int>(gPropertyWrappers->size())) 8358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return CSSPropertyInvalid; 8368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 837635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project PropertyWrapperBase* wrapper = (*gPropertyWrappers)[i]; 838635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project isShorthand = wrapper->isShorthandWrapper(); 839635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return wrapper->property(); 8408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 8418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectint AnimationBase::getNumProperties() 8438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 8448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ensurePropertyMap(); 8458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return gPropertyWrappers->size(); 8468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 8478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project// Returns true if we need to start animation timers 8498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectbool AnimationBase::blendProperties(const AnimationBase* anim, int prop, RenderStyle* dst, const RenderStyle* a, const RenderStyle* b, double progress) 8508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 8518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(prop != cAnimateAll); 8528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 853635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project ensurePropertyMap(); 854635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project PropertyWrapperBase* wrapper = wrapperForProperty(prop); 855635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (wrapper) { 856635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project wrapper->blend(anim, dst, a, b, progress); 8578f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#if USE(ACCELERATED_COMPOSITING) 858967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch return !wrapper->animationIsAccelerated() || !anim->isAccelerated(); 8598f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#else 860635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return true; 8618f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#endif 8628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 8638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return false; 8658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 8668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 8678f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#if USE(ACCELERATED_COMPOSITING) 8688f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qianbool AnimationBase::animationOfPropertyIsAccelerated(int prop) 8698f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian{ 8708f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian ensurePropertyMap(); 8718f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian PropertyWrapperBase* wrapper = wrapperForProperty(prop); 8728f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian return wrapper ? wrapper->animationIsAccelerated() : false; 8738f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian} 8748f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#endif 8758f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 876f05b935882198ccf7d81675736e3aeb089c5113aBen Murdochstatic bool gatherEnclosingShorthandProperties(int property, PropertyWrapperBase* wrapper, HashSet<int>& propertySet) 877f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch{ 878f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch if (!wrapper->isShorthandWrapper()) 879f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch return false; 880f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 881f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch ShorthandPropertyWrapper* shorthandWrapper = static_cast<ShorthandPropertyWrapper*>(wrapper); 882f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 883f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch bool contained = false; 884f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch for (size_t i = 0; i < shorthandWrapper->propertyWrappers().size(); ++i) { 885f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch PropertyWrapperBase* currWrapper = shorthandWrapper->propertyWrappers()[i]; 886f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 887f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch if (gatherEnclosingShorthandProperties(property, currWrapper, propertySet) || currWrapper->property() == property) 888f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch contained = true; 889f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch } 890f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 891f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch if (contained) 892f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch propertySet.add(wrapper->property()); 893f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 894f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch return contained; 895f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch} 896f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 897f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch// Note: this is inefficient. It's only called from pauseTransitionAtTime(). 898f05b935882198ccf7d81675736e3aeb089c5113aBen MurdochHashSet<int> AnimationBase::animatableShorthandsAffectingProperty(int property) 899f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch{ 900f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch ensurePropertyMap(); 901f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 902f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch HashSet<int> foundProperties; 903f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch for (int i = 0; i < getNumProperties(); ++i) 904f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch gatherEnclosingShorthandProperties(property, (*gPropertyWrappers)[i], foundProperties); 905f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 906f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch return foundProperties; 907f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch} 908f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch 9095f1ab04193ad0130ca8204aadaceae083aca9881Feng Qianvoid AnimationBase::setNeedsStyleRecalc(Node* node) 9108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 9118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(!node || (node->document() && !node->document()->inPageCache())); 912635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (node) 913231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block node->setNeedsStyleRecalc(SyntheticStyleChange); 9148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 9158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectdouble AnimationBase::duration() const 9178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 9188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return m_animation->duration(); 9198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 9208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectbool AnimationBase::playStatePlaying() const 9228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 923635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return m_animation->playState() == AnimPlayStatePlaying; 9248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 9258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectbool AnimationBase::animationsMatch(const Animation* anim) const 9278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 9288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return m_animation->animationsMatch(anim); 9298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 9308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid AnimationBase::updateStateMachine(AnimStateInput input, double param) 9328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 9332daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch if (!m_compAnim) 9342daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch return; 9352daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch 9368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // If we get AnimationStateInputRestartAnimation then we force a new animation, regardless of state. 9378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (input == AnimationStateInputMakeNew) { 9388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_animState == AnimationStateStartWaitStyleAvailable) 9392bde8e466a4451c7319e3a072d118917957d6554Steve Block m_compAnim->animationController()->removeFromAnimationsWaitingForStyle(this); 9408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_animState = AnimationStateNew; 9418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_startTime = 0; 9428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_pauseTime = -1; 943635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_requestedStartTime = 0; 944635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_nextIterationDuration = -1; 945d0825bca7fe65beaee391d30da42e937db621564Steve Block endAnimation(); 9468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 9478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 9488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (input == AnimationStateInputRestartAnimation) { 9508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_animState == AnimationStateStartWaitStyleAvailable) 9512bde8e466a4451c7319e3a072d118917957d6554Steve Block m_compAnim->animationController()->removeFromAnimationsWaitingForStyle(this); 9528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_animState = AnimationStateNew; 9538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_startTime = 0; 9548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_pauseTime = -1; 955635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_requestedStartTime = 0; 956635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_nextIterationDuration = -1; 957d0825bca7fe65beaee391d30da42e937db621564Steve Block endAnimation(); 9588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!paused()) 9608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project updateStateMachine(AnimationStateInputStartAnimation, -1); 9618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 9628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 9638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (input == AnimationStateInputEndAnimation) { 9658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_animState == AnimationStateStartWaitStyleAvailable) 9662bde8e466a4451c7319e3a072d118917957d6554Steve Block m_compAnim->animationController()->removeFromAnimationsWaitingForStyle(this); 9678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_animState = AnimationStateDone; 968d0825bca7fe65beaee391d30da42e937db621564Steve Block endAnimation(); 9698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 9708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 9718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (input == AnimationStateInputPauseOverride) { 9738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_animState == AnimationStateStartWaitResponse) { 9748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // If we are in AnimationStateStartWaitResponse, the animation will get canceled before 9758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // we get a response, so move to the next state. 976d0825bca7fe65beaee391d30da42e937db621564Steve Block endAnimation(); 977635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project updateStateMachine(AnimationStateInputStartTimeSet, beginAnimationUpdateTime()); 9788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 9798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 9808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 9818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (input == AnimationStateInputResumeOverride) { 9838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_animState == AnimationStateLooping || m_animState == AnimationStateEnding) { 9848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Start the animation 985d0825bca7fe65beaee391d30da42e937db621564Steve Block startAnimation(beginAnimationUpdateTime() - m_startTime); 9868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 9878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 9888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 9898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 9908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Execute state machine 9918f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian switch (m_animState) { 9928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case AnimationStateNew: 993dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block ASSERT(input == AnimationStateInputStartAnimation || input == AnimationStateInputPlayStateRunning || input == AnimationStateInputPlayStatePaused); 994dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block if (input == AnimationStateInputStartAnimation || input == AnimationStateInputPlayStateRunning) { 995635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_requestedStartTime = beginAnimationUpdateTime(); 9968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_animState = AnimationStateStartWaitTimer; 9978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 9988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 9998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case AnimationStateStartWaitTimer: 10008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(input == AnimationStateInputStartTimerFired || input == AnimationStateInputPlayStatePaused); 10018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (input == AnimationStateInputStartTimerFired) { 10038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(param >= 0); 10048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Start timer has fired, tell the animation to start and wait for it to respond with start time 10058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_animState = AnimationStateStartWaitStyleAvailable; 10062bde8e466a4451c7319e3a072d118917957d6554Steve Block m_compAnim->animationController()->addToAnimationsWaitingForStyle(this); 10078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Trigger a render so we can start the animation 1009635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (m_object) 10105f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian m_compAnim->animationController()->addNodeChangeToDispatch(m_object->node()); 10118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else { 10128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(!paused()); 10138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // We're waiting for the start timer to fire and we got a pause. Cancel the timer, pause and wait 1014635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_pauseTime = beginAnimationUpdateTime(); 10158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_animState = AnimationStatePausedWaitTimer; 10168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 10178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 10188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case AnimationStateStartWaitStyleAvailable: 10198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(input == AnimationStateInputStyleAvailable || input == AnimationStateInputPlayStatePaused); 10208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10210617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen if (input == AnimationStateInputStyleAvailable) { 10220617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // Start timer has fired, tell the animation to start and wait for it to respond with start time 10230617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_animState = AnimationStateStartWaitResponse; 10248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10250617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen overrideAnimations(); 10260617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen 10270617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // Start the animation 10280617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen if (overridden()) { 10290617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // We won't try to start accelerated animations if we are overridden and 10300617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // just move on to the next state. 10310617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_animState = AnimationStateStartWaitResponse; 10320617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_isAccelerated = false; 10330617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen updateStateMachine(AnimationStateInputStartTimeSet, beginAnimationUpdateTime()); 10340617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen } else { 10350617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen double timeOffset = 0; 10360617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // If the value for 'animation-delay' is negative then the animation appears to have started in the past. 10370617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen if (m_animation->delay() < 0) 10380617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen timeOffset = -m_animation->delay(); 10390617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen bool started = startAnimation(timeOffset); 10408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10412bde8e466a4451c7319e3a072d118917957d6554Steve Block m_compAnim->animationController()->addToAnimationsWaitingForStartTimeResponse(this, started); 10420617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_isAccelerated = started; 10430617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen } 10440617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen } else { 10450617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // We're waiting for the style to be available and we got a pause. Pause and wait 10460617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_pauseTime = beginAnimationUpdateTime(); 10470617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_animState = AnimationStatePausedWaitStyleAvailable; 10488f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian } 10498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 10508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case AnimationStateStartWaitResponse: 10518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(input == AnimationStateInputStartTimeSet || input == AnimationStateInputPlayStatePaused); 10528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (input == AnimationStateInputStartTimeSet) { 10548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(param >= 0); 10558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // We have a start time, set it, unless the startTime is already set 1056d0825bca7fe65beaee391d30da42e937db621564Steve Block if (m_startTime <= 0) { 10578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_startTime = param; 1058d0825bca7fe65beaee391d30da42e937db621564Steve Block // If the value for 'animation-delay' is negative then the animation appears to have started in the past. 1059d0825bca7fe65beaee391d30da42e937db621564Steve Block if (m_animation->delay() < 0) 1060d0825bca7fe65beaee391d30da42e937db621564Steve Block m_startTime += m_animation->delay(); 1061d0825bca7fe65beaee391d30da42e937db621564Steve Block } 10628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 106321939df44de1705786c545cd1bf519d47250322dBen Murdoch // Now that we know the start time, fire the start event. 106421939df44de1705786c545cd1bf519d47250322dBen Murdoch onAnimationStart(0); // The elapsedTime is 0. 106521939df44de1705786c545cd1bf519d47250322dBen Murdoch 1066635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Decide whether to go into looping or ending state 1067635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project goIntoEndingOrLoopingState(); 10688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10695f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian // Dispatch updateStyleIfNeeded so we can start the animation 1070635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (m_object) 10715f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian m_compAnim->animationController()->addNodeChangeToDispatch(m_object->node()); 10728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else { 10738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // We are pausing while waiting for a start response. Cancel the animation and wait. When 10748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // we unpause, we will act as though the start timer just fired 10752bde8e466a4451c7319e3a072d118917957d6554Steve Block m_pauseTime = beginAnimationUpdateTime(); 1076d0825bca7fe65beaee391d30da42e937db621564Steve Block pauseAnimation(beginAnimationUpdateTime() - m_startTime); 10778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_animState = AnimationStatePausedWaitResponse; 10788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 10798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 10808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case AnimationStateLooping: 10818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(input == AnimationStateInputLoopTimerFired || input == AnimationStateInputPlayStatePaused); 10828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 10838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (input == AnimationStateInputLoopTimerFired) { 10848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(param >= 0); 10858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Loop timer fired, loop again or end. 10868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project onAnimationIteration(param); 1087635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 1088635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Decide whether to go into looping or ending state 1089635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project goIntoEndingOrLoopingState(); 10908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else { 10918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // We are pausing while running. Cancel the animation and wait 1092635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_pauseTime = beginAnimationUpdateTime(); 1093d0825bca7fe65beaee391d30da42e937db621564Steve Block pauseAnimation(beginAnimationUpdateTime() - m_startTime); 10948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_animState = AnimationStatePausedRun; 10958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 10968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 10978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case AnimationStateEnding: 10988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(input == AnimationStateInputEndTimerFired || input == AnimationStateInputPlayStatePaused); 10998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (input == AnimationStateInputEndTimerFired) { 1101dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block 11028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(param >= 0); 11038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // End timer fired, finish up 11048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project onAnimationEnd(param); 11058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_animState = AnimationStateDone; 1107635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 1108635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (m_object) { 1109dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block if (m_animation->fillsForwards()) 1110dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block m_animState = AnimationStateFillingForwards; 1111dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block else 1112dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block resumeOverriddenAnimations(); 1113635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 1114635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Fire off another style change so we can set the final value 11155f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian m_compAnim->animationController()->addNodeChangeToDispatch(m_object->node()); 1116635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 11178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else { 11188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // We are pausing while running. Cancel the animation and wait 1119635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_pauseTime = beginAnimationUpdateTime(); 1120d0825bca7fe65beaee391d30da42e937db621564Steve Block pauseAnimation(beginAnimationUpdateTime() - m_startTime); 11218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_animState = AnimationStatePausedRun; 11228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 11238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // |this| may be deleted here 11248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 11258e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case AnimationStatePausedWaitTimer: 1126dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block ASSERT(input == AnimationStateInputPlayStateRunning); 11278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(paused()); 11288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Update the times 1129635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_startTime += beginAnimationUpdateTime() - m_pauseTime; 11308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_pauseTime = -1; 11318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 11328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // we were waiting for the start timer to fire, go back and wait again 11338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_animState = AnimationStateNew; 11348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project updateStateMachine(AnimationStateInputStartAnimation, 0); 11358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 11368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case AnimationStatePausedWaitResponse: 11370617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen case AnimationStatePausedWaitStyleAvailable: 11388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case AnimationStatePausedRun: 11398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // We treat these two cases the same. The only difference is that, when we are in 11408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // AnimationStatePausedWaitResponse, we don't yet have a valid startTime, so we send 0 to startAnimation. 11418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // When the AnimationStateInputStartTimeSet comes in and we were in AnimationStatePausedRun, we will notice 11428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // that we have already set the startTime and will ignore it. 11430617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen ASSERT(input == AnimationStateInputPlayStateRunning || input == AnimationStateInputStartTimeSet || input == AnimationStateInputStyleAvailable); 11448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(paused()); 11458f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 11460617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen if (input == AnimationStateInputPlayStateRunning) { 11470617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // Update the times 11480617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen if (m_animState == AnimationStatePausedRun) 11490617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_startTime += beginAnimationUpdateTime() - m_pauseTime; 11500617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen else 11510617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_startTime = 0; 11520617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_pauseTime = -1; 11530617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen 11540617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen if (m_animState == AnimationStatePausedWaitStyleAvailable) 11550617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_animState = AnimationStateStartWaitStyleAvailable; 11560617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen else { 11570617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // We were either running or waiting for a begin time response from the animation. 11580617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // Either way we need to restart the animation (possibly with an offset if we 11590617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // had already been running) and wait for it to start. 11600617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_animState = AnimationStateStartWaitResponse; 11610617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen 11620617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // Start the animation 11630617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen if (overridden()) { 11640617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // We won't try to start accelerated animations if we are overridden and 11650617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // just move on to the next state. 11660617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen updateStateMachine(AnimationStateInputStartTimeSet, beginAnimationUpdateTime()); 11670617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_isAccelerated = true; 11680617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen } else { 11690617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen bool started = startAnimation(beginAnimationUpdateTime() - m_startTime); 11702bde8e466a4451c7319e3a072d118917957d6554Steve Block m_compAnim->animationController()->addToAnimationsWaitingForStartTimeResponse(this, started); 11715ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_isAccelerated = started; 11720617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen } 11730617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen } 11740617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen break; 11750617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen } 11760617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen 11770617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen if (input == AnimationStateInputStartTimeSet) { 11780617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen ASSERT(m_animState == AnimationStatePausedWaitResponse); 11790617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen 11800617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // We are paused but we got the callback that notifies us that an accelerated animation started. 11810617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // We ignore the start time and just move into the paused-run state. 11828f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian m_animState = AnimationStatePausedRun; 11838f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian ASSERT(m_startTime == 0); 11848f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian m_startTime = param; 11858f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian m_pauseTime += m_startTime; 11868f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian break; 11878f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian } 11888f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 11890617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen ASSERT(m_animState == AnimationStatePausedWaitStyleAvailable); 11900617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // We are paused but we got the callback that notifies us that style has been updated. 11910617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen // We move to the AnimationStatePausedWaitResponse state 11920617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen m_animState = AnimationStatePausedWaitResponse; 11930617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen overrideAnimations(); 11948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 1195dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block case AnimationStateFillingForwards: 11968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project case AnimationStateDone: 11978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // We're done. Stay in this state until we are deleted 11988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project break; 11998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 12008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 12018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1202635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectvoid AnimationBase::fireAnimationEventsIfNeeded() 12038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 12042daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch if (!m_compAnim) 12052daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch return; 12062daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch 1207635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // If we are waiting for the delay time to expire and it has, go to the next state 1208635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (m_animState != AnimationStateStartWaitTimer && m_animState != AnimationStateLooping && m_animState != AnimationStateEnding) 1209635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return; 12108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1211635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // We have to make sure to keep a ref to the this pointer, because it could get destroyed 1212635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // during an animation callback that might get called. Since the owner is a CompositeAnimation 1213635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // and it ref counts this object, we will keep a ref to that instead. That way the AnimationBase 1214635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // can still access the resources of its CompositeAnimation as needed. 1215635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project RefPtr<AnimationBase> protector(this); 1216635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project RefPtr<CompositeAnimation> compProtector(m_compAnim); 1217635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 1218635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Check for start timeout 1219635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (m_animState == AnimationStateStartWaitTimer) { 1220635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (beginAnimationUpdateTime() - m_requestedStartTime >= m_animation->delay()) 1221635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project updateStateMachine(AnimationStateInputStartTimerFired, 0); 1222635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return; 1223635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 1224635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 1225635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project double elapsedDuration = beginAnimationUpdateTime() - m_startTime; 12268f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian // FIXME: we need to ensure that elapsedDuration is never < 0. If it is, this suggests that 12278f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian // we had a recalcStyle() outside of beginAnimationUpdate()/endAnimationUpdate(). 12288f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian // Also check in getTimeToNextEvent(). 12298f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian elapsedDuration = max(elapsedDuration, 0.0); 1230635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 1231635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Check for end timeout 1232635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (m_totalDuration >= 0 && elapsedDuration >= m_totalDuration) { 123368513a70bcd92384395513322f1b801e7bf9c729Steve Block // We may still be in AnimationStateLooping if we've managed to skip a 123468513a70bcd92384395513322f1b801e7bf9c729Steve Block // whole iteration, in which case we should jump to the end state. 123568513a70bcd92384395513322f1b801e7bf9c729Steve Block m_animState = AnimationStateEnding; 123668513a70bcd92384395513322f1b801e7bf9c729Steve Block 1237635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Fire an end event 1238635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project updateStateMachine(AnimationStateInputEndTimerFired, m_totalDuration); 12398f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian } else { 1240635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Check for iteration timeout 1241635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (m_nextIterationDuration < 0) { 1242635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Hasn't been set yet, set it 1243635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project double durationLeft = m_animation->duration() - fmod(elapsedDuration, m_animation->duration()); 1244635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_nextIterationDuration = elapsedDuration + durationLeft; 1245635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 1246635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 1247635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (elapsedDuration >= m_nextIterationDuration) { 1248635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Set to the next iteration 1249635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project double previous = m_nextIterationDuration; 1250635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project double durationLeft = m_animation->duration() - fmod(elapsedDuration, m_animation->duration()); 1251635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_nextIterationDuration = elapsedDuration + durationLeft; 1252635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 1253635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Send the event 1254635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project updateStateMachine(AnimationStateInputLoopTimerFired, previous); 1255635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 12568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 12578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 12588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 125928040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhuvoid AnimationBase::updatePlayState(EAnimPlayState playState) 12608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 12612daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch if (!m_compAnim) 12622daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch return; 12632daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch 126428040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhu // When we get here, we can have one of 4 desired states: running, paused, suspended, paused & suspended. 126528040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhu // The state machine can be in one of two states: running, paused. 126628040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhu // Set the state machine to the desired state. 126728040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhu bool pause = playState == AnimPlayStatePaused || m_compAnim->suspended(); 126828040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhu 126928040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhu if (pause == paused() && !isNew()) 127028040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhu return; 127128040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhu 127228040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhu updateStateMachine(pause ? AnimationStateInputPlayStatePaused : AnimationStateInputPlayStateRunning, -1); 12738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 12748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 12755f1ab04193ad0130ca8204aadaceae083aca9881Feng Qiandouble AnimationBase::timeToNextService() 1276635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project{ 1277635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Returns the time at which next service is required. -1 means no service is required. 0 means 1278635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // service is required now, and > 0 means service is required that many seconds in the future. 1279dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block if (paused() || isNew() || m_animState == AnimationStateFillingForwards) 1280635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return -1; 12818f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 1282635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (m_animState == AnimationStateStartWaitTimer) { 1283635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project double timeFromNow = m_animation->delay() - (beginAnimationUpdateTime() - m_requestedStartTime); 12848f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian return max(timeFromNow, 0.0); 1285635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 1286635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 12878f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian fireAnimationEventsIfNeeded(); 12888f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 1289635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // In all other cases, we need service right away. 1290635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return 0; 1291635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project} 1292635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 12938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectdouble AnimationBase::progress(double scale, double offset, const TimingFunction* tf) const 12948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 12958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (preActive()) 12968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return 0; 12978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1298635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project double elapsedTime = getElapsedTime(); 12998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 13008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project double dur = m_animation->duration(); 13018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_animation->iterationCount() > 0) 13028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project dur *= m_animation->iterationCount(); 13038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1304dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block if (postActive() || !m_animation->duration()) 13058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return 1.0; 1306dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block if (m_animation->iterationCount() > 0 && elapsedTime >= dur) 1307dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block return (m_animation->iterationCount() % 2) ? 1.0 : 0.0; 13088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 13098e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Compute the fractional time, taking into account direction. 13108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // There is no need to worry about iterations, we assume that we would have 13118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // short circuited above if we were done. 13128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project double fractionalTime = elapsedTime / m_animation->duration(); 13138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project int integralTime = static_cast<int>(fractionalTime); 13148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project fractionalTime -= integralTime; 13158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 13165ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen if ((m_animation->direction() == Animation::AnimationDirectionAlternate) && (integralTime & 1)) 13178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project fractionalTime = 1 - fractionalTime; 13188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 13198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (scale != 1 || offset) 13208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project fractionalTime = (fractionalTime - offset) * scale; 13218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 13228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!tf) 13235abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick tf = m_animation->timingFunction().get(); 13245abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick 13255abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick if (tf->isCubicBezierTimingFunction()) { 13265abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick const CubicBezierTimingFunction* ctf = static_cast<const CubicBezierTimingFunction*>(tf); 13275abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick return solveCubicBezierFunction(ctf->x1(), 13285abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick ctf->y1(), 13295abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick ctf->x2(), 13305abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick ctf->y2(), 13315abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick fractionalTime, m_animation->duration()); 13325abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick } else if (tf->isStepsTimingFunction()) { 13335abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick const StepsTimingFunction* stf = static_cast<const StepsTimingFunction*>(tf); 13345abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick return solveStepsFunction(stf->numberOfSteps(), stf->stepAtStart(), fractionalTime); 13355abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick } else 13368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return fractionalTime; 13378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 13388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 13398f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qianvoid AnimationBase::getTimeToNextEvent(double& time, bool& isLooping) const 13408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 13418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Decide when the end or loop event needs to fire 13428f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian const double elapsedDuration = max(beginAnimationUpdateTime() - m_startTime, 0.0); 13438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project double durationLeft = 0; 13448f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian double nextIterationTime = m_totalDuration; 1345635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 13468f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian if (m_totalDuration < 0 || elapsedDuration < m_totalDuration) { 13470bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch durationLeft = m_animation->duration() > 0 ? (m_animation->duration() - fmod(elapsedDuration, m_animation->duration())) : 0; 13488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project nextIterationTime = elapsedDuration + durationLeft; 13498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 13508f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 13518f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian if (m_totalDuration < 0 || nextIterationTime < m_totalDuration) { 1352635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // We are not at the end yet 13538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(nextIterationTime > 0); 13548f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian isLooping = true; 13558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else { 1356635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // We are at the end 13578f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian isLooping = false; 13588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 13598f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 13608f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian time = durationLeft; 13618f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian} 13628f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 13638f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qianvoid AnimationBase::goIntoEndingOrLoopingState() 13648f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian{ 13658f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian double t; 13668f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian bool isLooping; 13678f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian getTimeToNextEvent(t, isLooping); 13688f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian m_animState = isLooping ? AnimationStateLooping : AnimationStateEnding; 13698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 13708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 13710bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdochvoid AnimationBase::freezeAtTime(double t) 1372635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project{ 13732daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch if (!m_compAnim) 13742daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch return; 13752daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch 1376cad810f21b803229eb11403f9209855525a25d57Steve Block if (!m_startTime) { 1377cad810f21b803229eb11403f9209855525a25d57Steve Block // If we haven't started yet, just generate the start event now 1378cad810f21b803229eb11403f9209855525a25d57Steve Block m_compAnim->animationController()->receivedStartTimeResponse(currentTime()); 1379cad810f21b803229eb11403f9209855525a25d57Steve Block } 1380cad810f21b803229eb11403f9209855525a25d57Steve Block 13810bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch ASSERT(m_startTime); // if m_startTime is zero, we haven't started yet, so we'll get a bad pause time. 1382635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_pauseTime = m_startTime + t - m_animation->delay(); 13830bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch 13840bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch#if USE(ACCELERATED_COMPOSITING) 13850bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch if (m_object && m_object->hasLayer()) { 13860bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch RenderLayer* layer = toRenderBoxModelObject(m_object)->layer(); 13870bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch if (layer->isComposited()) 13880bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch layer->backing()->suspendAnimations(m_pauseTime); 13890bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch } 13900bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch#endif 1391635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project} 1392635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 1393635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectdouble AnimationBase::beginAnimationUpdateTime() const 1394635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project{ 13952daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch if (!m_compAnim) 13962daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch return 0; 13972daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch 13985f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian return m_compAnim->animationController()->beginAnimationUpdateTime(); 1399635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project} 1400635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 1401635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectdouble AnimationBase::getElapsedTime() const 1402635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project{ 1403635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (paused()) 1404635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return m_pauseTime - m_startTime; 1405635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (m_startTime <= 0) 1406635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return 0; 1407635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (postActive()) 1408635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return 1; 1409cad810f21b803229eb11403f9209855525a25d57Steve Block 1410635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return beginAnimationUpdateTime() - m_startTime; 1411635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project} 14122bde8e466a4451c7319e3a072d118917957d6554Steve Block 14132bde8e466a4451c7319e3a072d118917957d6554Steve Blockvoid AnimationBase::setElapsedTime(double time) 14142bde8e466a4451c7319e3a072d118917957d6554Steve Block{ 14152bde8e466a4451c7319e3a072d118917957d6554Steve Block // FIXME: implement this method 14162bde8e466a4451c7319e3a072d118917957d6554Steve Block UNUSED_PARAM(time); 14172bde8e466a4451c7319e3a072d118917957d6554Steve Block} 14182bde8e466a4451c7319e3a072d118917957d6554Steve Block 14192bde8e466a4451c7319e3a072d118917957d6554Steve Blockvoid AnimationBase::play() 14202bde8e466a4451c7319e3a072d118917957d6554Steve Block{ 14212bde8e466a4451c7319e3a072d118917957d6554Steve Block // FIXME: implement this method 14222bde8e466a4451c7319e3a072d118917957d6554Steve Block} 14232bde8e466a4451c7319e3a072d118917957d6554Steve Block 14242bde8e466a4451c7319e3a072d118917957d6554Steve Blockvoid AnimationBase::pause() 14252bde8e466a4451c7319e3a072d118917957d6554Steve Block{ 14262bde8e466a4451c7319e3a072d118917957d6554Steve Block // FIXME: implement this method 14272bde8e466a4451c7319e3a072d118917957d6554Steve Block} 14282bde8e466a4451c7319e3a072d118917957d6554Steve Block 14298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} // namespace WebCore 1430