From dcc00ffadf64270b0ae82431f5b71c527590e91b Mon Sep 17 00:00:00 2001 From: janekptacijarabaci Date: Wed, 14 Mar 2018 09:18:49 +0100 Subject: Bug 1264125: Queue CSS related event when setting null target effect Issue #55 --- layout/style/nsTransitionManager.cpp | 52 +++++++++++++++++++++++++++--------- layout/style/nsTransitionManager.h | 6 +++++ 2 files changed, 45 insertions(+), 13 deletions(-) (limited to 'layout/style') diff --git a/layout/style/nsTransitionManager.cpp b/layout/style/nsTransitionManager.cpp index da12a0ecd..abb9e2311 100644 --- a/layout/style/nsTransitionManager.cpp +++ b/layout/style/nsTransitionManager.cpp @@ -182,8 +182,7 @@ CSSTransition::UpdateTiming(SeekFlag aSeekFlag, SyncNotifyFlag aSyncNotifyFlag) void CSSTransition::QueueEvents(StickyTimeDuration aActiveTime) { - if (!mEffect || - !mOwningElement.IsSet()) { + if (!mOwningElement.IsSet()) { return; } @@ -197,14 +196,27 @@ CSSTransition::QueueEvents(StickyTimeDuration aActiveTime) return; } - ComputedTiming computedTiming = mEffect->GetComputedTiming(); - const StickyTimeDuration zeroDuration; - StickyTimeDuration intervalStartTime = - std::max(std::min(StickyTimeDuration(-mEffect->SpecifiedTiming().mDelay), - computedTiming.mActiveDuration), zeroDuration); - StickyTimeDuration intervalEndTime = - std::max(std::min((EffectEnd() - mEffect->SpecifiedTiming().mDelay), - computedTiming.mActiveDuration), zeroDuration); + const StickyTimeDuration zeroDuration = StickyTimeDuration(); + + TransitionPhase currentPhase; + StickyTimeDuration intervalStartTime; + StickyTimeDuration intervalEndTime; + + if (!mEffect) { + currentPhase = GetTransitionPhaseWithoutEffect(); + intervalStartTime = zeroDuration; + intervalEndTime = zeroDuration; + } else { + ComputedTiming computedTiming = mEffect->GetComputedTiming(); + + currentPhase = static_cast(computedTiming.mPhase); + intervalStartTime = + std::max(std::min(StickyTimeDuration(-mEffect->SpecifiedTiming().mDelay), + computedTiming.mActiveDuration), zeroDuration); + intervalEndTime = + std::max(std::min((EffectEnd() - mEffect->SpecifiedTiming().mDelay), + computedTiming.mActiveDuration), zeroDuration); + } // TimeStamps to use for ordering the events when they are dispatched. We // use a TimeStamp so we can compare events produced by different elements, @@ -215,14 +227,11 @@ CSSTransition::QueueEvents(StickyTimeDuration aActiveTime) TimeStamp startTimeStamp = ElapsedTimeToTimeStamp(intervalStartTime); TimeStamp endTimeStamp = ElapsedTimeToTimeStamp(intervalEndTime); - TransitionPhase currentPhase; if (mPendingState != PendingState::NotPending && (mPreviousTransitionPhase == TransitionPhase::Idle || mPreviousTransitionPhase == TransitionPhase::Pending)) { currentPhase = TransitionPhase::Pending; - } else { - currentPhase = static_cast(computedTiming.mPhase); } AutoTArray events; @@ -320,6 +329,23 @@ CSSTransition::QueueEvents(StickyTimeDuration aActiveTime) } } +CSSTransition::TransitionPhase +CSSTransition::GetTransitionPhaseWithoutEffect() const +{ + MOZ_ASSERT(!mEffect, "Should only be called when we do not have an effect"); + + Nullable currentTime = GetCurrentTime(); + if (currentTime.IsNull()) { + return TransitionPhase::Idle; + } + + // If we don't have a target effect, the duration will be zero so the phase is + // 'before' if the current time is less than zero. + return currentTime.Value() < TimeDuration() + ? TransitionPhase::Before + : TransitionPhase::After; +} + void CSSTransition::Tick() { diff --git a/layout/style/nsTransitionManager.h b/layout/style/nsTransitionManager.h index 80042adcd..e2f198a40 100644 --- a/layout/style/nsTransitionManager.h +++ b/layout/style/nsTransitionManager.h @@ -243,6 +243,12 @@ protected: void QueueEvents(StickyTimeDuration activeTime = StickyTimeDuration()); + + enum class TransitionPhase; + // Return the TransitionPhase to use when the transition doesn't have a target + // effect. + TransitionPhase GetTransitionPhaseWithoutEffect() const; + // The (pseudo-)element whose computed transition-property refers to this // transition (if any). // -- cgit v1.2.3