diff options
author | jochen@chromium.org <jochen@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-07-24 07:07:14 +0000 |
---|---|---|
committer | jochen@chromium.org <jochen@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-07-24 07:07:14 +0000 |
commit | 1fc9e80dab903b1dddf3b219c9f4fb45568e090b (patch) | |
tree | d52bbd48661fcd7b0ad2b6a3c08974443fe050cb /cc | |
parent | f3d2b866af7d3fdebdfbe32ede60b8d1e2419625 (diff) | |
download | chromium_src-1fc9e80dab903b1dddf3b219c9f4fb45568e090b.zip chromium_src-1fc9e80dab903b1dddf3b219c9f4fb45568e090b.tar.gz chromium_src-1fc9e80dab903b1dddf3b219c9f4fb45568e090b.tar.bz2 |
Revert 213338 "cc: Allow the main thread to cancel commits"
Broke WebViewInteractiveTest.EditCommandsNoMenu on Mac
[1288:27139:0723/221703:FATAL:layer_impl.cc(286)] Check failed: TotalScrollOffset().y() <= max_scroll_offset_.y() (62 vs. 47)
> cc: Allow the main thread to cancel commits
>
> Add a new SetNeedsUpdateLayers that triggers the commit flow, but is
> abortable if update layers doesn't actually make any changes. This
> allows the main thread to abort a begin frame. This happens in the case
> of scroll updates from the compositor thread or invalidations.
>
> There was previously an abort begin frame call for when a visibility
> message and a begin frame message were posted simultaneously, but it
> incorrectly applied the scrolls and scales without informing the
> compositor thread that these had already been consumed. To fix this,
> the abort message passes back a boolean about whether or not the
> commit was aborted (and needed to be sent again) or was handled
> (and the scrolls and scales processed).
>
> To avoid a deluge of begin frames (in the commit sense) from the
> scheduler, the scheduler has been adjusted to wait until the next begin
> frame (in the vsync signal sense) so that these calls can be throttled.
> Otherwise, the scheduler will just keep trying to begin frame.
>
> R=brianderson@chromium.org, danakj@chromium.org
> BUG=256381
>
> Review URL: https://chromiumcodereview.appspot.com/19106007
TBR=enne@chromium.org
Review URL: https://codereview.chromium.org/19519019
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@213355 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'cc')
34 files changed, 114 insertions, 581 deletions
diff --git a/cc/layers/layer.cc b/cc/layers/layer.cc index 156e475..3437d86 100644 --- a/cc/layers/layer.cc +++ b/cc/layers/layer.cc @@ -121,11 +121,6 @@ void Layer::SetLayerTreeHost(LayerTreeHost* host) { layer_tree_host_->set_needs_filter_context(); } -void Layer::SetNeedsUpdate() { - if (layer_tree_host_ && !ignore_set_needs_commit_) - layer_tree_host_->SetNeedsUpdateLayers(); -} - void Layer::SetNeedsCommit() { if (!layer_tree_host_) return; @@ -568,17 +563,14 @@ void Layer::SetScrollOffset(gfx::Vector2d scroll_offset) { void Layer::SetScrollOffsetFromImplSide(gfx::Vector2d scroll_offset) { DCHECK(IsPropertyChangeAllowed()); - // This function only gets called during a begin frame, so there - // is no need to call SetNeedsUpdate here. DCHECK(layer_tree_host_ && layer_tree_host_->CommitRequested()); if (scroll_offset_ == scroll_offset) return; scroll_offset_ = scroll_offset; - SetNeedsPushProperties(); if (!did_scroll_callback_.is_null()) did_scroll_callback_.Run(); - // The callback could potentially change the layer structure: - // "this" may have been destroyed during the process. + // Note: didScroll() could potentially change the layer structure. + // "this" may have been destroyed during the process. } void Layer::SetMaxScrollOffset(gfx::Vector2d max_scroll_offset) { @@ -671,16 +663,14 @@ void Layer::SetHideLayerAndSubtree(bool hide) { } void Layer::SetNeedsDisplayRect(const gfx::RectF& dirty_rect) { - if (!update_rect_.Contains(dirty_rect)) { - SetNeedsPushProperties(); - } - update_rect_.Union(dirty_rect); needs_display_ = true; - if (DrawsContent() && !update_rect_.IsEmpty()) { - SetNeedsUpdate(); - } + // Simply mark the contents as dirty. For non-root layers, the call to + // SetNeedsCommit will schedule a fresh compositing pass. + // For the root layer, SetNeedsCommit has no effect. + if (DrawsContent() && !update_rect_.IsEmpty()) + SetNeedsCommit(); } bool Layer::DescendantIsFixedToContainerLayer() const { diff --git a/cc/layers/layer.h b/cc/layers/layer.h index 3f76a9b..76c4899 100644 --- a/cc/layers/layer.h +++ b/cc/layers/layer.h @@ -393,18 +393,7 @@ class CC_EXPORT Layer : public base::RefCounted<Layer>, Layer(); - // These SetNeeds functions are in order of severity of update: - // - // Called when this layer has been modified in some way, but isn't sure - // that it needs a commit yet. It needs CalcDrawProperties and UpdateLayers - // before it knows whether or not a commit is required. - void SetNeedsUpdate(); - // Called when a property has been modified in a way that the layer - // knows immediately that a commit is required. This implies SetNeedsUpdate - // as well as SetNeedsPushProperties to push that property. void SetNeedsCommit(); - // Called when there's been a change in layer structure. Implies both - // SetNeedsUpdate and SetNeedsCommit, but not SetNeedsPushProperties. void SetNeedsFullTreeSync(); bool IsPropertyChangeAllowed() const; @@ -445,7 +434,7 @@ class CC_EXPORT Layer : public base::RefCounted<Layer>, int layer_id_; // When true, the layer is about to perform an update. Any commit requests - // will be handled implicitly after the update completes. + // will be handled implcitly after the update completes. bool ignore_set_needs_commit_; private: diff --git a/cc/layers/layer_impl.cc b/cc/layers/layer_impl.cc index 33d5c04..4865fe2 100644 --- a/cc/layers/layer_impl.cc +++ b/cc/layers/layer_impl.cc @@ -270,22 +270,6 @@ gfx::Vector2dF LayerImpl::ScrollBy(gfx::Vector2dF scroll) { return unscrolled; } -void LayerImpl::ApplySentScrollDeltas() { - // Pending tree never has sent scroll deltas - DCHECK(layer_tree_impl()->IsActiveTree()); - - // Apply sent scroll deltas to scroll position / scroll delta as if the - // main thread had applied them and then committed those values. - scroll_offset_ += sent_scroll_delta_; - scroll_delta_ -= sent_scroll_delta_; - sent_scroll_delta_ = gfx::Vector2d(); - - DCHECK_GE(TotalScrollOffset().x(), 0); - DCHECK_GE(TotalScrollOffset().y(), 0); - DCHECK_LE(TotalScrollOffset().x(), max_scroll_offset_.x()); - DCHECK_LE(TotalScrollOffset().y(), max_scroll_offset_.y()); -} - InputHandler::ScrollStatus LayerImpl::TryScroll( gfx::PointF screen_space_point, InputHandler::ScrollInputType type) const { diff --git a/cc/layers/layer_impl.h b/cc/layers/layer_impl.h index 90da41a..ff7e956 100644 --- a/cc/layers/layer_impl.h +++ b/cc/layers/layer_impl.h @@ -330,8 +330,6 @@ class CC_EXPORT LayerImpl : LayerAnimationValueObserver { void SetScrollable(bool scrollable) { scrollable_ = scrollable; } bool scrollable() const { return scrollable_; } - void ApplySentScrollDeltas(); - void SetShouldScrollOnMainThread(bool should_scroll_on_main_thread) { should_scroll_on_main_thread_ = should_scroll_on_main_thread; } diff --git a/cc/layers/layer_unittest.cc b/cc/layers/layer_unittest.cc index b7fa166..fb3a752 100644 --- a/cc/layers/layer_unittest.cc +++ b/cc/layers/layer_unittest.cc @@ -44,7 +44,6 @@ class MockLayerTreeHost : public LayerTreeHost { } MOCK_METHOD0(SetNeedsCommit, void()); - MOCK_METHOD0(SetNeedsUpdateLayers, void()); MOCK_METHOD0(SetNeedsFullTreeSync, void()); }; @@ -447,7 +446,7 @@ TEST_F(LayerTest, GetRootLayerAfterTreeManipulations) { TEST_F(LayerTest, CheckSetNeedsDisplayCausesCorrectBehavior) { // The semantics for SetNeedsDisplay which are tested here: // 1. sets NeedsDisplay flag appropriately. - // 2. indirectly calls SetNeedsUpdate, exactly once for each call to + // 2. indirectly calls SetNeedsCommit, exactly once for each call to // SetNeedsDisplay. scoped_refptr<Layer> test_layer = Layer::Create(); @@ -477,7 +476,7 @@ TEST_F(LayerTest, CheckSetNeedsDisplayCausesCorrectBehavior) { // Case 1: Layer should accept dirty rects that go beyond its bounds. test_layer->ResetNeedsDisplayForTesting(); EXPECT_FALSE(test_layer->NeedsDisplayForTesting()); - EXPECT_SET_NEEDS_UPDATE( + EXPECT_SET_NEEDS_COMMIT( 1, test_layer->SetNeedsDisplayRect(out_of_bounds_dirty_rect)); EXPECT_TRUE(test_layer->NeedsDisplayForTesting()); test_layer->ResetNeedsDisplayForTesting(); @@ -485,7 +484,7 @@ TEST_F(LayerTest, CheckSetNeedsDisplayCausesCorrectBehavior) { // Case 2: SetNeedsDisplay() without the dirty rect arg. test_layer->ResetNeedsDisplayForTesting(); EXPECT_FALSE(test_layer->NeedsDisplayForTesting()); - EXPECT_SET_NEEDS_UPDATE(1, test_layer->SetNeedsDisplay()); + EXPECT_SET_NEEDS_COMMIT(1, test_layer->SetNeedsDisplay()); EXPECT_TRUE(test_layer->NeedsDisplayForTesting()); test_layer->ResetNeedsDisplayForTesting(); @@ -493,7 +492,7 @@ TEST_F(LayerTest, CheckSetNeedsDisplayCausesCorrectBehavior) { EXPECT_SET_NEEDS_COMMIT(1, test_layer->SetIsDrawable(false)); test_layer->ResetNeedsDisplayForTesting(); EXPECT_FALSE(test_layer->NeedsDisplayForTesting()); - EXPECT_SET_NEEDS_UPDATE(0, test_layer->SetNeedsDisplayRect(dirty1)); + EXPECT_SET_NEEDS_COMMIT(0, test_layer->SetNeedsDisplayRect(dirty1)); EXPECT_TRUE(test_layer->NeedsDisplayForTesting()); } diff --git a/cc/layers/texture_layer_unittest.cc b/cc/layers/texture_layer_unittest.cc index 2d39dab..f4482ac 100644 --- a/cc/layers/texture_layer_unittest.cc +++ b/cc/layers/texture_layer_unittest.cc @@ -38,7 +38,6 @@ class MockLayerTreeHost : public LayerTreeHost { MOCK_METHOD0(AcquireLayerTextures, void()); MOCK_METHOD0(SetNeedsCommit, void()); - MOCK_METHOD0(SetNeedsUpdateLayers, void()); MOCK_METHOD1(StartRateLimiter, void(WebKit::WebGraphicsContext3D* context)); MOCK_METHOD1(StopRateLimiter, void(WebKit::WebGraphicsContext3D* context)); }; @@ -119,7 +118,7 @@ TEST_F(TextureLayerTest, SyncImplWhenDrawing) { Mock::VerifyAndClearExpectations(layer_tree_host_.get()); EXPECT_CALL(*layer_tree_host_, AcquireLayerTextures()).Times(0); - EXPECT_CALL(*layer_tree_host_, SetNeedsUpdateLayers()).Times(1); + EXPECT_CALL(*layer_tree_host_, SetNeedsCommit()).Times(1); test_layer->SetNeedsDisplayRect(dirty_rect); Mock::VerifyAndClearExpectations(layer_tree_host_.get()); diff --git a/cc/scheduler/scheduler.cc b/cc/scheduler/scheduler.cc index 010cc99..5e397bd 100644 --- a/cc/scheduler/scheduler.cc +++ b/cc/scheduler/scheduler.cc @@ -85,9 +85,9 @@ void Scheduler::FinishCommit() { ProcessScheduledActions(); } -void Scheduler::BeginFrameAbortedByMainThread(bool did_handle) { +void Scheduler::BeginFrameAbortedByMainThread() { TRACE_EVENT0("cc", "Scheduler::BeginFrameAbortedByMainThread"); - state_machine_.BeginFrameAbortedByMainThread(did_handle); + state_machine_.BeginFrameAbortedByMainThread(); ProcessScheduledActions(); } diff --git a/cc/scheduler/scheduler.h b/cc/scheduler/scheduler.h index 230f20d..48a3bb2 100644 --- a/cc/scheduler/scheduler.h +++ b/cc/scheduler/scheduler.h @@ -86,7 +86,7 @@ class CC_EXPORT Scheduler { void DidSwapUseIncompleteTile(); void FinishCommit(); - void BeginFrameAbortedByMainThread(bool did_handle); + void BeginFrameAbortedByMainThread(); void DidLoseOutputSurface(); void DidCreateAndInitializeOutputSurface(); diff --git a/cc/scheduler/scheduler_state_machine.cc b/cc/scheduler/scheduler_state_machine.cc index 94100b8..eed9f15 100644 --- a/cc/scheduler/scheduler_state_machine.cc +++ b/cc/scheduler/scheduler_state_machine.cc @@ -15,7 +15,6 @@ SchedulerStateMachine::SchedulerStateMachine(const SchedulerSettings& settings) commit_state_(COMMIT_STATE_IDLE), commit_count_(0), current_frame_number_(0), - last_frame_number_where_begin_frame_sent_to_main_thread_(-1), last_frame_number_where_draw_was_called_(-1), last_frame_number_where_tree_activation_attempted_(-1), last_frame_number_where_update_visible_tiles_was_called_(-1), @@ -25,7 +24,6 @@ SchedulerStateMachine::SchedulerStateMachine(const SchedulerSettings& settings) swap_used_incomplete_tile_(false), needs_forced_redraw_(false), needs_forced_redraw_after_next_commit_(false), - needs_redraw_after_next_commit_(false), needs_commit_(false), needs_forced_commit_(false), expect_immediate_begin_frame_for_main_thread_(false), @@ -118,19 +116,6 @@ bool SchedulerStateMachine::HasUpdatedVisibleTilesThisFrame() const { last_frame_number_where_update_visible_tiles_was_called_; } -void SchedulerStateMachine::SetPostCommitFlags() { - // This post-commit work is common to both completed and aborted commits. - if (needs_forced_redraw_after_next_commit_) { - needs_forced_redraw_after_next_commit_ = false; - needs_forced_redraw_ = true; - } - if (needs_redraw_after_next_commit_) { - needs_redraw_after_next_commit_ = false; - needs_redraw_ = true; - } - texture_state_ = LAYER_TEXTURE_STATE_ACQUIRED_BY_IMPL_THREAD; -} - bool SchedulerStateMachine::DrawSuspendedUntilCommit() const { if (!can_draw_) return true; @@ -199,7 +184,7 @@ SchedulerStateMachine::Action SchedulerStateMachine::NextAction() const { return ACTION_ACQUIRE_LAYER_TEXTURES_FOR_MAIN_THREAD; switch (commit_state_) { - case COMMIT_STATE_IDLE: { + case COMMIT_STATE_IDLE: if (output_surface_state_ != OUTPUT_SURFACE_ACTIVE && needs_forced_redraw_) return ACTION_DRAW_FORCED; @@ -220,18 +205,14 @@ SchedulerStateMachine::Action SchedulerStateMachine::NextAction() const { return needs_forced_redraw_ ? ACTION_DRAW_FORCED : ACTION_DRAW_IF_POSSIBLE; } - bool can_commit_this_frame = - visible_ && - current_frame_number_ > - last_frame_number_where_begin_frame_sent_to_main_thread_; - if (needs_commit_ && ((can_commit_this_frame && - output_surface_state_ == OUTPUT_SURFACE_ACTIVE) || - needs_forced_commit_)) + if (needs_commit_ && + ((visible_ && output_surface_state_ == OUTPUT_SURFACE_ACTIVE) + || needs_forced_commit_)) // TODO(enne): Should probably drop the active tree on force commit. return has_pending_tree_ ? ACTION_NONE : ACTION_SEND_BEGIN_FRAME_TO_MAIN_THREAD; return ACTION_NONE; - } + case COMMIT_STATE_FRAME_IN_PROGRESS: if (ShouldUpdateVisibleTiles()) return ACTION_UPDATE_VISIBLE_TILES; @@ -258,11 +239,7 @@ SchedulerStateMachine::Action SchedulerStateMachine::NextAction() const { // COMMIT_STATE_WAITING_FOR_FIRST_DRAW wants to enforce a draw. If // can_draw_ is false or textures are not available, proceed to the next // step (similar as in COMMIT_STATE_IDLE). - bool can_commit = - needs_forced_commit_ || - (visible_ && - current_frame_number_ > - last_frame_number_where_begin_frame_sent_to_main_thread_); + bool can_commit = visible_ || needs_forced_commit_; if (needs_commit_ && can_commit && DrawSuspendedUntilCommit()) return has_pending_tree_ ? ACTION_NONE : ACTION_SEND_BEGIN_FRAME_TO_MAIN_THREAD; @@ -299,16 +276,10 @@ void SchedulerStateMachine::UpdateState(Action action) { case ACTION_SEND_BEGIN_FRAME_TO_MAIN_THREAD: DCHECK(!has_pending_tree_); - if (!needs_forced_commit_) { - DCHECK(visible_); - DCHECK_GT(current_frame_number_, - last_frame_number_where_begin_frame_sent_to_main_thread_); - } + DCHECK(visible_ || needs_forced_commit_); commit_state_ = COMMIT_STATE_FRAME_IN_PROGRESS; needs_commit_ = false; needs_forced_commit_ = false; - last_frame_number_where_begin_frame_sent_to_main_thread_ = - current_frame_number_; return; case ACTION_COMMIT: @@ -322,7 +293,13 @@ void SchedulerStateMachine::UpdateState(Action action) { needs_redraw_ = true; if (draw_if_possible_failed_) last_frame_number_where_draw_was_called_ = -1; - SetPostCommitFlags(); + + if (needs_forced_redraw_after_next_commit_) { + needs_forced_redraw_after_next_commit_ = false; + needs_forced_redraw_ = true; + } + + texture_state_ = LAYER_TEXTURE_STATE_ACQUIRED_BY_IMPL_THREAD; return; case ACTION_DRAW_FORCED: @@ -390,12 +367,12 @@ bool SchedulerStateMachine::ProactiveBeginFrameWantedByImplThread() const { } void SchedulerStateMachine::DidEnterBeginFrame(const BeginFrameArgs& args) { - current_frame_number_++; inside_begin_frame_ = true; last_begin_frame_args_ = args; } void SchedulerStateMachine::DidLeaveBeginFrame() { + current_frame_number_++; inside_begin_frame_ = false; } @@ -445,13 +422,10 @@ void SchedulerStateMachine::FinishCommit() { commit_state_ = COMMIT_STATE_READY_TO_COMMIT; } -void SchedulerStateMachine::BeginFrameAbortedByMainThread(bool did_handle) { +void SchedulerStateMachine::BeginFrameAbortedByMainThread() { DCHECK_EQ(commit_state_, COMMIT_STATE_FRAME_IN_PROGRESS); if (expect_immediate_begin_frame_for_main_thread_) { expect_immediate_begin_frame_for_main_thread_ = false; - } else if (did_handle) { - commit_state_ = COMMIT_STATE_IDLE; - SetPostCommitFlags(); } else { commit_state_ = COMMIT_STATE_IDLE; SetNeedsCommit(); @@ -484,7 +458,6 @@ void SchedulerStateMachine::DidCreateAndInitializeOutputSurface() { // sort themselves out with a commit. needs_redraw_ = false; } - needs_redraw_after_next_commit_ = true; did_create_and_initialize_first_output_surface_ = true; } diff --git a/cc/scheduler/scheduler_state_machine.h b/cc/scheduler/scheduler_state_machine.h index 5c7d5b5..5a29830d 100644 --- a/cc/scheduler/scheduler_state_machine.h +++ b/cc/scheduler/scheduler_state_machine.h @@ -79,7 +79,7 @@ class CC_EXPORT SchedulerStateMachine { // Indicates that the system has entered and left a BeginFrame callback. // The scheduler will not draw more than once in a given BeginFrame - // callback nor send more than one BeginFrame message. + // callback. void DidEnterBeginFrame(const BeginFrameArgs& args); void DidLeaveBeginFrame(); bool inside_begin_frame() const { return inside_begin_frame_; } @@ -120,9 +120,8 @@ class CC_EXPORT SchedulerStateMachine { // Call this only in response to receiving an // ACTION_SEND_BEGIN_FRAME_TO_MAIN_THREAD from NextAction if the client - // rejects the begin frame message. If did_handle is false, then - // another commit will be retried soon. - void BeginFrameAbortedByMainThread(bool did_handle); + // rejects the begin frame message. + void BeginFrameAbortedByMainThread(); // Request exclusive access to the textures that back single buffered // layers on behalf of the main thread. Upon acquisition, @@ -169,7 +168,6 @@ class CC_EXPORT SchedulerStateMachine { bool HasDrawnThisFrame() const; bool HasAttemptedTreeActivationThisFrame() const; bool HasUpdatedVisibleTilesThisFrame() const; - void SetPostCommitFlags(); const SchedulerSettings settings_; @@ -177,7 +175,6 @@ class CC_EXPORT SchedulerStateMachine { int commit_count_; int current_frame_number_; - int last_frame_number_where_begin_frame_sent_to_main_thread_; int last_frame_number_where_draw_was_called_; int last_frame_number_where_tree_activation_attempted_; int last_frame_number_where_update_visible_tiles_was_called_; @@ -187,7 +184,6 @@ class CC_EXPORT SchedulerStateMachine { bool swap_used_incomplete_tile_; bool needs_forced_redraw_; bool needs_forced_redraw_after_next_commit_; - bool needs_redraw_after_next_commit_; bool needs_commit_; bool needs_forced_commit_; bool expect_immediate_begin_frame_for_main_thread_; diff --git a/cc/scheduler/scheduler_state_machine_unittest.cc b/cc/scheduler/scheduler_state_machine_unittest.cc index c7210eb..7036459 100644 --- a/cc/scheduler/scheduler_state_machine_unittest.cc +++ b/cc/scheduler/scheduler_state_machine_unittest.cc @@ -718,7 +718,7 @@ TEST(SchedulerStateMachineTest, TestGoesInvisibleBeforeFinishCommit) { // Become invisible and abort the main thread's begin frame. state.SetVisible(false); - state.BeginFrameAbortedByMainThread(false); + state.BeginFrameAbortedByMainThread(); // We should now be back in the idle state as if we didn't start a frame at // all. @@ -728,14 +728,8 @@ TEST(SchedulerStateMachineTest, TestGoesInvisibleBeforeFinishCommit) { // Become visible again. state.SetVisible(true); - // Although we have aborted on this frame and haven't cancelled the commit - // (i.e. need another), don't send another begin frame yet. + // We should be beginning a frame now. EXPECT_EQ(SchedulerStateMachine::COMMIT_STATE_IDLE, state.CommitState()); - EXPECT_EQ(SchedulerStateMachine::ACTION_NONE, state.NextAction()); - EXPECT_TRUE(state.NeedsCommit()); - - // Start a new frame. - state.DidEnterBeginFrame(BeginFrameArgs::CreateForTesting()); EXPECT_EQ(SchedulerStateMachine::ACTION_SEND_BEGIN_FRAME_TO_MAIN_THREAD, state.NextAction()); @@ -747,52 +741,6 @@ TEST(SchedulerStateMachineTest, TestGoesInvisibleBeforeFinishCommit) { state.CommitState()); } -TEST(SchedulerStateMachineTest, AbortBeginFrameAndCancelCommit) { - SchedulerSettings default_scheduler_settings; - StateMachine state(default_scheduler_settings); - state.SetCanStart(); - state.UpdateState(state.NextAction()); - state.DidCreateAndInitializeOutputSurface(); - state.SetVisible(true); - state.SetCanDraw(true); - - // Get into a begin frame / commit state. - state.SetNeedsCommit(); - EXPECT_EQ(SchedulerStateMachine::ACTION_SEND_BEGIN_FRAME_TO_MAIN_THREAD, - state.NextAction()); - state.UpdateState( - SchedulerStateMachine::ACTION_SEND_BEGIN_FRAME_TO_MAIN_THREAD); - EXPECT_EQ(SchedulerStateMachine::COMMIT_STATE_FRAME_IN_PROGRESS, - state.CommitState()); - EXPECT_FALSE(state.NeedsCommit()); - EXPECT_EQ(SchedulerStateMachine::ACTION_NONE, state.NextAction()); - - // Abort the commit, cancelling future commits. - state.BeginFrameAbortedByMainThread(true); - - // Verify that another commit doesn't start on the same frame. - EXPECT_EQ(SchedulerStateMachine::COMMIT_STATE_IDLE, state.CommitState()); - EXPECT_EQ(SchedulerStateMachine::ACTION_NONE, state.NextAction()); - EXPECT_FALSE(state.NeedsCommit()); - - // Start a new frame; draw because this is the first frame since output - // surface init'd. - state.DidEnterBeginFrame(BeginFrameArgs::CreateForTesting()); - EXPECT_EQ(SchedulerStateMachine::ACTION_DRAW_IF_POSSIBLE, state.NextAction()); - state.DidLeaveBeginFrame(); - - // Verify another commit doesn't start on another frame either. - EXPECT_EQ(SchedulerStateMachine::COMMIT_STATE_IDLE, state.CommitState()); - EXPECT_EQ(SchedulerStateMachine::ACTION_NONE, state.NextAction()); - EXPECT_FALSE(state.NeedsCommit()); - - // Verify another commit can start if requested, though. - state.SetNeedsCommit(); - EXPECT_EQ(SchedulerStateMachine::COMMIT_STATE_IDLE, state.CommitState()); - EXPECT_EQ(SchedulerStateMachine::ACTION_SEND_BEGIN_FRAME_TO_MAIN_THREAD, - state.NextAction()); -} - TEST(SchedulerStateMachineTest, TestFirstContextCreation) { SchedulerSettings default_scheduler_settings; StateMachine state(default_scheduler_settings); @@ -868,23 +816,15 @@ TEST(SchedulerStateMachineTest, // Recreate the context state.DidCreateAndInitializeOutputSurface(); - EXPECT_FALSE(state.RedrawPending()); // When the context is recreated, we should begin a commit EXPECT_EQ(SchedulerStateMachine::ACTION_SEND_BEGIN_FRAME_TO_MAIN_THREAD, state.NextAction()); state.UpdateState(state.NextAction()); - EXPECT_EQ(SchedulerStateMachine::COMMIT_STATE_FRAME_IN_PROGRESS, - state.CommitState()); - state.FinishCommit(); - EXPECT_EQ(SchedulerStateMachine::ACTION_COMMIT, state.NextAction()); - state.UpdateState(state.NextAction()); - // Finishing the first commit after initializing an output surface should - // automatically cause a redraw. - EXPECT_TRUE(state.RedrawPending()); // Once the context is recreated, whether we draw should be based on // SetCanDraw. + state.SetNeedsRedraw(true); state.DidEnterBeginFrame(BeginFrameArgs::CreateForTesting()); EXPECT_EQ(SchedulerStateMachine::ACTION_DRAW_IF_POSSIBLE, state.NextAction()); state.SetCanDraw(false); @@ -1252,7 +1192,7 @@ TEST(SchedulerStateMachineTest, // Become invisible and abort the main thread's begin frame. state.SetVisible(false); - state.BeginFrameAbortedByMainThread(false); + state.BeginFrameAbortedByMainThread(); // Should be back in the idle state, but needing a commit. EXPECT_EQ(SchedulerStateMachine::COMMIT_STATE_IDLE, state.CommitState()); @@ -1355,37 +1295,5 @@ TEST(SchedulerStateMachineTest, ReportIfNotDrawingFromAcquiredTextures) { EXPECT_FALSE(state.DrawSuspendedUntilCommit()); } -TEST(SchedulerStateMachineTest, AcquireTexturesWithAbort) { - SchedulerSettings default_scheduler_settings; - SchedulerStateMachine state(default_scheduler_settings); - state.SetCanStart(); - state.UpdateState(state.NextAction()); - state.DidCreateAndInitializeOutputSurface(); - state.SetCanDraw(true); - state.SetVisible(true); - - state.SetMainThreadNeedsLayerTextures(); - EXPECT_EQ( - SchedulerStateMachine::ACTION_ACQUIRE_LAYER_TEXTURES_FOR_MAIN_THREAD, - state.NextAction()); - state.UpdateState(state.NextAction()); - EXPECT_TRUE(state.DrawSuspendedUntilCommit()); - - EXPECT_EQ(SchedulerStateMachine::ACTION_NONE, state.NextAction()); - - state.SetNeedsCommit(); - EXPECT_EQ(SchedulerStateMachine::ACTION_SEND_BEGIN_FRAME_TO_MAIN_THREAD, - state.NextAction()); - state.UpdateState(state.NextAction()); - EXPECT_TRUE(state.DrawSuspendedUntilCommit()); - - EXPECT_EQ(SchedulerStateMachine::ACTION_NONE, state.NextAction()); - - state.BeginFrameAbortedByMainThread(true); - - EXPECT_EQ(SchedulerStateMachine::ACTION_NONE, state.NextAction()); - EXPECT_FALSE(state.DrawSuspendedUntilCommit()); -} - } // namespace } // namespace cc diff --git a/cc/scheduler/scheduler_unittest.cc b/cc/scheduler/scheduler_unittest.cc index 930111c..0a3c250 100644 --- a/cc/scheduler/scheduler_unittest.cc +++ b/cc/scheduler/scheduler_unittest.cc @@ -378,17 +378,12 @@ TEST(SchedulerTest, VisibilitySwitchWithTextureAcquisition) { client); client.Reset(); - // Already sent a begin frame on this current frame, so wait. - scheduler->SetVisible(true); - EXPECT_EQ(0, client.num_actions_()); - client.Reset(); - // Regaining visibility with textures acquired by main thread while // compositor is waiting for first draw should result in a request // for a new frame in order to escape a deadlock. - scheduler->BeginFrame(BeginFrameArgs::CreateForTesting()); - EXPECT_ACTION("ScheduledActionSendBeginFrameToMainThread", client, 0, 2); - EXPECT_ACTION("SetNeedsBeginFrameOnImplThread", client, 1, 2); + scheduler->SetVisible(true); + EXPECT_SINGLE_ACTION("ScheduledActionSendBeginFrameToMainThread", client); + client.Reset(); } class SchedulerClientThatsetNeedsDrawInsideDraw : public FakeSchedulerClient { diff --git a/cc/test/fake_content_layer.cc b/cc/test/fake_content_layer.cc index 077831fd..5dcc512 100644 --- a/cc/test/fake_content_layer.cc +++ b/cc/test/fake_content_layer.cc @@ -12,8 +12,7 @@ namespace cc { FakeContentLayer::FakeContentLayer(ContentLayerClient* client) : ContentLayer(client), update_count_(0), - push_properties_count_(0), - always_update_resources_(false) { + push_properties_count_(0) { SetAnchorPoint(gfx::PointF(0.f, 0.f)); SetBounds(gfx::Size(1, 1)); SetIsDrawable(true); @@ -30,7 +29,7 @@ bool FakeContentLayer::Update(ResourceUpdateQueue* queue, const OcclusionTracker* occlusion) { bool updated = ContentLayer::Update(queue, occlusion); update_count_++; - return updated || always_update_resources_; + return updated; } void FakeContentLayer::PushPropertiesTo(LayerImpl* layer) { diff --git a/cc/test/fake_content_layer.h b/cc/test/fake_content_layer.h index 191a634..6b7a37d 100644 --- a/cc/test/fake_content_layer.h +++ b/cc/test/fake_content_layer.h @@ -29,10 +29,6 @@ class FakeContentLayer : public ContentLayer { ResourceUpdateQueue* queue, const OcclusionTracker* occlusion) OVERRIDE; - void set_always_update_resources(bool always_update_resources) { - always_update_resources_ = always_update_resources; - } - virtual void PushPropertiesTo(LayerImpl* layer) OVERRIDE; bool HaveBackingAt(int i, int j); @@ -43,7 +39,6 @@ class FakeContentLayer : public ContentLayer { size_t update_count_; size_t push_properties_count_; - bool always_update_resources_; }; } // namespace cc diff --git a/cc/test/fake_picture_layer.cc b/cc/test/fake_picture_layer.cc index 69292c3..997197c 100644 --- a/cc/test/fake_picture_layer.cc +++ b/cc/test/fake_picture_layer.cc @@ -11,8 +11,7 @@ namespace cc { FakePictureLayer::FakePictureLayer(ContentLayerClient* client) : PictureLayer(client), update_count_(0), - push_properties_count_(0), - always_update_resources_(false) { + push_properties_count_(0) { SetAnchorPoint(gfx::PointF(0.f, 0.f)); SetBounds(gfx::Size(1, 1)); SetIsDrawable(true); @@ -29,7 +28,7 @@ bool FakePictureLayer::Update(ResourceUpdateQueue* queue, const OcclusionTracker* occlusion) { bool updated = PictureLayer::Update(queue, occlusion); update_count_++; - return updated || always_update_resources_; + return updated; } void FakePictureLayer::PushPropertiesTo(LayerImpl* layer) { diff --git a/cc/test/fake_picture_layer.h b/cc/test/fake_picture_layer.h index 824ac6c..b5b81de 100644 --- a/cc/test/fake_picture_layer.h +++ b/cc/test/fake_picture_layer.h @@ -26,12 +26,9 @@ class FakePictureLayer : public PictureLayer { size_t push_properties_count() const { return push_properties_count_; } void reset_push_properties_count() { push_properties_count_ = 0; } - void set_always_update_resources(bool always_update_resources) { - always_update_resources_ = always_update_resources; - } - - virtual bool Update(ResourceUpdateQueue* queue, - const OcclusionTracker* occlusion) OVERRIDE; + virtual bool Update( + ResourceUpdateQueue* queue, + const OcclusionTracker* occlusion) OVERRIDE; virtual void PushPropertiesTo(LayerImpl* layer) OVERRIDE; @@ -41,7 +38,6 @@ class FakePictureLayer : public PictureLayer { size_t update_count_; size_t push_properties_count_; - bool always_update_resources_; }; } // namespace cc diff --git a/cc/test/fake_proxy.h b/cc/test/fake_proxy.h index 8cc3311..76de4b0 100644 --- a/cc/test/fake_proxy.h +++ b/cc/test/fake_proxy.h @@ -29,7 +29,6 @@ class FakeProxy : public Proxy { virtual void CreateAndInitializeOutputSurface() OVERRIDE; virtual const RendererCapabilities& GetRendererCapabilities() const OVERRIDE; virtual void SetNeedsAnimate() OVERRIDE {} - virtual void SetNeedsUpdateLayers() OVERRIDE {} virtual void SetNeedsCommit() OVERRIDE {} virtual void SetNeedsRedraw(gfx::Rect damage_rect) OVERRIDE {} virtual void SetDeferCommits(bool defer_commits) OVERRIDE {} diff --git a/cc/test/layer_test_common.h b/cc/test/layer_test_common.h index 0021398..94e2f2a 100644 --- a/cc/test/layer_test_common.h +++ b/cc/test/layer_test_common.h @@ -5,18 +5,10 @@ #ifndef CC_TEST_LAYER_TEST_COMMON_H_ #define CC_TEST_LAYER_TEST_COMMON_H_ -#define EXPECT_SET_NEEDS_COMMIT(expect, code_to_test) \ - do { \ - EXPECT_CALL(*layer_tree_host_, SetNeedsCommit()).Times((expect)); \ - code_to_test; \ - Mock::VerifyAndClearExpectations(layer_tree_host_.get()); \ - } while (false) - -#define EXPECT_SET_NEEDS_UPDATE(expect, code_to_test) \ - do { \ - EXPECT_CALL(*layer_tree_host_, SetNeedsUpdateLayers()).Times((expect)); \ - code_to_test; \ - Mock::VerifyAndClearExpectations(layer_tree_host_.get()); \ +#define EXPECT_SET_NEEDS_COMMIT(expect, code_to_test) do { \ + EXPECT_CALL(*layer_tree_host_, SetNeedsCommit()).Times((expect)); \ + code_to_test; \ + Mock::VerifyAndClearExpectations(layer_tree_host_.get()); \ } while (false) namespace gfx { class Rect; } diff --git a/cc/test/layer_tree_test.cc b/cc/test/layer_tree_test.cc index 6193d84..ed97752 100644 --- a/cc/test/layer_tree_test.cc +++ b/cc/test/layer_tree_test.cc @@ -233,9 +233,9 @@ class LayerTreeHostClientForTesting : public LayerTreeHostClient { } virtual ~LayerTreeHostClientForTesting() {} - virtual void WillBeginFrame() OVERRIDE { test_hooks_->WillBeginFrame(); } + virtual void WillBeginFrame() OVERRIDE {} - virtual void DidBeginFrame() OVERRIDE { test_hooks_->DidBeginFrame(); } + virtual void DidBeginFrame() OVERRIDE {} virtual void Animate(double monotonic_time) OVERRIDE { test_hooks_->Animate(base::TimeTicks::FromInternalValue( @@ -263,7 +263,7 @@ class LayerTreeHostClientForTesting : public LayerTreeHostClient { test_hooks_->DidFailToInitializeOutputSurface(); } - virtual void WillCommit() OVERRIDE { test_hooks_->WillCommit(); } + virtual void WillCommit() OVERRIDE {} virtual void DidCommit() OVERRIDE { test_hooks_->DidCommit(); diff --git a/cc/test/layer_tree_test.h b/cc/test/layer_tree_test.h index 627fff2..556378b 100644 --- a/cc/test/layer_tree_test.h +++ b/cc/test/layer_tree_test.h @@ -52,13 +52,10 @@ class TestHooks : public AnimationDelegate { virtual void ApplyScrollAndScale(gfx::Vector2d scroll_delta, float scale) {} virtual void Animate(base::TimeTicks monotonic_time) {} - virtual void WillBeginFrame() {} - virtual void DidBeginFrame() {} virtual void Layout() {} virtual void DidInitializeOutputSurface(bool succeeded) {} virtual void DidFailToInitializeOutputSurface() {} virtual void DidAddAnimation() {} - virtual void WillCommit() {} virtual void DidCommit() {} virtual void DidCommitAndDrawFrame() {} virtual void DidCompleteSwapBuffers() {} diff --git a/cc/trees/layer_tree_host.cc b/cc/trees/layer_tree_host.cc index 308b519..0d90c59 100644 --- a/cc/trees/layer_tree_host.cc +++ b/cc/trees/layer_tree_host.cc @@ -469,8 +469,6 @@ void LayerTreeHost::SetNeedsAnimate() { proxy_->SetNeedsAnimate(); } -void LayerTreeHost::SetNeedsUpdateLayers() { proxy_->SetNeedsUpdateLayers(); } - void LayerTreeHost::SetNeedsCommit() { if (!prepaint_callback_.IsCancelled()) { TRACE_EVENT_INSTANT0("cc", @@ -583,11 +581,6 @@ void LayerTreeHost::SetOverdrawBottomHeight(float overdraw_bottom_height) { SetNeedsCommit(); } -void LayerTreeHost::ApplyPageScaleDeltaFromImplSide(float page_scale_delta) { - DCHECK(CommitRequested()); - page_scale_factor_ *= page_scale_delta; -} - void LayerTreeHost::SetPageScaleFactorAndLimits(float page_scale_factor, float min_page_scale_factor, float max_page_scale_factor) { @@ -971,8 +964,8 @@ void LayerTreeHost::ApplyScrollAndScale(const ScrollAndScaleSet& info) { if (!root_layer_.get()) return; - gfx::Vector2d root_scroll_delta; Layer* root_scroll_layer = FindFirstScrollableLayer(root_layer_.get()); + gfx::Vector2d root_scroll_delta; for (size_t i = 0; i < info.scrolls.size(); ++i) { Layer* layer = @@ -987,22 +980,8 @@ void LayerTreeHost::ApplyScrollAndScale(const ScrollAndScaleSet& info) { info.scrolls[i].scroll_delta); } } - - if (!root_scroll_delta.IsZero() || info.page_scale_delta != 1.f) { - // SetScrollOffsetFromImplSide above could have destroyed the tree, - // so re-get this layer before doing anything to it. - root_scroll_layer = FindFirstScrollableLayer(root_layer_.get()); - - // Preemptively apply the scroll offset and scale delta here before sending - // it to the client. If the client comes back and sets it to the same - // value, then the layer can early out without needing a full commit. - if (root_scroll_layer) { - root_scroll_layer->SetScrollOffsetFromImplSide( - root_scroll_layer->scroll_offset() + root_scroll_delta); - } - ApplyPageScaleDeltaFromImplSide(info.page_scale_delta); + if (!root_scroll_delta.IsZero() || info.page_scale_delta != 1.f) client_->ApplyScrollAndScale(root_scroll_delta, info.page_scale_delta); - } } void LayerTreeHost::StartRateLimiter(WebKit::WebGraphicsContext3D* context3d) { diff --git a/cc/trees/layer_tree_host.h b/cc/trees/layer_tree_host.h index 6de24c4..0fd3abb 100644 --- a/cc/trees/layer_tree_host.h +++ b/cc/trees/layer_tree_host.h @@ -165,7 +165,6 @@ class CC_EXPORT LayerTreeHost : NON_EXPORTED_BASE(public RateLimiterClient) { const RendererCapabilities& GetRendererCapabilities() const; void SetNeedsAnimate(); - virtual void SetNeedsUpdateLayers(); virtual void SetNeedsCommit(); virtual void SetNeedsFullTreeSync(); void SetNeedsRedraw(); @@ -190,7 +189,6 @@ class CC_EXPORT LayerTreeHost : NON_EXPORTED_BASE(public RateLimiterClient) { gfx::Size device_viewport_size() const { return device_viewport_size_; } float overdraw_bottom_height() const { return overdraw_bottom_height_; } - void ApplyPageScaleDeltaFromImplSide(float page_scale_delta); void SetPageScaleFactorAndLimits(float page_scale_factor, float min_page_scale_factor, float max_page_scale_factor); diff --git a/cc/trees/layer_tree_host_impl.cc b/cc/trees/layer_tree_host_impl.cc index f97eea0..629877f 100644 --- a/cc/trees/layer_tree_host_impl.cc +++ b/cc/trees/layer_tree_host_impl.cc @@ -1180,10 +1180,8 @@ void LayerTreeHostImpl::DrawLayers(FrameData* frame, TRACE_EVENT0("cc", "LayerTreeHostImpl::DrawLayers"); DCHECK(CanDraw()); - if (frame->has_no_damage) { - TRACE_EVENT0("cc", "EarlyOut_NoDamage"); + if (frame->has_no_damage) return; - } DCHECK(!frame->render_passes.empty()); diff --git a/cc/trees/layer_tree_host_unittest.cc b/cc/trees/layer_tree_host_unittest.cc index a6bdd90..7c940bb 100644 --- a/cc/trees/layer_tree_host_unittest.cc +++ b/cc/trees/layer_tree_host_unittest.cc @@ -1812,7 +1812,7 @@ class LayerTreeHostTestContinuousCommit : public LayerTreeHostTest { virtual void DidCommit() OVERRIDE { if (num_draw_layers_ == 2) return; - layer_tree_host()->SetNeedsCommit(); + layer_tree_host()->root_layer()->SetNeedsDisplay(); } virtual void CommitCompleteOnThread(LayerTreeHostImpl* impl) OVERRIDE { @@ -3099,9 +3099,6 @@ class LayerTreeHostTestDeferredInitialize : public LayerTreeHostTest { virtual void SetupTree() OVERRIDE { layer_ = FakePictureLayer::Create(&client_); - // Force commits to not be aborted so new frames get drawn, otherwise - // the renderer gets deferred initialized but nothing new needs drawing. - layer_->set_always_update_resources(true); layer_tree_host()->SetRootLayer(layer_); LayerTreeHostTest::SetupTree(); } @@ -3398,11 +3395,9 @@ class LayerTreeHostTestLayersPushProperties : public LayerTreeHostTest { ++expected_push_properties_grandchild_; break; case 16: - // SetNeedsDisplay does not always set needs commit (so call it - // explicitly), but is a property change. child_->SetNeedsDisplay(); + // The modified layer needs commit ++expected_push_properties_child_; - layer_tree_host()->SetNeedsCommit(); break; case 17: EndTest(); diff --git a/cc/trees/layer_tree_host_unittest_context.cc b/cc/trees/layer_tree_host_unittest_context.cc index fc779b0..94f15c2 100644 --- a/cc/trees/layer_tree_host_unittest_context.cc +++ b/cc/trees/layer_tree_host_unittest_context.cc @@ -286,7 +286,6 @@ class LayerTreeHostContextTestLostContextSucceeds virtual void InvalidateAndSetNeedsCommit() { // Cause damage so we try to draw. layer_tree_host()->root_layer()->SetNeedsDisplay(); - layer_tree_host()->SetNeedsCommit(); } bool NextTestCase() { diff --git a/cc/trees/layer_tree_host_unittest_damage.cc b/cc/trees/layer_tree_host_unittest_damage.cc index 69fa34d..0feabf7 100644 --- a/cc/trees/layer_tree_host_unittest_damage.cc +++ b/cc/trees/layer_tree_host_unittest_damage.cc @@ -87,7 +87,6 @@ class LayerTreeHostDamageTestNoDamageDoesNotSwap case 3: // Cause non-visible damage. content_->SetNeedsDisplayRect(gfx::Rect(1990, 1990, 10, 10)); - layer_tree_host()->SetNeedsCommit(); break; } } diff --git a/cc/trees/layer_tree_host_unittest_scroll.cc b/cc/trees/layer_tree_host_unittest_scroll.cc index 5443cd3..e531194 100644 --- a/cc/trees/layer_tree_host_unittest_scroll.cc +++ b/cc/trees/layer_tree_host_unittest_scroll.cc @@ -70,8 +70,10 @@ class LayerTreeHostScrollTestScrollSimple : public LayerTreeHostScrollTest { } } - virtual void ApplyScrollAndScale(gfx::Vector2d scroll_delta, - float scale) OVERRIDE { + virtual void ApplyScrollAndScale(gfx::Vector2d scroll_delta, float scale) + OVERRIDE { + gfx::Vector2d offset = layer_tree_host()->root_layer()->scroll_offset(); + layer_tree_host()->root_layer()->SetScrollOffset(offset + scroll_delta); num_scrolls_++; } @@ -148,8 +150,10 @@ class LayerTreeHostScrollTestScrollMultipleRedraw } } - virtual void ApplyScrollAndScale(gfx::Vector2d scroll_delta, - float scale) OVERRIDE { + virtual void ApplyScrollAndScale(gfx::Vector2d scroll_delta, float scale) + OVERRIDE { + gfx::Vector2d offset = layer_tree_host()->root_layer()->scroll_offset(); + layer_tree_host()->root_layer()->SetScrollOffset(offset + scroll_delta); num_scrolls_++; } @@ -163,182 +167,6 @@ class LayerTreeHostScrollTestScrollMultipleRedraw MULTI_THREAD_TEST_F(LayerTreeHostScrollTestScrollMultipleRedraw); -class LayerTreeHostScrollTestScrollAbortedCommit - : public LayerTreeHostScrollTest { - public: - LayerTreeHostScrollTestScrollAbortedCommit() - : initial_scroll_(50, 60), - impl_scroll_(-3, 2), - second_main_scroll_(14, -3), - impl_scale_(2.f), - num_will_begin_frames_(0), - num_did_begin_frames_(0), - num_will_commits_(0), - num_did_commits_(0), - num_impl_commits_(0), - num_impl_scrolls_(0) {} - - virtual void BeginTest() OVERRIDE { PostSetNeedsCommitToMainThread(); } - - virtual void SetupTree() OVERRIDE { - LayerTreeHostScrollTest::SetupTree(); - scoped_refptr<Layer> root_scroll_layer = Layer::Create(); - root_scroll_layer->SetScrollable(true); - root_scroll_layer->SetScrollOffset(initial_scroll_); - root_scroll_layer->SetBounds(gfx::Size(200, 200)); - root_scroll_layer->SetMaxScrollOffset(gfx::Vector2d(100, 100)); - root_scroll_layer->SetIsDrawable(true); - layer_tree_host()->root_layer()->AddChild(root_scroll_layer); - - layer_tree_host()->SetPageScaleFactorAndLimits(1.f, 0.01f, 100.f); - } - - virtual void WillBeginFrame() OVERRIDE { - num_will_begin_frames_++; - Layer* root_scroll_layer = layer_tree_host()->root_layer()->children()[0]; - switch (num_will_begin_frames_) { - case 1: - // This will not be aborted because of the initial prop changes. - EXPECT_EQ(0, num_impl_scrolls_); - EXPECT_EQ(0, layer_tree_host()->commit_number()); - EXPECT_VECTOR_EQ(root_scroll_layer->scroll_offset(), initial_scroll_); - EXPECT_EQ(1.f, layer_tree_host()->page_scale_factor()); - break; - case 2: - // This commit will be aborted, and another commit will be - // initiated from the redraw. - EXPECT_EQ(1, num_impl_scrolls_); - EXPECT_EQ(1, layer_tree_host()->commit_number()); - EXPECT_VECTOR_EQ(root_scroll_layer->scroll_offset(), - initial_scroll_ + impl_scroll_); - EXPECT_EQ(impl_scale_, layer_tree_host()->page_scale_factor()); - PostSetNeedsRedrawToMainThread(); - break; - case 3: - // This commit will not be aborted because of the scroll change. - EXPECT_EQ(2, num_impl_scrolls_); - EXPECT_EQ(1, layer_tree_host()->commit_number()); - EXPECT_VECTOR_EQ(root_scroll_layer->scroll_offset(), - initial_scroll_ + impl_scroll_ + impl_scroll_); - EXPECT_EQ(impl_scale_ * impl_scale_, - layer_tree_host()->page_scale_factor()); - root_scroll_layer->SetScrollOffset(root_scroll_layer->scroll_offset() + - second_main_scroll_); - break; - case 4: - // This commit will also be aborted. - EXPECT_EQ(3, num_impl_scrolls_); - EXPECT_EQ(2, layer_tree_host()->commit_number()); - EXPECT_VECTOR_EQ(root_scroll_layer->scroll_offset(), - initial_scroll_ + impl_scroll_ + impl_scroll_ + - impl_scroll_ + second_main_scroll_); - // End the test by drawing to verify this commit is also aborted. - PostSetNeedsRedrawToMainThread(); - break; - } - } - - virtual void DidBeginFrame() OVERRIDE { num_did_begin_frames_++; } - - virtual void WillCommit() OVERRIDE { num_will_commits_++; } - - virtual void DidCommit() OVERRIDE { num_did_commits_++; } - - virtual void BeginCommitOnThread(LayerTreeHostImpl* impl) OVERRIDE { - num_impl_commits_++; - } - - virtual void DrawLayersOnThread(LayerTreeHostImpl* impl) OVERRIDE { - LayerImpl* root_scroll_layer = - impl->active_tree()->root_layer()->children()[0]; - - if (impl->active_tree()->source_frame_number() == 0 && - impl->SourceAnimationFrameNumber() == 1) { - // First draw - EXPECT_VECTOR_EQ(root_scroll_layer->ScrollDelta(), gfx::Vector2d()); - root_scroll_layer->ScrollBy(impl_scroll_); - EXPECT_VECTOR_EQ(root_scroll_layer->ScrollDelta(), impl_scroll_); - EXPECT_VECTOR_EQ(root_scroll_layer->scroll_offset(), initial_scroll_); - - EXPECT_EQ(1.f, impl->active_tree()->page_scale_delta()); - EXPECT_EQ(1.f, impl->active_tree()->total_page_scale_factor()); - impl->active_tree()->SetPageScaleDelta(impl_scale_); - EXPECT_EQ(impl_scale_, impl->active_tree()->page_scale_delta()); - EXPECT_EQ(impl_scale_, impl->active_tree()->total_page_scale_factor()); - - // To simplify the testing flow, don't redraw here, just commit. - impl->SetNeedsCommit(); - } else if (impl->active_tree()->source_frame_number() == 0 && - impl->SourceAnimationFrameNumber() == 2) { - // Test a second draw after an aborted commit. - // The scroll/scale values should be baked into the offset/scale factor - // since the main thread consumed but aborted the begin frame. - EXPECT_VECTOR_EQ(root_scroll_layer->ScrollDelta(), gfx::Vector2d()); - root_scroll_layer->ScrollBy(impl_scroll_); - EXPECT_VECTOR_EQ(root_scroll_layer->ScrollDelta(), impl_scroll_); - EXPECT_VECTOR_EQ(root_scroll_layer->scroll_offset(), - initial_scroll_ + impl_scroll_); - - EXPECT_EQ(1.f, impl->active_tree()->page_scale_delta()); - EXPECT_EQ(impl_scale_, impl->active_tree()->total_page_scale_factor()); - impl->active_tree()->SetPageScaleDelta(impl_scale_); - EXPECT_EQ(impl_scale_, impl->active_tree()->page_scale_delta()); - EXPECT_EQ(impl_scale_ * impl_scale_, - impl->active_tree()->total_page_scale_factor()); - - impl->SetNeedsCommit(); - } else if (impl->active_tree()->source_frame_number() == 1 && - impl->SourceAnimationFrameNumber() == 3) { - // Third draw after the second full commit. - EXPECT_EQ(root_scroll_layer->ScrollDelta(), gfx::Vector2d()); - root_scroll_layer->ScrollBy(impl_scroll_); - impl->SetNeedsCommit(); - EXPECT_VECTOR_EQ(root_scroll_layer->ScrollDelta(), impl_scroll_); - EXPECT_VECTOR_EQ( - root_scroll_layer->scroll_offset(), - initial_scroll_ + impl_scroll_ + impl_scroll_ + second_main_scroll_); - } else if (impl->active_tree()->source_frame_number() == 1 && - impl->SourceAnimationFrameNumber() == 4) { - // Final draw after the second aborted commit. - EXPECT_VECTOR_EQ(root_scroll_layer->ScrollDelta(), gfx::Vector2d()); - EXPECT_VECTOR_EQ(root_scroll_layer->scroll_offset(), - initial_scroll_ + impl_scroll_ + impl_scroll_ + - impl_scroll_ + second_main_scroll_); - EndTest(); - } - } - - virtual void ApplyScrollAndScale(gfx::Vector2d scroll_delta, - float scale) OVERRIDE { - num_impl_scrolls_++; - } - - virtual void AfterTest() OVERRIDE { - EXPECT_EQ(3, num_impl_scrolls_); - // Verify that the embedder sees aborted commits as real commits. - EXPECT_EQ(4, num_will_begin_frames_); - EXPECT_EQ(4, num_did_begin_frames_); - EXPECT_EQ(4, num_will_commits_); - EXPECT_EQ(4, num_did_commits_); - // ...but the compositor thread only sees two real ones. - EXPECT_EQ(2, num_impl_commits_); - } - - private: - gfx::Vector2d initial_scroll_; - gfx::Vector2d impl_scroll_; - gfx::Vector2d second_main_scroll_; - float impl_scale_; - int num_will_begin_frames_; - int num_did_begin_frames_; - int num_will_commits_; - int num_did_commits_; - int num_impl_commits_; - int num_impl_scrolls_; -}; - -MULTI_THREAD_TEST_F(LayerTreeHostScrollTestScrollAbortedCommit); - class LayerTreeHostScrollTestFractionalScroll : public LayerTreeHostScrollTest { public: LayerTreeHostScrollTestFractionalScroll() : scroll_amount_(1.75, 0) {} @@ -380,6 +208,12 @@ class LayerTreeHostScrollTestFractionalScroll : public LayerTreeHostScrollTest { root->ScrollBy(scroll_amount_); } + virtual void ApplyScrollAndScale(gfx::Vector2d scroll_delta, float scale) + OVERRIDE { + gfx::Vector2d offset = layer_tree_host()->root_layer()->scroll_offset(); + layer_tree_host()->root_layer()->SetScrollOffset(offset + scroll_delta); + } + virtual void AfterTest() OVERRIDE {} private: @@ -451,20 +285,14 @@ class LayerTreeHostScrollTestCaseWithChild : public LayerTreeHostScrollTest { virtual void BeginTest() OVERRIDE { PostSetNeedsCommitToMainThread(); } - virtual void WillCommit() OVERRIDE { - // Keep the test committing (otherwise the early out for no update - // will stall the test). - if (layer_tree_host()->commit_number() < 2) { - layer_tree_host()->SetNeedsCommit(); - } - } - void DidScroll() { final_scroll_offset_ = expected_scroll_layer_->scroll_offset(); } - virtual void ApplyScrollAndScale(gfx::Vector2d scroll_delta, - float scale) OVERRIDE { + virtual void ApplyScrollAndScale(gfx::Vector2d scroll_delta, float scale) + OVERRIDE { + gfx::Vector2d offset = root_scroll_layer_->scroll_offset(); + root_scroll_layer_->SetScrollOffset(offset + scroll_delta); num_scrolls_++; } @@ -814,8 +642,10 @@ class ImplSidePaintingScrollTestSimple : public ImplSidePaintingScrollTest { } } - virtual void ApplyScrollAndScale(gfx::Vector2d scroll_delta, - float scale) OVERRIDE { + virtual void ApplyScrollAndScale(gfx::Vector2d scroll_delta, float scale) + OVERRIDE { + gfx::Vector2d offset = layer_tree_host()->root_layer()->scroll_offset(); + layer_tree_host()->root_layer()->SetScrollOffset(offset + scroll_delta); num_scrolls_++; } diff --git a/cc/trees/layer_tree_impl.cc b/cc/trees/layer_tree_impl.cc index ca768e3..d69e7ff 100644 --- a/cc/trees/layer_tree_impl.cc +++ b/cc/trees/layer_tree_impl.cc @@ -231,24 +231,6 @@ void LayerTreeImpl::UpdateMaxScrollOffset() { root_scroll_layer_->SetMaxScrollOffset(gfx::ToFlooredVector2d(max_scroll)); } -static void ApplySentScrollDeltasOn(LayerImpl* layer) { - layer->ApplySentScrollDeltas(); -} - -void LayerTreeImpl::ApplySentScrollAndScaleDeltas() { - DCHECK(IsActiveTree()); - - page_scale_factor_ *= sent_page_scale_delta_; - page_scale_delta_ /= sent_page_scale_delta_; - sent_page_scale_delta_ = 1.f; - - if (!root_layer()) - return; - - LayerTreeHostCommon::CallFunctionForSubtree( - root_layer(), base::Bind(&ApplySentScrollDeltasOn)); -} - void LayerTreeImpl::UpdateSolidColorScrollbars() { DCHECK(settings().solid_color_scrollbars); diff --git a/cc/trees/layer_tree_impl.h b/cc/trees/layer_tree_impl.h index 27aa6fa..aafaf2a 100644 --- a/cc/trees/layer_tree_impl.h +++ b/cc/trees/layer_tree_impl.h @@ -109,7 +109,6 @@ class CC_EXPORT LayerTreeImpl { void FindRootScrollLayer(); void UpdateMaxScrollOffset(); - void ApplySentScrollAndScaleDeltas(); SkColor background_color() const { return background_color_; } void set_background_color(SkColor color) { background_color_ = color; } diff --git a/cc/trees/proxy.h b/cc/trees/proxy.h index f4a1ef9..e3b5f82 100644 --- a/cc/trees/proxy.h +++ b/cc/trees/proxy.h @@ -66,7 +66,6 @@ class CC_EXPORT Proxy { virtual const RendererCapabilities& GetRendererCapabilities() const = 0; virtual void SetNeedsAnimate() = 0; - virtual void SetNeedsUpdateLayers() = 0; virtual void SetNeedsCommit() = 0; virtual void SetNeedsRedraw(gfx::Rect damage_rect) = 0; diff --git a/cc/trees/single_thread_proxy.cc b/cc/trees/single_thread_proxy.cc index 2c4d3a8..426b44f 100644 --- a/cc/trees/single_thread_proxy.cc +++ b/cc/trees/single_thread_proxy.cc @@ -171,11 +171,6 @@ void SingleThreadProxy::SetNeedsAnimate() { NOTREACHED(); } -void SingleThreadProxy::SetNeedsUpdateLayers() { - DCHECK(Proxy::IsMainThread()); - layer_tree_host_->ScheduleComposite(); -} - void SingleThreadProxy::DoCommit(scoped_ptr<ResourceUpdateQueue> queue) { DCHECK(Proxy::IsMainThread()); // Commit immediately. @@ -208,12 +203,11 @@ void SingleThreadProxy::DoCommit(scoped_ptr<ResourceUpdateQueue> queue) { layer_tree_host_impl_->CommitComplete(); #ifndef NDEBUG - // In the single-threaded case, the scale and scroll deltas should never be + // In the single-threaded case, the scroll deltas should never be // touched on the impl layer tree. scoped_ptr<ScrollAndScaleSet> scroll_info = layer_tree_host_impl_->ProcessScrollDeltas(); DCHECK(!scroll_info->scrolls.size()); - DCHECK_EQ(1.f, scroll_info->page_scale_delta); #endif base::TimeDelta duration = stats_instrumentation->EndRecording(start_time); diff --git a/cc/trees/single_thread_proxy.h b/cc/trees/single_thread_proxy.h index 9f7eed4..b344cc3 100644 --- a/cc/trees/single_thread_proxy.h +++ b/cc/trees/single_thread_proxy.h @@ -32,7 +32,6 @@ class SingleThreadProxy : public Proxy, LayerTreeHostImplClient { virtual void CreateAndInitializeOutputSurface() OVERRIDE; virtual const RendererCapabilities& GetRendererCapabilities() const OVERRIDE; virtual void SetNeedsAnimate() OVERRIDE; - virtual void SetNeedsUpdateLayers() OVERRIDE; virtual void SetNeedsCommit() OVERRIDE; virtual void SetNeedsRedraw(gfx::Rect damage_rect) OVERRIDE; virtual void SetDeferCommits(bool defer_commits) OVERRIDE; diff --git a/cc/trees/thread_proxy.cc b/cc/trees/thread_proxy.cc index 775330e..2bf8247 100644 --- a/cc/trees/thread_proxy.cc +++ b/cc/trees/thread_proxy.cc @@ -90,7 +90,6 @@ ThreadProxy::ThreadProxy( using_synchronous_renderer_compositor_( layer_tree_host->settings().using_synchronous_renderer_compositor), inside_draw_(false), - can_cancel_commit_(true), defer_commits_(false), renew_tree_priority_on_impl_thread_pending_(false), draw_duration_history_(kDurationHistorySize), @@ -129,15 +128,10 @@ bool ThreadProxy::CompositeAndReadback(void* pixels, gfx::Rect rect) { &begin_frame_sent_to_main_thread_completion)); begin_frame_sent_to_main_thread_completion.Wait(); } - in_composite_and_readback_ = true; BeginFrameOnMainThread(scoped_ptr<BeginFrameAndCommitState>()); in_composite_and_readback_ = false; - // Composite and readback requires a second commit to undo any changes - // that it made. - can_cancel_commit_ = false; - // Perform a synchronous readback. ReadbackRequest request; request.rect = rect; @@ -307,17 +301,6 @@ void ThreadProxy::OnOutputSurfaceInitializeAttempted( } } -void ThreadProxy::SendCommitRequestToImplThreadIfNeeded() { - DCHECK(IsMainThread()); - if (commit_request_sent_to_impl_thread_) - return; - commit_request_sent_to_impl_thread_ = true; - Proxy::ImplThreadTaskRunner()->PostTask( - FROM_HERE, - base::Bind(&ThreadProxy::SetNeedsCommitOnImplThread, - impl_thread_weak_ptr_)); -} - const RendererCapabilities& ThreadProxy::GetRendererCapabilities() const { DCHECK(IsMainThread()); DCHECK(!layer_tree_host_->output_surface_lost()); @@ -331,26 +314,30 @@ void ThreadProxy::SetNeedsAnimate() { TRACE_EVENT0("cc", "ThreadProxy::SetNeedsAnimate"); animate_requested_ = true; - can_cancel_commit_ = false; - SendCommitRequestToImplThreadIfNeeded(); -} -void ThreadProxy::SetNeedsUpdateLayers() { - DCHECK(IsMainThread()); - SendCommitRequestToImplThreadIfNeeded(); + if (commit_request_sent_to_impl_thread_) + return; + commit_request_sent_to_impl_thread_ = true; + Proxy::ImplThreadTaskRunner()->PostTask( + FROM_HERE, + base::Bind(&ThreadProxy::SetNeedsCommitOnImplThread, + impl_thread_weak_ptr_)); } void ThreadProxy::SetNeedsCommit() { DCHECK(IsMainThread()); - // Unconditionally set here to handle SetNeedsCommit calls during a commit. - can_cancel_commit_ = false; - if (commit_requested_) return; TRACE_EVENT0("cc", "ThreadProxy::SetNeedsCommit"); commit_requested_ = true; - SendCommitRequestToImplThreadIfNeeded(); + if (commit_request_sent_to_impl_thread_) + return; + commit_request_sent_to_impl_thread_ = true; + Proxy::ImplThreadTaskRunner()->PostTask( + FROM_HERE, + base::Bind(&ThreadProxy::SetNeedsCommitOnImplThread, + impl_thread_weak_ptr_)); } void ThreadProxy::DidLoseOutputSurfaceOnImplThread() { @@ -693,23 +680,21 @@ void ThreadProxy::BeginFrameOnMainThread( // callbacks will trigger another frame. animate_requested_ = false; + if (begin_frame_state) + layer_tree_host_->ApplyScrollAndScale(*begin_frame_state->scroll_info); + if (!in_composite_and_readback_ && !layer_tree_host_->visible()) { commit_requested_ = false; commit_request_sent_to_impl_thread_ = false; TRACE_EVENT0("cc", "EarlyOut_NotVisible"); - bool did_handle = false; Proxy::ImplThreadTaskRunner()->PostTask( FROM_HERE, base::Bind(&ThreadProxy::BeginFrameAbortedByMainThreadOnImplThread, - impl_thread_weak_ptr_, - did_handle)); + impl_thread_weak_ptr_)); return; } - if (begin_frame_state) - layer_tree_host_->ApplyScrollAndScale(*begin_frame_state->scroll_info); - layer_tree_host_->WillBeginFrame(); if (begin_frame_state) { @@ -733,44 +718,24 @@ void ThreadProxy::BeginFrameOnMainThread( // UpdateLayers. commit_requested_ = false; commit_request_sent_to_impl_thread_ = false; - bool can_cancel_this_commit = - can_cancel_commit_ && !in_composite_and_readback_; - can_cancel_commit_ = true; scoped_ptr<ResourceUpdateQueue> queue = make_scoped_ptr(new ResourceUpdateQueue); - bool updated = layer_tree_host_->UpdateLayers( + layer_tree_host_->UpdateLayers( queue.get(), - begin_frame_state ? begin_frame_state->memory_allocation_limit_bytes - : 0u); + begin_frame_state ? + begin_frame_state->memory_allocation_limit_bytes : 0u); // Once single buffered layers are committed, they cannot be modified until // they are drawn by the impl thread. textures_acquired_ = false; layer_tree_host_->WillCommit(); - - if (!updated && can_cancel_this_commit) { - TRACE_EVENT0("cc", "EarlyOut_NoUpdates"); - bool did_handle = true; - Proxy::ImplThreadTaskRunner()->PostTask( - FROM_HERE, - base::Bind(&ThreadProxy::BeginFrameAbortedByMainThreadOnImplThread, - impl_thread_weak_ptr_, - did_handle)); - - // Although the commit is internally aborted, this is because it has been - // detected to be a no-op. From the perspective of an embedder, this commit - // went through, and input should no longer be throttled, etc. - layer_tree_host_->CommitComplete(); - layer_tree_host_->DidBeginFrame(); - return; - } - - // Before calling animate, we set animate_requested_ to false. If it is true - // now, it means SetNeedAnimate was called again, but during a state when - // commit_request_sent_to_impl_thread_ = true. We need to force that call to - // happen again now so that the commit request is sent to the impl thread. + // Before applying scrolls and calling animate, we set animate_requested_ to + // false. If it is true now, it means SetNeedAnimate was called again, but + // during a state when commit_request_sent_to_impl_thread_ = true. We need to + // force that call to happen again now so that the commit request is sent to + // the impl thread. if (animate_requested_) { // Forces SetNeedsAnimate to consider posting a commit task. animate_requested_ = false; @@ -866,18 +831,13 @@ void ThreadProxy::StartCommitOnImplThread( scheduler_on_impl_thread_->AnticipatedDrawTime()); } -void ThreadProxy::BeginFrameAbortedByMainThreadOnImplThread(bool did_handle) { +void ThreadProxy::BeginFrameAbortedByMainThreadOnImplThread() { TRACE_EVENT0("cc", "ThreadProxy::BeginFrameAbortedByMainThreadOnImplThread"); DCHECK(IsImplThread()); DCHECK(scheduler_on_impl_thread_); DCHECK(scheduler_on_impl_thread_->CommitPending()); - // If the begin frame data was handled, then scroll and scale set was applied - // by the main thread, so the active tree needs to be updated as if these sent - // values were applied and committed. - if (did_handle) - layer_tree_host_impl_->active_tree()->ApplySentScrollAndScaleDeltas(); - scheduler_on_impl_thread_->BeginFrameAbortedByMainThread(did_handle); + scheduler_on_impl_thread_->BeginFrameAbortedByMainThread(); } void ThreadProxy::ScheduledActionCommit() { @@ -945,8 +905,7 @@ void ThreadProxy::ScheduledActionBeginOutputSurfaceCreation() { ScheduledActionDrawAndSwapResult ThreadProxy::ScheduledActionDrawAndSwapInternal(bool forced_draw) { - TRACE_EVENT1( - "cc", "ThreadProxy::ScheduledActionDrawAndSwap", "forced", forced_draw); + TRACE_EVENT0("cc", "ThreadProxy::ScheduledActionDrawAndSwap"); ScheduledActionDrawAndSwapResult result; result.did_draw = false; @@ -1107,7 +1066,6 @@ void ThreadProxy::AcquireLayerTextures() { completion.Wait(); textures_acquired_ = true; - can_cancel_commit_ = false; } void ThreadProxy::AcquireLayerTexturesForMainThreadOnImplThread( diff --git a/cc/trees/thread_proxy.h b/cc/trees/thread_proxy.h index c9d5b47..eb2ef7e 100644 --- a/cc/trees/thread_proxy.h +++ b/cc/trees/thread_proxy.h @@ -49,7 +49,6 @@ class ThreadProxy : public Proxy, virtual void CreateAndInitializeOutputSurface() OVERRIDE; virtual const RendererCapabilities& GetRendererCapabilities() const OVERRIDE; virtual void SetNeedsAnimate() OVERRIDE; - virtual void SetNeedsUpdateLayers() OVERRIDE; virtual void SetNeedsCommit() OVERRIDE; virtual void SetNeedsRedraw(gfx::Rect damage_rect) OVERRIDE; virtual void SetDeferCommits(bool defer_commits) OVERRIDE; @@ -136,7 +135,6 @@ class ThreadProxy : public Proxy, void OnOutputSurfaceInitializeAttempted( bool success, const RendererCapabilities& capabilities); - void SendCommitRequestToImplThreadIfNeeded(); // Called on impl thread. struct ReadbackRequest; @@ -148,7 +146,7 @@ class ThreadProxy : public Proxy, CompletionEvent* completion, ResourceUpdateQueue* queue, scoped_refptr<cc::ContextProvider> offscreen_context_provider); - void BeginFrameAbortedByMainThreadOnImplThread(bool did_handle); + void BeginFrameAbortedByMainThreadOnImplThread(); void RequestReadbackOnImplThread(ReadbackRequest* request); void FinishAllRenderingOnImplThread(CompletionEvent* completion); void InitializeImplOnImplThread(CompletionEvent* completion); @@ -243,8 +241,6 @@ class ThreadProxy : public Proxy, bool inside_draw_; - bool can_cancel_commit_; - bool defer_commits_; scoped_ptr<BeginFrameAndCommitState> pending_deferred_commit_; |