diff options
author | ccameron <ccameron@chromium.org> | 2015-11-26 16:52:33 -0800 |
---|---|---|
committer | Commit bot <commit-bot@chromium.org> | 2015-11-27 00:53:57 +0000 |
commit | a54da38a2d8b44643a70b1fbe8297f8fd2365f9c (patch) | |
tree | af26de27c15c50bf373759d71a3aef2745c7b4a7 /cc/layers/painted_scrollbar_layer_unittest.cc | |
parent | cc7032a14feed29b3eec8e33e161489f7d1a45b8 (diff) | |
download | chromium_src-a54da38a2d8b44643a70b1fbe8297f8fd2365f9c.zip chromium_src-a54da38a2d8b44643a70b1fbe8297f8fd2365f9c.tar.gz chromium_src-a54da38a2d8b44643a70b1fbe8297f8fd2365f9c.tar.bz2 |
Mac: Don't repaint scrollbars every frame
The core issue here is that Blink, when it sees that it needs to
change the scrollbar in any way (even just moving the thumb), uses the
signal blink::Scrollbar::setNeedsPaintInvalidation(). This will trigger
a call to cc::PaintedScrollbarLayer::Update(), which will re-paint all
controls into textures and then emit quads the quads for the controls.
We often only need to re-arrange the quads for the controls of the
scrollbar, not re-paint them.
The system that knows whether or not the controls need to be
repainted is blink::ScrollbarTheme (because that's the code that knows
the theme that will be used to do the painting).
Add blink::ScrollbarTheme::shouldRepaintAllPartsOnInvalidation() to
indicate if a call to blink::Scrollbar::setNeedsPaintInvalidation()
should cause re-painting of all of the controls. If this returns false
for a given theme, then methods blink::Scrollbar::setNeedsPaintTrack()
and blink::Scrollbar::setNeedsPaintThumb() may be used to specify more
granular control.
Back in cc::PaintedScrollbarLayer::Update(), use the methods
cc::Scrollbar::NeedsPaintPart() to check if re-paint is needed (it is
hooked up to the bit that is set by the blink::Scrollbar methods).
While we're in the neighborhood, it is worth noting that most of the
repainting of scrollbars on Mac is due to the alpha of the thumb or the
track changing. Add methods to blink::Scrollbar to query the opacity
of the controls, so that we can do the blending at compositing time
instead of requiring a repaint.
And, while we're in that neighborhood, fix cc::CALayerOverlay's
FromTextureQuad function to correctly take into account per-vertex
opacity.
BUG=549277
TEST=
- Set the system to only show scrollbars while scrolling
- Open a page with a vertical scrollbar
- Scroll to make the scroll thumb appear
- Hover the mouse somewhere below the thumb
- The thumb should become thicker and the track should appear
- After some time, the thumb and the track should fade away
TEST=
- Open a page with a scrollbar and search (command-F) for some text
- Ensure that the ticks on the vertical scrollbar appear
CQ_INCLUDE_TRYBOTS=tryserver.blink:linux_blink_rel
Review URL: https://codereview.chromium.org/1458703010
Cr-Commit-Position: refs/heads/master@{#361938}
Diffstat (limited to 'cc/layers/painted_scrollbar_layer_unittest.cc')
-rw-r--r-- | cc/layers/painted_scrollbar_layer_unittest.cc | 87 |
1 files changed, 87 insertions, 0 deletions
diff --git a/cc/layers/painted_scrollbar_layer_unittest.cc b/cc/layers/painted_scrollbar_layer_unittest.cc new file mode 100644 index 0000000..ac814ee --- /dev/null +++ b/cc/layers/painted_scrollbar_layer_unittest.cc @@ -0,0 +1,87 @@ +// Copyright 2015 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "cc/layers/painted_scrollbar_layer.h" + +#include "cc/layers/layer_settings.h" +#include "cc/test/fake_layer_tree_host.h" +#include "cc/test/fake_layer_tree_host_client.h" +#include "cc/test/fake_scrollbar.h" +#include "cc/test/test_task_graph_runner.h" +#include "testing/gmock/include/gmock/gmock.h" + +using ::testing::Mock; +using ::testing::_; + +namespace cc { + +namespace { + +class MockScrollbar : public FakeScrollbar { + public: + MockScrollbar() : FakeScrollbar(true, true, true) {} + MOCK_METHOD3(PaintPart, + void(SkCanvas* canvas, + ScrollbarPart part, + const gfx::Rect& content_rect)); +}; + +TEST(PaintedScrollbarLayerTest, NeedsPaint) { + FakeLayerTreeHostClient fake_client_(FakeLayerTreeHostClient::DIRECT_3D); + TestTaskGraphRunner task_graph_runner_; + scoped_ptr<FakeLayerTreeHost> layer_tree_host_; + LayerSettings layer_settings_; + + layer_tree_host_ = + FakeLayerTreeHost::Create(&fake_client_, &task_graph_runner_); + RendererCapabilities renderer_capabilities; + renderer_capabilities.max_texture_size = 2048; + layer_tree_host_->set_renderer_capabilities(renderer_capabilities); + + MockScrollbar* scrollbar = new MockScrollbar(); + scoped_refptr<PaintedScrollbarLayer> scrollbar_layer = + PaintedScrollbarLayer::Create(layer_settings_, + scoped_ptr<Scrollbar>(scrollbar).Pass(), 1); + + scrollbar_layer->SetIsDrawable(true); + scrollbar_layer->SetBounds(gfx::Size(100, 100)); + + layer_tree_host_->SetRootLayer(scrollbar_layer); + EXPECT_EQ(scrollbar_layer->layer_tree_host(), layer_tree_host_.get()); + scrollbar_layer->SavePaintProperties(); + + // Request no paint, but expect them to be painted because they have not + // yet been initialized. + scrollbar->set_needs_paint_thumb(false); + scrollbar->set_needs_paint_track(false); + EXPECT_CALL(*scrollbar, PaintPart(_, THUMB, _)).Times(1); + EXPECT_CALL(*scrollbar, PaintPart(_, TRACK, _)).Times(1); + scrollbar_layer->Update(); + Mock::VerifyAndClearExpectations(scrollbar); + + // The next update will paint nothing because the first update caused a paint. + EXPECT_CALL(*scrollbar, PaintPart(_, THUMB, _)).Times(0); + EXPECT_CALL(*scrollbar, PaintPart(_, TRACK, _)).Times(0); + scrollbar_layer->Update(); + Mock::VerifyAndClearExpectations(scrollbar); + + // Enable the thumb. + EXPECT_CALL(*scrollbar, PaintPart(_, THUMB, _)).Times(1); + EXPECT_CALL(*scrollbar, PaintPart(_, TRACK, _)).Times(0); + scrollbar->set_needs_paint_thumb(true); + scrollbar->set_needs_paint_track(false); + scrollbar_layer->Update(); + Mock::VerifyAndClearExpectations(scrollbar); + + // Enable the track. + EXPECT_CALL(*scrollbar, PaintPart(_, THUMB, _)).Times(0); + EXPECT_CALL(*scrollbar, PaintPart(_, TRACK, _)).Times(1); + scrollbar->set_needs_paint_thumb(false); + scrollbar->set_needs_paint_track(true); + scrollbar_layer->Update(); + Mock::VerifyAndClearExpectations(scrollbar); +} + +} // namespace +} // namespace cc |