Changeset 177238 in webkit
- Timestamp:
- Dec 12, 2014 2:52:36 PM (9 years ago)
- Location:
- trunk/Source/WebCore
- Files:
-
- 6 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/WebCore/ChangeLog
r177236 r177238 1 2014-12-12 Simon Fraser <simon.fraser@apple.com> 2 3 REGRESSION (r168217): Images are cropped out during animation at jetblue.com 4 https://bugs.webkit.org/show_bug.cgi?id=136410 5 rdar://problem/18188533 6 7 Reviewed by Dean Jackson. 8 9 During GraphicsLayer flushing, for tiled layers we can compute a visible rect using 10 the current state of an animation, which is obtained via the AnimationController. 11 If that animation was running in a subframe, AnimationController could use a stale 12 beginAnimationUpdateTime since no-one called its beginAnimationUpdate(). That 13 resulted in an incorrect computation of the visible rect, resulting in missing tiles. 14 15 There are two parts to this fix. First, add an assertion that beginAnimationUpdateTime() 16 is being called inside an animation update block. This required moving m_beginAnimationUpdateCount 17 into AnimationControllerPrivate, and changes to endAnimationUpdate(). 18 19 The second is adding a AnimationUpdateBlock to getAnimatedStyleForRenderer(), which 20 can be called outside of style resolution. We also need some in other API functions. 21 22 Testing revealed that layout can call via layoutOverflowRectForPropagation(), suggesting 23 that we should have an animation batch inside FrameView::layout(). In addition, a single 24 resolveStyle/layout should use the same animationBeginTime, so we add a batch to 25 updateLayoutAndStyleIfNeededRecursive(). 26 27 No test because it's timing-dependent. Existing tests exercise the new assertion. 28 29 * css/CSSComputedStyleDeclaration.cpp: 30 (WebCore::computeRenderStyleForProperty): 31 * page/FrameView.cpp: 32 (WebCore::FrameView::layout): 33 (WebCore::FrameView::updateLayoutAndStyleIfNeededRecursive): 34 * page/animation/AnimationController.cpp: 35 (WebCore::AnimationPrivateUpdateBlock::AnimationPrivateUpdateBlock): 36 (WebCore::AnimationPrivateUpdateBlock::~AnimationPrivateUpdateBlock): 37 (WebCore::AnimationControllerPrivate::AnimationControllerPrivate): 38 (WebCore::AnimationControllerPrivate::animationTimerFired): 39 (WebCore::AnimationControllerPrivate::suspendAnimationsForDocument): 40 (WebCore::AnimationControllerPrivate::resumeAnimationsForDocument): 41 (WebCore::AnimationControllerPrivate::beginAnimationUpdateTime): 42 (WebCore::AnimationControllerPrivate::beginAnimationUpdate): 43 (WebCore::AnimationControllerPrivate::endAnimationUpdate): 44 (WebCore::AnimationControllerPrivate::getAnimatedStyleForRenderer): 45 (WebCore::AnimationController::AnimationController): 46 (WebCore::AnimationController::notifyAnimationStarted): 47 (WebCore::AnimationController::pauseAnimationAtTime): 48 (WebCore::AnimationController::pauseTransitionAtTime): 49 (WebCore::AnimationController::resumeAnimationsForDocument): 50 (WebCore::AnimationController::startAnimationsIfNotSuspended): 51 (WebCore::AnimationController::beginAnimationUpdate): 52 (WebCore::AnimationController::endAnimationUpdate): 53 * page/animation/AnimationController.h: 54 * page/animation/AnimationControllerPrivate.h: 55 1 56 2014-12-12 Roger Fong <roger_fong@apple.com> 2 57 -
trunk/Source/WebCore/css/CSSComputedStyleDeclaration.cpp
r177223 r177238 1706 1706 1707 1707 if (renderer && renderer->isComposited() && AnimationController::supportsAcceleratedAnimationOfProperty(propertyID)) { 1708 AnimationUpdateBlock animationUpdateBlock(&renderer->animation());1709 1708 RefPtr<RenderStyle> style = renderer->animation().getAnimatedStyleForRenderer(downcast<RenderElement>(*renderer)); 1710 1709 if (pseudoElementSpecifier && !styledNode->isPseudoElement()) { -
trunk/Source/WebCore/page/FrameView.cpp
r177223 r177238 1154 1154 1155 1155 InspectorInstrumentationCookie cookie = InspectorInstrumentation::willLayout(&frame()); 1156 1156 AnimationUpdateBlock animationUpdateBlock(&frame().animation()); 1157 1157 1158 if (!allowSubtree && m_layoutRoot) { 1158 1159 m_layoutRoot->markContainingBlocksForLayout(false); … … 3938 3939 // when it lays out. 3939 3940 3941 AnimationUpdateBlock animationUpdateBlock(&frame().animation()); 3942 3940 3943 frame().document()->updateStyleIfNeeded(); 3941 3944 -
trunk/Source/WebCore/page/animation/AnimationController.cpp
r176459 r177238 52 52 static const double cBeginAnimationUpdateTimeNotSet = -1; 53 53 54 class AnimationPrivateUpdateBlock { 55 public: 56 AnimationPrivateUpdateBlock(AnimationControllerPrivate& animationController) 57 : m_animationController(animationController) 58 { 59 m_animationController.beginAnimationUpdate(); 60 } 61 62 ~AnimationPrivateUpdateBlock() 63 { 64 m_animationController.endAnimationUpdate(); 65 } 66 67 AnimationControllerPrivate& m_animationController; 68 }; 69 54 70 AnimationControllerPrivate::AnimationControllerPrivate(Frame& frame) 55 71 : m_animationTimer(*this, &AnimationControllerPrivate::animationTimerFired) … … 59 75 , m_animationsWaitingForStyle() 60 76 , m_animationsWaitingForStartTimeResponse() 77 , m_beginAnimationUpdateCount(0) 61 78 , m_waitingForAsyncStartNotification(false) 62 79 , m_isSuspended(false) … … 231 248 // Make sure animationUpdateTime is updated, so that it is current even if no 232 249 // styleChange has happened (e.g. accelerated animations) 233 setBeginAnimationUpdateTime(cBeginAnimationUpdateTimeNotSet);250 AnimationPrivateUpdateBlock updateBlock(*this); 234 251 235 252 // When the timer fires, all we do is call setChanged on all DOM nodes with running animations and then do an immediate … … 288 305 void AnimationControllerPrivate::suspendAnimationsForDocument(Document* document) 289 306 { 290 setBeginAnimationUpdateTime(cBeginAnimationUpdateTimeNotSet);307 AnimationPrivateUpdateBlock updateBlock(*this); 291 308 292 309 for (auto it = m_compositeAnimations.begin(), end = m_compositeAnimations.end(); it != end; ++it) { … … 300 317 void AnimationControllerPrivate::resumeAnimationsForDocument(Document* document) 301 318 { 302 setBeginAnimationUpdateTime(cBeginAnimationUpdateTimeNotSet);319 AnimationPrivateUpdateBlock updateBlock(*this); 303 320 304 321 for (auto it = m_compositeAnimations.begin(), end = m_compositeAnimations.end(); it != end; ++it) { … … 353 370 double AnimationControllerPrivate::beginAnimationUpdateTime() 354 371 { 372 ASSERT(m_beginAnimationUpdateCount); 355 373 if (m_beginAnimationUpdateTime == cBeginAnimationUpdateTimeNotSet) 356 374 m_beginAnimationUpdateTime = monotonicallyIncreasingTime(); 375 357 376 return m_beginAnimationUpdateTime; 358 377 } 359 378 379 void AnimationControllerPrivate::beginAnimationUpdate() 380 { 381 if (!m_beginAnimationUpdateCount) 382 setBeginAnimationUpdateTime(cBeginAnimationUpdateTimeNotSet); 383 ++m_beginAnimationUpdateCount; 384 } 385 360 386 void AnimationControllerPrivate::endAnimationUpdate() 361 387 { 362 styleAvailable(); 363 if (!m_waitingForAsyncStartNotification) 364 startTimeResponse(beginAnimationUpdateTime()); 388 ASSERT(m_beginAnimationUpdateCount > 0); 389 if (m_beginAnimationUpdateCount == 1) { 390 styleAvailable(); 391 if (!m_waitingForAsyncStartNotification) 392 startTimeResponse(beginAnimationUpdateTime()); 393 } 394 --m_beginAnimationUpdateCount; 365 395 } 366 396 … … 373 403 PassRefPtr<RenderStyle> AnimationControllerPrivate::getAnimatedStyleForRenderer(RenderElement& renderer) 374 404 { 405 AnimationPrivateUpdateBlock animationUpdateBlock(*this); 406 375 407 ASSERT(renderer.isCSSAnimating()); 376 408 ASSERT(m_compositeAnimations.contains(&renderer)); … … 470 502 AnimationController::AnimationController(Frame& frame) 471 503 : m_data(std::make_unique<AnimationControllerPrivate>(frame)) 472 , m_beginAnimationUpdateCount(0)473 504 { 474 505 } … … 546 577 void AnimationController::notifyAnimationStarted(RenderElement&, double startTime) 547 578 { 579 AnimationUpdateBlock animationUpdateBlock(this); 548 580 m_data->receivedStartTimeResponse(startTime); 549 581 } … … 551 583 bool AnimationController::pauseAnimationAtTime(RenderElement* renderer, const AtomicString& name, double t) 552 584 { 585 AnimationUpdateBlock animationUpdateBlock(this); 553 586 return m_data->pauseAnimationAtTime(renderer, name, t); 554 587 } … … 561 594 bool AnimationController::pauseTransitionAtTime(RenderElement* renderer, const String& property, double t) 562 595 { 596 AnimationUpdateBlock animationUpdateBlock(this); 563 597 return m_data->pauseTransitionAtTime(renderer, property, t); 564 598 } … … 617 651 { 618 652 LOG(Animations, "resuming animations for document %p", document); 653 AnimationUpdateBlock animationUpdateBlock(this); 619 654 m_data->resumeAnimationsForDocument(document); 620 655 } … … 623 658 { 624 659 LOG(Animations, "animations may start for document %p", document); 660 661 AnimationUpdateBlock animationUpdateBlock(this); 625 662 m_data->startAnimationsIfNotSuspended(document); 626 663 } … … 628 665 void AnimationController::beginAnimationUpdate() 629 666 { 630 if (!m_beginAnimationUpdateCount) 631 m_data->setBeginAnimationUpdateTime(cBeginAnimationUpdateTimeNotSet); 632 ++m_beginAnimationUpdateCount; 667 m_data->beginAnimationUpdate(); 633 668 } 634 669 635 670 void AnimationController::endAnimationUpdate() 636 671 { 637 ASSERT(m_beginAnimationUpdateCount > 0); 638 --m_beginAnimationUpdateCount; 639 if (!m_beginAnimationUpdateCount) 640 m_data->endAnimationUpdate(); 672 m_data->endAnimationUpdate(); 641 673 } 642 674 -
trunk/Source/WebCore/page/animation/AnimationController.h
r174804 r177238 83 83 private: 84 84 const std::unique_ptr<AnimationControllerPrivate> m_data; 85 int m_beginAnimationUpdateCount;86 85 }; 87 86 -
trunk/Source/WebCore/page/animation/AnimationControllerPrivate.h
r176459 r177238 98 98 double beginAnimationUpdateTime(); 99 99 void setBeginAnimationUpdateTime(double t) { m_beginAnimationUpdateTime = t; } 100 101 void beginAnimationUpdate(); 100 102 void endAnimationUpdate(); 101 103 void receivedStartTimeResponse(double); … … 142 144 WaitingAnimationsSet m_animationsWaitingForStyle; 143 145 WaitingAnimationsSet m_animationsWaitingForStartTimeResponse; 146 147 int m_beginAnimationUpdateCount; 148 144 149 bool m_waitingForAsyncStartNotification; 145 150 bool m_isSuspended;
Note: See TracChangeset
for help on using the changeset viewer.