Index: Source/core/svg/animation/SVGSMILElement.cpp |
diff --git a/Source/core/svg/animation/SVGSMILElement.cpp b/Source/core/svg/animation/SVGSMILElement.cpp |
index c229f9544fca5d9521fe688681fd058adececdc4..c79205efa8d1ddae12bcac2561ba8e6803b2673a 100644 |
--- a/Source/core/svg/animation/SVGSMILElement.cpp |
+++ b/Source/core/svg/animation/SVGSMILElement.cpp |
@@ -31,6 +31,7 @@ |
#include "bindings/v8/ExceptionStatePlaceholder.h" |
#include "core/dom/Document.h" |
#include "core/dom/EventListener.h" |
+#include "core/dom/EventSender.h" |
#include "core/platform/FloatConversion.h" |
#include "core/svg/SVGDocumentExtensions.h" |
#include "core/svg/SVGSVGElement.h" |
@@ -44,6 +45,12 @@ using namespace std; |
namespace WebCore { |
+static SMILEventSender& smilEndEventSender() |
+{ |
+ DEFINE_STATIC_LOCAL(SMILEventSender, sender, ("endEvent")); |
+ return sender; |
+} |
+ |
// This is used for duration type time values that can't be negative. |
static const double invalidCachedTime = -1.; |
@@ -133,6 +140,7 @@ SVGSMILElement::SVGSMILElement(const QualifiedName& tagName, Document* doc) |
SVGSMILElement::~SVGSMILElement() |
{ |
clearResourceReferences(); |
+ smilEndEventSender().cancelEvent(this); |
disconnectConditions(); |
if (m_timeContainer && m_targetElement && hasValidAttributeName()) |
m_timeContainer->unschedule(this, m_targetElement, m_attributeName); |
@@ -1051,9 +1059,6 @@ bool SVGSMILElement::progress(SMILTime elapsed, SVGSMILElement* resultElement, b |
ASSERT(m_timeContainer); |
ASSERT(m_isWaitingForFirstInterval || m_intervalBegin.isFinite()); |
- if (!m_conditionsConnected) |
- connectConditions(); |
- |
if (!m_intervalBegin.isFinite()) { |
ASSERT(m_activeState == Inactive); |
m_nextProgressTime = SMILTime::unresolved(); |
@@ -1110,11 +1115,18 @@ bool SVGSMILElement::progress(SMILTime elapsed, SVGSMILElement* resultElement, b |
} |
if (oldActiveState == Active && m_activeState != Active) { |
+ smilEndEventSender().dispatchEventSoon(this); |
endedActiveInterval(); |
if (m_activeState != Frozen && this == resultElement) |
clearAnimatedType(m_targetElement); |
} |
+ // Triggering all the pending events if the animation timeline is changed. |
+ if (seekToTime) { |
+ if (m_activeState == Inactive || m_activeState == Frozen) |
+ smilEndEventSender().dispatchEventSoon(this); |
+ } |
+ |
m_nextProgressTime = calculateNextProgressTime(elapsed); |
return animationIsContributing; |
} |
@@ -1191,4 +1203,11 @@ void SVGSMILElement::endedActiveInterval() |
clearTimesWithDynamicOrigins(m_endTimes); |
} |
+void SVGSMILElement::dispatchPendingEvent(SMILEventSender* eventSender) |
+{ |
+ ASSERT(eventSender == &smilEndEventSender()); |
+ const AtomicString& eventType = eventSender->eventType(); |
+ dispatchEvent(Event::create(eventType)); |
+} |
+ |
} |