| Index: skia/animator/SkDisplayApply.cpp
|
| ===================================================================
|
| --- skia/animator/SkDisplayApply.cpp (revision 16859)
|
| +++ skia/animator/SkDisplayApply.cpp (working copy)
|
| @@ -1,814 +0,0 @@
|
| -/* libs/graphics/animator/SkDisplayApply.cpp
|
| -**
|
| -** Copyright 2006, The Android Open Source Project
|
| -**
|
| -** Licensed under the Apache License, Version 2.0 (the "License");
|
| -** you may not use this file except in compliance with the License.
|
| -** You may obtain a copy of the License at
|
| -**
|
| -** http://www.apache.org/licenses/LICENSE-2.0
|
| -**
|
| -** Unless required by applicable law or agreed to in writing, software
|
| -** distributed under the License is distributed on an "AS IS" BASIS,
|
| -** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
| -** See the License for the specific language governing permissions and
|
| -** limitations under the License.
|
| -*/
|
| -
|
| -#include "SkDisplayApply.h"
|
| -#include "SkAnimateActive.h"
|
| -#include "SkAnimateMaker.h"
|
| -#include "SkAnimateSet.h"
|
| -#include "SkAnimatorScript.h"
|
| -#include "SkDisplayType.h"
|
| -#include "SkDrawGroup.h"
|
| -#include "SkParse.h"
|
| -#include "SkScript.h"
|
| -#include "SkSystemEventTypes.h"
|
| -#ifdef SK_DEBUG
|
| -#include "SkTime.h"
|
| -#endif
|
| -#include <ctype.h>
|
| -
|
| -enum SkApply_Properties {
|
| - SK_PROPERTY(animator),
|
| - SK_PROPERTY(step),
|
| - SK_PROPERTY(steps),
|
| - SK_PROPERTY(time)
|
| -};
|
| -
|
| -#if SK_USE_CONDENSED_INFO == 0
|
| -
|
| -// if no attibutes, enclosed displayable is both scope & target
|
| -// only if both scope & target are specified, or if target and enclosed displayable, are scope and target different
|
| -const SkMemberInfo SkApply::fInfo[] = {
|
| - SK_MEMBER_PROPERTY(animator, Animate),
|
| - SK_MEMBER(begin, MSec),
|
| - SK_MEMBER(dontDraw, Boolean),
|
| - SK_MEMBER(dynamicScope, String),
|
| - SK_MEMBER(interval, MSec), // recommended redraw interval
|
| - SK_MEMBER(mode, ApplyMode),
|
| -#if 0
|
| - SK_MEMBER(pickup, Boolean),
|
| -#endif
|
| - SK_MEMBER(restore, Boolean),
|
| - SK_MEMBER(scope, Drawable), // thing that scopes animation (unnamed enclosed displayable goes here)
|
| - SK_MEMBER_PROPERTY(step, Int),
|
| - SK_MEMBER_PROPERTY(steps, Int),
|
| - SK_MEMBER_PROPERTY(time, MSec),
|
| - SK_MEMBER(transition, ApplyTransition)
|
| -};
|
| -
|
| -#endif
|
| -
|
| -DEFINE_GET_MEMBER(SkApply);
|
| -
|
| -SkApply::SkApply() : begin(0), dontDraw(false), interval((SkMSec) -1), mode((Mode) -1), /*pickup(false), */
|
| - restore(false), scope(NULL), steps(-1), transition((Transition) -1), fActive(NULL), /*fCurrentScope(NULL),*/
|
| - fLastTime(0), fAppended(false), fContainsScope(false), fDeleteScope(false), fEmbedded(false),
|
| - fEnabled(false), fEnabling(false) {
|
| -}
|
| -
|
| -SkApply::~SkApply() {
|
| - for (SkDrawable** curPtr = fScopes.begin(); curPtr < fScopes.end(); curPtr++)
|
| - delete *curPtr;
|
| - if (fDeleteScope)
|
| - delete scope;
|
| - // !!! caller must call maker.removeActive(fActive)
|
| - delete fActive;
|
| -}
|
| -
|
| -void SkApply::activate(SkAnimateMaker& maker) {
|
| - if (fActive != NULL) {
|
| - if (fActive->fDrawIndex == 0 && fActive->fDrawMax == 0)
|
| - return; // if only one use, nothing more to do
|
| - if (restore == false)
|
| - return; // all share same state, regardless of instance number
|
| - bool save = fActive->initializeSave();
|
| - fActive->fixInterpolator(save);
|
| - } else {
|
| - fActive = new SkActive(*this, maker);
|
| - fActive->init();
|
| - maker.appendActive(fActive);
|
| - if (restore) {
|
| - fActive->initializeSave();
|
| - int animators = fAnimators.count();
|
| - for (int index = 0; index < animators; index++)
|
| - fActive->saveInterpolatorValues(index);
|
| - }
|
| - }
|
| -}
|
| -
|
| -void SkApply::append(SkApply* apply) {
|
| - if (fActive == NULL)
|
| - return;
|
| - int oldCount = fActive->fAnimators.count();
|
| - fActive->append(apply);
|
| - if (restore) {
|
| - fActive->appendSave(oldCount);
|
| - int newCount = fActive->fAnimators.count();
|
| - for (int index = oldCount; index < newCount; index++)
|
| - fActive->saveInterpolatorValues(index);
|
| - }
|
| -}
|
| -
|
| -void SkApply::applyValues(int animatorIndex, SkOperand* values, int count,
|
| - SkDisplayTypes valuesType, SkMSec time)
|
| -{
|
| - SkAnimateBase* animator = fActive->fAnimators[animatorIndex];
|
| - const SkMemberInfo * info = animator->fFieldInfo;
|
| - SkASSERT(animator);
|
| - SkASSERT(info != NULL);
|
| - SkDisplayTypes type = (SkDisplayTypes) info->fType;
|
| - SkDisplayable* target = getTarget(animator);
|
| - if (animator->hasExecute() || type == SkType_MemberFunction || type == SkType_MemberProperty) {
|
| - SkDisplayable* executor = animator->hasExecute() ? animator : target;
|
| - if (type != SkType_MemberProperty) {
|
| - SkTDArray<SkScriptValue> typedValues;
|
| - for (int index = 0; index < count; index++) {
|
| - SkScriptValue temp;
|
| - temp.fType = valuesType;
|
| - temp.fOperand = values[index];
|
| - *typedValues.append() = temp;
|
| - }
|
| - executor->executeFunction(target, info->functionIndex(), typedValues, info->getType(), NULL);
|
| - } else {
|
| - SkScriptValue scriptValue;
|
| - scriptValue.fOperand = values[0];
|
| - scriptValue.fType = info->getType();
|
| - target->setProperty(info->propertyIndex(), scriptValue);
|
| - }
|
| - } else {
|
| - SkTypedArray converted;
|
| - if (type == SkType_ARGB) {
|
| - if (count == 4) {
|
| - // !!! assert that it is SkType_Float ?
|
| - animator->packARGB(&values->fScalar, count, &converted);
|
| - values = converted.begin();
|
| - count = converted.count();
|
| - } else
|
| - SkASSERT(count == 1);
|
| - }
|
| -// SkASSERT(type == SkType_ARGB || type == SkType_String ||info->isSettable());
|
| - if (type == SkType_String || type == SkType_DynamicString)
|
| - info->setString(target, values->fString);
|
| - else if (type == SkType_Drawable || type == SkType_Displayable)
|
| - target->setReference(info, values->fDisplayable);
|
| - else
|
| - info->setValue(target, values, count);
|
| - }
|
| -}
|
| -
|
| -bool SkApply::contains(SkDisplayable* child) {
|
| - for (SkDrawable** curPtr = fScopes.begin(); curPtr < fScopes.end(); curPtr++) {
|
| - if (*curPtr == child || (*curPtr)->contains(child))
|
| - return true;
|
| - }
|
| - return fDeleteScope && scope == child;
|
| -}
|
| -
|
| -SkDisplayable* SkApply::deepCopy(SkAnimateMaker* maker) {
|
| - SkDrawable* saveScope = scope;
|
| - scope = NULL;
|
| - SkApply* result = (SkApply*) INHERITED::deepCopy(maker);
|
| - result->scope = scope = saveScope;
|
| - SkAnimateBase** end = fAnimators.end();
|
| - for (SkAnimateBase** animPtr = fAnimators.begin(); animPtr < end; animPtr++) {
|
| - SkAnimateBase* anim = (SkAnimateBase*) (*animPtr)->deepCopy(maker);
|
| - *result->fAnimators.append() = anim;
|
| - maker->helperAdd(anim);
|
| - }
|
| - return result;
|
| -}
|
| -
|
| -void SkApply::disable() {
|
| - //!!! this is the right thing to do, but has bad side effects because of other problems
|
| - // currently, if an apply is in a g and scopes a statement in another g, it ends up as members
|
| - // of both containers. The disabling here incorrectly disables both instances
|
| - // maybe the fEnabled flag needs to be moved to the fActive data so that both
|
| - // instances are not affected.
|
| -// fEnabled = false;
|
| -}
|
| -
|
| -bool SkApply::draw(SkAnimateMaker& maker) {
|
| - if (scope ==NULL)
|
| - return false;
|
| - if (scope->isApply() || scope->isDrawable() == false)
|
| - return false;
|
| - if (fEnabled == false)
|
| - enable(maker);
|
| - SkASSERT(scope);
|
| - activate(maker);
|
| - if (mode == kMode_immediate)
|
| - return fActive->draw();
|
| - bool result = interpolate(maker, maker.getInTime());
|
| - if (dontDraw == false) {
|
| -// if (scope->isDrawable())
|
| - result |= scope->draw(maker);
|
| - }
|
| - if (restore) {
|
| - for (int index = 0; index < fActive->fAnimators.count(); index++)
|
| - endSave(index);
|
| - fActive->advance();
|
| - }
|
| - return result;
|
| -}
|
| -
|
| -#ifdef SK_DUMP_ENABLED
|
| -void SkApply::dump(SkAnimateMaker* maker) {
|
| - dumpBase(maker);
|
| - if (dynamicScope.isEmpty() == false)
|
| - SkDebugf("dynamicScope=\"%s\" ", dynamicScope.c_str());
|
| - if (dontDraw)
|
| - SkDebugf("dontDraw=\"true\" ");
|
| - if (begin != 0) //perhaps we want this no matter what?
|
| - SkDebugf("begin=\"%g\" ", (float) begin/1000.0f); //is this correct?
|
| - if (interval != (SkMSec) -1)
|
| - SkDebugf("interval=\"%g\" ", (float) interval/1000.0f);
|
| - if (steps != -1)
|
| - SkDebugf("steps=\"%d\" ", steps);
|
| - if (restore)
|
| - SkDebugf("restore=\"true\" ");
|
| - if (transition == kTransition_reverse)
|
| - SkDebugf("transition=\"reverse\" ");
|
| - if (mode == kMode_immediate) {
|
| - SkDebugf("mode=\"immediate\" ");
|
| - }
|
| - else if (mode == kMode_create) {
|
| - SkDebugf("mode=\"create\" ");
|
| - }
|
| - bool closedYet = false;
|
| - SkDisplayList::fIndent += 4;
|
| - int save = SkDisplayList::fDumpIndex;
|
| - if (scope) {
|
| - if (closedYet == false) {
|
| - SkDebugf(">\n");
|
| - closedYet = true;
|
| - }
|
| - scope->dump(maker);
|
| - }
|
| - int index;
|
| -// if (fActive) {
|
| - for (index = 0; index < fAnimators.count(); index++) {
|
| - if (closedYet == false) {
|
| - SkDebugf(">\n");
|
| - closedYet = true;
|
| - }
|
| - SkAnimateBase* animator = fAnimators[index];
|
| - animator->dump(maker);
|
| -// }
|
| - }
|
| - SkDisplayList::fIndent -= 4;
|
| - SkDisplayList::fDumpIndex = save;
|
| - if (closedYet)
|
| - dumpEnd(maker);
|
| - else
|
| - SkDebugf("/>\n");
|
| -}
|
| -#endif
|
| -
|
| -bool SkApply::enable(SkAnimateMaker& maker) {
|
| - fEnabled = true;
|
| - bool initialized = fActive != NULL;
|
| - if (dynamicScope.size() > 0)
|
| - enableDynamic(maker);
|
| - if (maker.fError.hasError())
|
| - return false;
|
| - int animators = fAnimators.count();
|
| - int index;
|
| - for (index = 0; index < animators; index++) {
|
| - SkAnimateBase* animator = fAnimators[index];
|
| - animator->fStart = maker.fEnableTime;
|
| - animator->fResetPending = animator->fReset;
|
| - }
|
| - if (scope && scope->isApply())
|
| - ((SkApply*) scope)->setEmbedded();
|
| -/* if (mode == kMode_once) {
|
| - if (scope) {
|
| - activate(maker);
|
| - interpolate(maker, maker.fEnableTime);
|
| - inactivate(maker);
|
| - }
|
| - return true;
|
| - }*/
|
| - if ((mode == kMode_immediate || mode == kMode_create) && scope == NULL)
|
| - return false; // !!! error?
|
| - bool enableMe = scope && (scope->hasEnable() || scope->isApply() || scope->isDrawable() == false);
|
| - if (mode == kMode_immediate && enableMe || mode == kMode_create)
|
| - activate(maker); // for non-drawables like post, prime them here
|
| - if (mode == kMode_immediate && enableMe)
|
| - fActive->enable();
|
| - if (mode == kMode_create && scope != NULL) {
|
| - enableCreate(maker);
|
| - return true;
|
| - }
|
| - if (mode == kMode_immediate) {
|
| - return scope->isApply() || scope->isDrawable() == false;
|
| - }
|
| - refresh(maker);
|
| - SkDisplayList& displayList = maker.fDisplayList;
|
| - SkDrawable* drawable;
|
| -#if defined SK_DEBUG && defined SK_DEBUG_ANIMATION_TIMING
|
| - SkString debugOut;
|
| - SkMSec time = maker.getAppTime();
|
| - debugOut.appendS32(time - maker.fDebugTimeBase);
|
| - debugOut.append(" apply enable id=");
|
| - debugOut.append(_id);
|
| - debugOut.append("; start=");
|
| - debugOut.appendS32(maker.fEnableTime - maker.fDebugTimeBase);
|
| - SkDebugf("%s\n", debugOut.c_str());
|
| -#endif
|
| - if (scope == NULL || scope->isApply() || scope->getType() == SkType_Movie || scope->isDrawable() == false) {
|
| - activate(maker); // for non-drawables like post, prime them here
|
| - if (initialized) {
|
| - append(this);
|
| - }
|
| - fEnabling = true;
|
| - interpolate(maker, maker.fEnableTime);
|
| - fEnabling = false;
|
| - if (scope != NULL && dontDraw == false)
|
| - scope->enable(maker);
|
| - return true;
|
| - } else if (initialized && restore == false)
|
| - append(this);
|
| -#if 0
|
| - bool wasActive = inactivate(maker); // start fresh
|
| - if (wasActive) {
|
| - activate(maker);
|
| - interpolate(maker, maker.fEnableTime);
|
| - return true;
|
| - }
|
| -#endif
|
| -// start here;
|
| - // now that one apply might embed another, only the parent apply should replace the scope
|
| - // or get appended to the display list
|
| - // similarly, an apply added by an add immediate has already been located in the display list
|
| - // and should not get moved or added again here
|
| - if (fEmbedded) {
|
| - return false; // already added to display list by embedder
|
| - }
|
| - drawable = (SkDrawable*) scope;
|
| - SkTDDrawableArray* parentList;
|
| - SkTDDrawableArray* grandList;
|
| - SkGroup* parentGroup;
|
| - SkGroup* thisGroup;
|
| - int old = displayList.findGroup(drawable, &parentList, &parentGroup, &thisGroup, &grandList);
|
| - if (old < 0)
|
| - goto append;
|
| - else if (fContainsScope) {
|
| - if ((*parentList)[old] != this || restore == true) {
|
| -append:
|
| - if (parentGroup)
|
| - parentGroup->markCopySize(old);
|
| - if (parentList->count() < 10000) {
|
| - fAppended = true;
|
| - *parentList->append() = this;
|
| - } else
|
| - maker.setErrorCode(SkDisplayXMLParserError::kDisplayTreeTooDeep);
|
| - old = -1;
|
| - } else
|
| - reset();
|
| - } else {
|
| - SkASSERT(old < parentList->count());
|
| - if ((*parentList)[old]->isApply()) {
|
| - SkApply* apply = (SkApply*) (*parentList)[old];
|
| - if (apply != this && apply->fActive == NULL)
|
| - apply->activate(maker);
|
| - apply->append(this);
|
| - parentGroup = NULL;
|
| - } else {
|
| - if (parentGroup)
|
| - parentGroup->markCopySize(old);
|
| - SkDrawable** newApplyLocation = &(*parentList)[old];
|
| - SkGroup* pGroup;
|
| - int oldApply = displayList.findGroup(this, &parentList, &pGroup, &thisGroup, &grandList);
|
| - if (oldApply >= 0) {
|
| - (*parentList)[oldApply] = (SkDrawable*) SkDisplayType::CreateInstance(&maker, SkType_Apply);
|
| - parentGroup = NULL;
|
| - fDeleteScope = true;
|
| - }
|
| - *newApplyLocation = this;
|
| - }
|
| - }
|
| - if (parentGroup) {
|
| - parentGroup->markCopySet(old);
|
| - fDeleteScope = dynamicScope.size() == 0;
|
| - }
|
| - return true;
|
| -}
|
| -
|
| -void SkApply::enableCreate(SkAnimateMaker& maker) {
|
| - SkString newID;
|
| - for (int step = 0; step <= steps; step++) {
|
| - fLastTime = step * SK_MSec1;
|
| - bool success = maker.computeID(scope, this, &newID);
|
| - if (success == false)
|
| - return;
|
| - if (maker.find(newID.c_str(), NULL))
|
| - continue;
|
| - SkApply* copy = (SkApply*) deepCopy(&maker); // work on copy of animator state
|
| - if (mode == kMode_create)
|
| - copy->mode = (Mode) -1;
|
| - SkDrawable* copyScope = copy->scope = (SkDrawable*) scope->deepCopy(&maker);
|
| - *fScopes.append() = copyScope;
|
| - if (copyScope->resolveIDs(maker, scope, this)) {
|
| - step = steps; // quit
|
| - goto next; // resolveIDs failed
|
| - }
|
| - if (newID.size() > 0)
|
| - maker.setID(copyScope, newID);
|
| - if (copy->resolveIDs(maker, this, this)) { // fix up all fields, including target
|
| - step = steps; // quit
|
| - goto next; // resolveIDs failed
|
| - }
|
| - copy->activate(maker);
|
| - copy->interpolate(maker, step * SK_MSec1);
|
| - maker.removeActive(copy->fActive);
|
| - next:
|
| - delete copy;
|
| - }
|
| -}
|
| -
|
| -void SkApply::enableDynamic(SkAnimateMaker& maker) {
|
| - SkASSERT(mode != kMode_create); // create + dynamic are not currently compatible
|
| - SkDisplayable* newScope;
|
| - bool success = SkAnimatorScript::EvaluateDisplayable(maker, this, dynamicScope.c_str(),
|
| - &newScope);
|
| - if (success && scope != newScope) {
|
| - SkTDDrawableArray* pList, * gList;
|
| - SkGroup* pGroup = NULL, * found = NULL;
|
| - int old = maker.fDisplayList.findGroup(scope, &pList, &pGroup, &found, &gList);
|
| - if (pList && old >= 0 && (*pList)[old]->isApply() && (*pList)[old] != this) {
|
| - if (fAppended == false) {
|
| - if (found != NULL) {
|
| - SkDisplayable* oldChild = (*pList)[old];
|
| - if (oldChild->isApply() && found->copySet(old)) {
|
| - found->markCopyClear(old);
|
| - // delete oldChild;
|
| - }
|
| - }
|
| - (*pList)[old] = scope;
|
| - } else
|
| - pList->remove(old);
|
| - }
|
| - scope = (SkDrawable*) newScope;
|
| - onEndElement(maker);
|
| - }
|
| - maker.removeActive(fActive);
|
| - delete fActive;
|
| - fActive = NULL;
|
| -}
|
| -
|
| -void SkApply::endSave(int index) {
|
| - SkAnimateBase* animate = fActive->fAnimators[index];
|
| - const SkMemberInfo* info = animate->fFieldInfo;
|
| - SkDisplayTypes type = (SkDisplayTypes) info->fType;
|
| - if (type == SkType_MemberFunction)
|
| - return;
|
| - SkDisplayable* target = getTarget(animate);
|
| - size_t size = info->getSize(target);
|
| - int count = (int) (size / sizeof(SkScalar));
|
| - int activeIndex = fActive->fDrawIndex + index;
|
| - SkOperand* last = new SkOperand[count];
|
| - SkAutoTDelete<SkOperand> autoLast(last);
|
| - if (type != SkType_MemberProperty) {
|
| - info->getValue(target, last, count);
|
| - SkOperand* saveOperand = fActive->fSaveRestore[activeIndex];
|
| - if (saveOperand)
|
| - info->setValue(target, fActive->fSaveRestore[activeIndex], count);
|
| - } else {
|
| - SkScriptValue scriptValue;
|
| - bool success = target->getProperty(info->propertyIndex(), &scriptValue);
|
| - SkASSERT(success = true);
|
| - last[0] = scriptValue.fOperand;
|
| - scriptValue.fOperand = fActive->fSaveRestore[activeIndex][0];
|
| - target->setProperty(info->propertyIndex(), scriptValue);
|
| - }
|
| - SkOperand* save = fActive->fSaveRestore[activeIndex];
|
| - if (save)
|
| - memcpy(save, last, count * sizeof(SkOperand));
|
| -}
|
| -
|
| -bool SkApply::getProperty(int index, SkScriptValue* value) const {
|
| - switch (index) {
|
| - case SK_PROPERTY(step):
|
| - value->fType = SkType_Int;
|
| - value->fOperand.fS32 = fLastTime / SK_MSec1;
|
| - break;
|
| - case SK_PROPERTY(steps):
|
| - value->fType = SkType_Int;
|
| - value->fOperand.fS32 = steps;
|
| - break;
|
| - case SK_PROPERTY(time):
|
| - value->fType = SkType_MSec;
|
| - value->fOperand.fS32 = fLastTime;
|
| - break;
|
| - default:
|
| - // SkASSERT(0);
|
| - return false;
|
| - }
|
| - return true;
|
| -}
|
| -
|
| -void SkApply::getStep(SkScriptValue* value) {
|
| - getProperty(SK_PROPERTY(step), value);
|
| -}
|
| -
|
| -SkDrawable* SkApply::getTarget(SkAnimateBase* animate) {
|
| - if (animate->fTargetIsScope == false || mode != kMode_create)
|
| - return animate->fTarget;
|
| - return scope;
|
| -}
|
| -
|
| -bool SkApply::hasDelayedAnimator() const {
|
| - SkAnimateBase** animEnd = fAnimators.end();
|
| - for (SkAnimateBase** animPtr = fAnimators.begin(); animPtr < animEnd; animPtr++) {
|
| - SkAnimateBase* animator = *animPtr;
|
| - if (animator->fDelayed)
|
| - return true;
|
| - }
|
| - return false;
|
| -}
|
| -
|
| -bool SkApply::hasEnable() const {
|
| - return true;
|
| -}
|
| -
|
| -bool SkApply::inactivate(SkAnimateMaker& maker) {
|
| - if (fActive == NULL)
|
| - return false;
|
| - maker.removeActive(fActive);
|
| - delete fActive;
|
| - fActive = NULL;
|
| - return true;
|
| -}
|
| -
|
| -#ifdef SK_DEBUG
|
| -SkMSec lastTime = (SkMSec) -1;
|
| -#endif
|
| -
|
| -bool SkApply::interpolate(SkAnimateMaker& maker, SkMSec rawTime) {
|
| - if (fActive == NULL)
|
| - return false;
|
| - bool result = false;
|
| -#if defined SK_DEBUG && defined SK_DEBUG_ANIMATION_TIMING
|
| - SkMSec time = maker.getAppTime();
|
| - if (lastTime == (SkMSec) -1)
|
| - lastTime = rawTime - 1;
|
| - if (fActive != NULL &&
|
| - strcmp(id, "a3") == 0 && rawTime > lastTime) {
|
| - lastTime += 1000;
|
| - SkString debugOut;
|
| - debugOut.appendS32(time - maker.fDebugTimeBase);
|
| - debugOut.append(" apply id=");
|
| - debugOut.append(_id);
|
| - debugOut.append("; ");
|
| - debugOut.append(fActive->fAnimators[0]->_id);
|
| - debugOut.append("=");
|
| - debugOut.appendS32(rawTime - fActive->fState[0].fStartTime);
|
| - debugOut.append(")");
|
| - SkDebugf("%s\n", debugOut.c_str());
|
| - }
|
| -#endif
|
| - fActive->start();
|
| - if (restore)
|
| - fActive->initializeSave();
|
| - int animators = fActive->fAnimators.count();
|
| - for (int inner = 0; inner < animators; inner++) {
|
| - SkAnimateBase* animate = fActive->fAnimators[inner];
|
| - if (animate->fChanged) {
|
| - animate->fChanged = false;
|
| - animate->fStart = rawTime;
|
| - // SkTypedArray values;
|
| - // int count = animate->fValues.count();
|
| - // values.setCount(count);
|
| - // memcpy(values.begin(), animate->fValues.begin(), sizeof(SkOperand) * count);
|
| - animate->onEndElement(maker);
|
| - // if (memcmp(values.begin(), animate->fValues.begin(), sizeof(SkOperand) * count) != 0) {
|
| - fActive->append(this);
|
| - fActive->start();
|
| - // }
|
| - }
|
| - SkMSec time = fActive->getTime(rawTime, inner);
|
| - SkActive::SkState& state = fActive->fState[inner];
|
| - if (SkMSec_LT(rawTime, state.fStartTime)) {
|
| - if (fEnabling) {
|
| - animate->fDelayed = true;
|
| - maker.delayEnable(this, state.fStartTime);
|
| - }
|
| - continue;
|
| - } else
|
| - animate->fDelayed = false;
|
| - SkMSec innerTime = fLastTime = state.getRelativeTime(time);
|
| - if (restore)
|
| - fActive->restoreInterpolatorValues(inner);
|
| - if (animate->fReset) {
|
| - if (transition != SkApply::kTransition_reverse) {
|
| - if (SkMSec_LT(state.fBegin + state.fDuration, innerTime)) {
|
| - if (animate->fResetPending) {
|
| - innerTime = 0;
|
| - animate->fResetPending = false;
|
| - } else
|
| - continue;
|
| - }
|
| - } else if (innerTime == 0) {
|
| - if (animate->fResetPending) {
|
| - innerTime = state.fBegin + state.fDuration;
|
| - animate->fResetPending = false;
|
| - } else
|
| - continue;
|
| - }
|
| - }
|
| - int count = animate->components();
|
| - SkAutoSTMalloc<16, SkOperand> values(count);
|
| - SkInterpolatorBase::Result interpResult = fActive->fInterpolators[inner]->timeToValues(
|
| - innerTime, values.get());
|
| - result |= (interpResult != SkInterpolatorBase::kFreezeEnd_Result);
|
| - if ((transition != SkApply::kTransition_reverse && interpResult == SkInterpolatorBase::kFreezeEnd_Result ||
|
| - transition == SkApply::kTransition_reverse && fLastTime == 0) && state.fUnpostedEndEvent) {
|
| -// SkDEBUGF(("interpolate: post on end\n"));
|
| - state.fUnpostedEndEvent = false;
|
| - maker.postOnEnd(animate, state.fBegin + state.fDuration);
|
| - maker.fAdjustedStart = 0; // !!! left over from synchronizing animation days, undoubtably out of date (and broken)
|
| - }
|
| - if (animate->formula.size() > 0) {
|
| - if (fLastTime > animate->dur)
|
| - fLastTime = animate->dur;
|
| - SkTypedArray formulaValues;
|
| - formulaValues.setCount(count);
|
| - bool success = animate->fFieldInfo->setValue(maker, &formulaValues, 0, 0, NULL,
|
| - animate->getValuesType(), animate->formula);
|
| - SkASSERT(success);
|
| - if (restore)
|
| - save(inner); // save existing value
|
| - applyValues(inner, formulaValues.begin(), count, animate->getValuesType(), innerTime);
|
| - } else {
|
| - if (restore)
|
| - save(inner); // save existing value
|
| - applyValues(inner, values.get(), count, animate->getValuesType(), innerTime);
|
| - }
|
| - }
|
| - return result;
|
| -}
|
| -
|
| -void SkApply::initialize() {
|
| - if (scope == NULL)
|
| - return;
|
| - if (scope->isApply() || scope->isDrawable() == false)
|
| - return;
|
| - scope->initialize();
|
| -}
|
| -
|
| -void SkApply::onEndElement(SkAnimateMaker& maker)
|
| -{
|
| - SkDrawable* scopePtr = scope;
|
| - while (scopePtr && scopePtr->isApply()) {
|
| - SkApply* scopedApply = (SkApply*) scopePtr;
|
| - if (scopedApply->scope == this) {
|
| - maker.setErrorCode(SkDisplayXMLParserError::kApplyScopesItself);
|
| - return;
|
| - }
|
| - scopePtr = scopedApply->scope;
|
| - }
|
| - if (mode == kMode_create)
|
| - return;
|
| - if (scope != NULL && steps >= 0 && scope->isApply() == false && scope->isDrawable())
|
| - scope->setSteps(steps);
|
| - for (SkAnimateBase** animPtr = fAnimators.begin(); animPtr < fAnimators.end(); animPtr++) {
|
| - SkAnimateBase* anim = *animPtr;
|
| - //for reusing apply statements with dynamic scope
|
| - if (anim->fTarget == NULL || anim->fTargetIsScope) {
|
| - anim->fTargetIsScope = true;
|
| - if (scope)
|
| - anim->fTarget = scope;
|
| - else
|
| - anim->setTarget(maker);
|
| - anim->onEndElement(maker); // allows animate->fFieldInfo to be set
|
| - }
|
| - if (scope != NULL && steps >= 0 && anim->fTarget != scope && anim->fTarget->isDrawable())
|
| - anim->fTarget->setSteps(steps);
|
| - }
|
| -}
|
| -
|
| -const SkMemberInfo* SkApply::preferredChild(SkDisplayTypes type) {
|
| - SkASSERT(SkDisplayType::IsAnimate(type) == false);
|
| - fContainsScope = true;
|
| - return getMember("scope"); // !!! cwap! need to refer to member through enum like kScope instead
|
| -}
|
| -
|
| -void SkApply::refresh(SkAnimateMaker& maker) {
|
| - for (SkAnimateBase** animPtr = fAnimators.begin(); animPtr < fAnimators.end(); animPtr++) {
|
| - SkAnimateBase* animate = *animPtr;
|
| - animate->onEndElement(maker);
|
| - }
|
| - if (fActive)
|
| - fActive->resetInterpolators();
|
| -}
|
| -
|
| -void SkApply::reset() {
|
| - if (fActive)
|
| - fActive->resetState();
|
| -}
|
| -
|
| -bool SkApply::resolveIDs(SkAnimateMaker& maker, SkDisplayable* original, SkApply* apply) { // replace to/formula strings in animators of the form xxx.step with the step value, if xxx.step is in scope
|
| - if (resolveField(maker, apply, &dynamicScope) == false)
|
| - return true; // failed
|
| - SkAnimateBase** endPtr = fAnimators.end();
|
| - SkAnimateBase** origPtr = ((SkApply*) original)->fAnimators.begin();
|
| - for (SkAnimateBase** animPtr = fAnimators.begin(); animPtr < endPtr; ) {
|
| - SkAnimateBase* animator = *animPtr++;
|
| - maker.resolveID(animator, *origPtr++);
|
| - if (resolveField(maker, this, &animator->target) == false)
|
| - return true;
|
| - if (resolveField(maker, this, &animator->from) == false)
|
| - return true;
|
| - if (resolveField(maker, this, &animator->to) == false)
|
| - return true;
|
| - if (resolveField(maker, this, &animator->formula) == false)
|
| - return true;
|
| - }
|
| -// setEmbedded();
|
| - onEndElement(maker);
|
| - return false; // succeeded
|
| -}
|
| -
|
| -bool SkApply::resolveField(SkAnimateMaker& maker, SkDisplayable* parent, SkString* str) {
|
| - const char* script = str->c_str();
|
| - if (str->startsWith("#string:") == false)
|
| - return true;
|
| - script += sizeof("#string:") - 1;
|
| - return SkAnimatorScript::EvaluateString(maker, this, parent, script, str);
|
| -}
|
| -
|
| -void SkApply::save(int index) {
|
| - SkAnimateBase* animate = fActive->fAnimators[index];
|
| - const SkMemberInfo * info = animate->fFieldInfo;
|
| - SkDisplayable* target = getTarget(animate);
|
| -// if (animate->hasExecute())
|
| -// info = animate->getResolvedInfo();
|
| - SkDisplayTypes type = (SkDisplayTypes) info->fType;
|
| - if (type == SkType_MemberFunction)
|
| - return; // nothing to save
|
| - size_t size = info->getSize(target);
|
| - int count = (int) (size / sizeof(SkScalar));
|
| - bool useLast = true;
|
| -// !!! this all may be unneeded, at least in the dynamic case ??
|
| - int activeIndex = fActive->fDrawIndex + index;
|
| - SkTDOperandArray last;
|
| - if (fActive->fSaveRestore[activeIndex] == NULL) {
|
| - fActive->fSaveRestore[activeIndex] = new SkOperand[count];
|
| - useLast = false;
|
| - } else {
|
| - last.setCount(count);
|
| - memcpy(last.begin(), fActive->fSaveRestore[activeIndex], count * sizeof(SkOperand));
|
| - }
|
| - if (type != SkType_MemberProperty) {
|
| - info->getValue(target, fActive->fSaveRestore[activeIndex], count);
|
| - if (useLast)
|
| - info->setValue(target, last.begin(), count);
|
| - } else {
|
| - SkScriptValue scriptValue;
|
| - bool success = target->getProperty(info->propertyIndex(), &scriptValue);
|
| - SkASSERT(success == true);
|
| - SkASSERT(scriptValue.fType == SkType_Float);
|
| - fActive->fSaveRestore[activeIndex][0] = scriptValue.fOperand;
|
| - if (useLast) {
|
| - SkScriptValue scriptValue;
|
| - scriptValue.fType = type;
|
| - scriptValue.fOperand = last[0];
|
| - target->setProperty(info->propertyIndex(), scriptValue);
|
| - }
|
| - }
|
| -// !!! end of unneeded
|
| -}
|
| -
|
| -bool SkApply::setProperty(int index, SkScriptValue& scriptValue) {
|
| - switch (index) {
|
| - case SK_PROPERTY(animator): {
|
| - SkAnimateBase* animate = (SkAnimateBase*) scriptValue.fOperand.fDisplayable;
|
| - SkASSERT(animate->isAnimate());
|
| - *fAnimators.append() = animate;
|
| - return true;
|
| - }
|
| - case SK_PROPERTY(steps):
|
| - steps = scriptValue.fOperand.fS32;
|
| - if (fActive)
|
| - fActive->setSteps(steps);
|
| - return true;
|
| - }
|
| - return false;
|
| -}
|
| -
|
| -void SkApply::setSteps(int _steps) {
|
| - steps = _steps;
|
| -}
|
| -
|
| -#ifdef SK_DEBUG
|
| -void SkApply::validate() {
|
| - if (fActive)
|
| - fActive->validate();
|
| -}
|
| -#endif
|
| -
|
| -
|
| -
|
|
|