diff options
author | ben@chromium.org <ben@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-09-29 20:36:29 +0000 |
---|---|---|
committer | ben@chromium.org <ben@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-09-29 20:36:29 +0000 |
commit | 6fb3c2719180afa6f2d64377b4e4c158e56637d6 (patch) | |
tree | 591418d951443528dc217b277aff113819df08b5 /views | |
parent | ae53df1368dbfb4d36b2bb6d1797e4a937b764d2 (diff) | |
download | chromium_src-6fb3c2719180afa6f2d64377b4e4c158e56637d6.zip chromium_src-6fb3c2719180afa6f2d64377b4e4c158e56637d6.tar.gz chromium_src-6fb3c2719180afa6f2d64377b4e4c158e56637d6.tar.bz2 |
Construct a View's layer immediately when SetPaintToLayer(true) is called or when a transform is set.This eliminates the need for LayerHelper since it basically just served as a middle-man for caching layer state when a layer did not exist (which occurred when a view was invisible or not part of a view hierarchy).Also includes a fix to reorder layer children properly without crashing due to dropped textures.BUG=noneTEST=existing unittests
Review URL: http://codereview.chromium.org/8054023
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@103338 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'views')
-rw-r--r-- | views/layer_helper.cc | 74 | ||||
-rw-r--r-- | views/layer_helper.h | 114 | ||||
-rw-r--r-- | views/view.cc | 275 | ||||
-rw-r--r-- | views/view.h | 73 | ||||
-rw-r--r-- | views/view_unittest.cc | 17 | ||||
-rw-r--r-- | views/views.gyp | 2 | ||||
-rw-r--r-- | views/widget/native_widget_gtk.cc | 10 | ||||
-rw-r--r-- | views/widget/native_widget_view.cc | 31 | ||||
-rw-r--r-- | views/widget/native_widget_view.h | 4 | ||||
-rw-r--r-- | views/widget/native_widget_views.cc | 12 | ||||
-rw-r--r-- | views/widget/native_widget_win.cc | 4 | ||||
-rw-r--r-- | views/widget/root_view.cc | 21 | ||||
-rw-r--r-- | views/widget/root_view.h | 2 | ||||
-rw-r--r-- | views/widget/widget.cc | 1 |
14 files changed, 173 insertions, 467 deletions
diff --git a/views/layer_helper.cc b/views/layer_helper.cc deleted file mode 100644 index 2a41b90..0000000 --- a/views/layer_helper.cc +++ /dev/null @@ -1,74 +0,0 @@ -// Copyright (c) 2011 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 "views/layer_helper.h" - -#include "views/layer_property_setter.h" -#include "ui/gfx/compositor/compositor.h" -#include "ui/gfx/compositor/layer.h" -#include "ui/gfx/transform.h" - -namespace views { - -namespace internal { - -LayerHelper::LayerHelper() - : fills_bounds_opaquely_(true), - paint_to_layer_(false), - property_setter_explicitly_set_(false), - needs_paint_all_(true) { -} - -LayerHelper::~LayerHelper() { - if (property_setter_.get() && layer_.get()) - property_setter_->Uninstalled(layer_.get()); - property_setter_.reset(); - layer_.reset(); -} - -void LayerHelper::SetTransform(const ui::Transform& transform) { - transform_.reset(transform.HasChange() ? new ui::Transform(transform) : NULL); -} - -void LayerHelper::SetLayer(ui::Layer* layer) { - if (property_setter_.get() && this->layer()) - property_setter_->Uninstalled(this->layer()); - layer_.reset(layer); - if (layer) { - if (!property_setter_.get()) - property_setter_.reset(LayerPropertySetter::CreateDefaultSetter()); - property_setter_->Installed(this->layer()); - if (layer_updated_externally()) - layer_->SetExternalTexture(external_texture_.get()); - } else if (!property_setter_explicitly_set_) { - property_setter_.reset(NULL); - } -} - -void LayerHelper::SetExternalTexture(ui::Texture* texture) { - external_texture_ = texture; - if (layer_.get()) - layer_->SetExternalTexture(texture); -} - -void LayerHelper::SetPropertySetter(LayerPropertySetter* setter) { - if (property_setter_.get() && layer()) - property_setter_->Uninstalled(layer()); - property_setter_.reset(setter); - if (layer()) { - if (!setter) - property_setter_.reset(LayerPropertySetter::CreateDefaultSetter()); - property_setter_->Installed(layer()); - } -} - -bool LayerHelper::ShouldPaintToLayer() const { - return paint_to_layer_ || - layer_updated_externally() || - (transform_.get() && transform_->HasChange()); -} - -} // namespace internal - -} // namespace views diff --git a/views/layer_helper.h b/views/layer_helper.h deleted file mode 100644 index 5246ae0..0000000 --- a/views/layer_helper.h +++ /dev/null @@ -1,114 +0,0 @@ -// Copyright (c) 2011 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. - -#ifndef VIEWS_LAYER_HELPER_H_ -#define VIEWS_LAYER_HELPER_H_ -#pragma once - -#include "base/basictypes.h" -#include "base/memory/ref_counted.h" -#include "base/memory/scoped_ptr.h" -#include "ui/gfx/rect.h" - -namespace ui { -class Layer; -class Texture; -class Transform; -} - -namespace views { - -class LayerPropertySetter; - -// This is a views-internal API and should not be used externally. View uses -// this class to manage fields related to accelerated painting. -namespace internal { - -class LayerHelper { - public: - LayerHelper(); - ~LayerHelper(); - - void SetTransform(const ui::Transform& transform); - - // Only returns non-null if a non-identity transform has been set. - const ui::Transform* transform() const { return transform_.get(); } - - void SetLayer(ui::Layer* layer); - ui::Layer* layer() { return layer_.get(); } - - // Passing NULL will cause the layer to get a texture from its compositor. - void SetExternalTexture(ui::Texture* texture); - - // Sometimes the Layer is being updated by something other than SetCanvas - // (e.g. the GPU process on TOUCH_UI). - bool layer_updated_externally() const { - return external_texture_.get() != NULL; - } - - // Rectangle that needs to be painted. - void set_clip_rect(const gfx::Rect& rect) { - clip_rect_ = rect; - } - const gfx::Rect& clip_rect() const { return clip_rect_; } - - // If true the layer was explicitly turned on. - void set_paint_to_layer(bool value) { paint_to_layer_ = value; } - bool paint_to_layer() const { return paint_to_layer_; } - - // See description in View for details - void set_fills_bounds_opaquely(bool fills_bounds_opaquely) { - fills_bounds_opaquely_ = fills_bounds_opaquely; - } - bool fills_bounds_opaquely() const { return fills_bounds_opaquely_; } - - void SetPropertySetter(LayerPropertySetter* setter); - LayerPropertySetter* property_setter() { - return property_setter_.get(); - } - - // If true the LayerPropertySetter was explicitly set. - void set_property_setter_explicitly_set(bool value) { - property_setter_explicitly_set_ = value; - } - bool property_setter_explicitly_set() { - return property_setter_explicitly_set_; - } - - // Returns true if the layer needs to be used. - bool ShouldPaintToLayer() const; - - private: - // The transformation matrix (rotation, translate, scale). If non-null the - // transform is not the identity transform. - scoped_ptr<ui::Transform> transform_; - - scoped_ptr<ui::Layer> layer_; - - scoped_ptr<LayerPropertySetter> property_setter_; - - // Used during painting. If not empty and View::Paint() is invoked, the canvas - // is created with the specified size. - // TODO(sky): this should be passed into paint. - gfx::Rect clip_rect_; - - bool fills_bounds_opaquely_; - - // Should the View paint to a layer? - bool paint_to_layer_; - - bool property_setter_explicitly_set_; - - bool needs_paint_all_; - - scoped_refptr<ui::Texture> external_texture_; - - DISALLOW_COPY_AND_ASSIGN(LayerHelper); -}; - -} // namespace internal - -} // namespace views - -#endif // VIEWS_LAYER_HELPER_H_ diff --git a/views/view.cc b/views/view.cc index 2239187..6bc4b8c 100644 --- a/views/view.cc +++ b/views/view.cc @@ -113,6 +113,7 @@ View::View() clip_y_(0.0), needs_layout_(true), flip_canvas_on_paint_for_rtl_ui_(false), + paint_to_layer_(false), accelerator_registration_delayed_(false), accelerator_focus_manager_(NULL), registered_accelerator_count_(0), @@ -170,21 +171,13 @@ void View::AddChildViewAt(View* view, int index) { view->parent_ = this; children_.insert(children_.begin() + index, view); - if (GetWidget()) { - // Sending out notification of insert may result in adding other views. - // Invoke this first to make sure we know the layer is created (if needed). - view->CreateLayerIfNecessary(); - } - for (View* v = this; v; v = v->parent_) v->ViewHierarchyChangedImpl(false, true, this, view); view->PropagateAddNotifications(this, view); UpdateTooltip(); - if (GetWidget()) { + if (GetWidget()) RegisterChildrenForVisibleBoundsNotification(view); - view->CreateLayerIfNecessary(); - } if (layout_manager_.get()) layout_manager_->ViewAdded(this, view); @@ -313,8 +306,7 @@ gfx::Rect View::GetVisibleBounds() const { ui::Transform transform; while (view != NULL && !vis_bounds.IsEmpty()) { - if (view->transform()) - transform.ConcatTransform(*view->transform()); + transform.ConcatTransform(view->GetTransform()); transform.ConcatTranslate(static_cast<float>(view->GetMirroredX()), static_cast<float>(view->y())); @@ -371,16 +363,13 @@ int View::GetHeightForWidth(int w) { void View::SetVisible(bool visible) { if (visible != visible_) { // If the View is currently visible, schedule paint to refresh parent. + // TODO(beng): not sure we should be doing this if we have a layer. if (visible_) SchedulePaint(); visible_ = visible; - - if (visible_) - CreateLayerIfNecessary(); - else - // Destroy layer if the View is invisible as invisible Views never paint. - DestroyLayerRecurse(); + if (layer()) + layer()->SetVisible(visible_); // This notifies all sub-views recursively. PropagateVisibilityNotifications(this, visible_); @@ -418,70 +407,48 @@ void View::OnEnabledChanged() { const ui::Transform& View::GetTransform() const { static const ui::Transform* no_op = new ui::Transform; - return transform() ? *transform() : *no_op; + return layer() ? layer()->transform() : *no_op; } void View::SetTransform(const ui::Transform& transform) { if (!transform.HasChange()) { - if (!layer_helper_.get() || !this->transform()) - return; - layer_helper_->SetTransform(transform); - - if (!ShouldPaintToLayer()) - DestroyLayerAndReparent(); - else if (layer()) - layer_helper_->property_setter()->SetTransform(layer(), transform); - - SchedulePaint(); - } else { - if (!layer_helper_.get()) - layer_helper_.reset(new internal::LayerHelper()); - layer_helper_->SetTransform(transform); - if (!layer()) { - CreateLayer(); - SchedulePaint(); + if (layer()) { + layer_property_setter_->SetTransform(layer(), transform); + if (!paint_to_layer_) + DestroyLayer(); } else { - layer_helper_->property_setter()->SetTransform(layer(), transform); - // We have a layer. When the transform changes and the layer is up to - // date we don't want to SchedulePaint as it'll trigger painting to the - // layer. Instead we tell the Widget to paint, which makes the - // compositor draw using the existing layer. - // We schedule paint the complete bounds as compositor generally don't - // support partial painting. - Widget* widget = GetWidget(); - if (widget) - widget->SchedulePaintInRect(widget->GetRootView()->bounds()); + // Nothing. } + } else { + if (!layer()) + CreateLayer(); + layer_property_setter_->SetTransform(layer(), transform); + if (layer()->GetCompositor()) + layer()->GetCompositor()->SchedulePaint(); } } -void View::SetPaintToLayer(bool value) { - bool paint_to_layer = layer_helper_.get() && layer_helper_->paint_to_layer(); - if (value == paint_to_layer) - return; - - if (value) { - if (!layer_helper_.get()) - layer_helper_.reset(new internal::LayerHelper()); - layer_helper_->set_paint_to_layer(true); +void View::SetPaintToLayer(bool paint_to_layer) { + paint_to_layer_ = paint_to_layer; + if (paint_to_layer_ && !layer()) { CreateLayer(); - } else if (layer_helper_.get()) { - layer_helper_->set_paint_to_layer(false); - if (!ShouldPaintToLayer()) - DestroyLayerAndReparent(); + } else if (!paint_to_layer_ && layer()) { + DestroyLayer(); } } void View::SetLayerPropertySetter(LayerPropertySetter* setter) { - if ((layer_helper_.get() && layer_helper_->property_setter() == setter) || - (!layer_helper_.get() && setter == NULL)) { + DCHECK(layer()); + LayerPropertySetter* old_setter = layer_property_setter_.get(); + if (!layer() || (old_setter && old_setter == setter)) return; - } + if (!setter) + setter = LayerPropertySetter::CreateDefaultSetter(); - if (!layer_helper_.get()) - layer_helper_.reset(new internal::LayerHelper()); - layer_helper_->set_property_setter_explicitly_set(setter != NULL); - layer_helper_->SetPropertySetter(setter); + if (old_setter) + old_setter->Uninstalled(layer()); + layer_property_setter_.reset(setter); + layer_property_setter_->Installed(layer()); } // RTL positioning ------------------------------------------------------------- @@ -657,8 +624,7 @@ void View::ConvertPointToScreen(const View* src, gfx::Point* p) { gfx::Rect View::ConvertRectToParent(const gfx::Rect& rect) const { gfx::Rect x_rect = rect; - if (transform()) - transform()->TransformRect(&x_rect); + GetTransform().TransformRect(&x_rect); x_rect.Offset(GetMirroredPosition()); return x_rect; } @@ -710,8 +676,7 @@ void View::Paint(gfx::Canvas* canvas) { // where this view is located (related to its parent). canvas->TranslateInt(GetMirroredX(), y()); - if (transform()) - canvas->Transform(*transform()); + canvas->Transform(GetTransform()); PaintCommon(canvas); } @@ -1104,23 +1069,16 @@ void View::OnPaintFocusBorder(gfx::Canvas* canvas) { // Accelerated Painting -------------------------------------------------------- void View::SetFillsBoundsOpaquely(bool fills_bounds_opaquely) { - if (!layer_helper_.get()) - layer_helper_.reset(new internal::LayerHelper()); - - layer_helper_->set_fills_bounds_opaquely(fills_bounds_opaquely); - + // This method should not have the side-effect of creating the layer. if (layer()) layer()->SetFillsBoundsOpaquely(fills_bounds_opaquely); } bool View::SetExternalTexture(ui::Texture* texture) { DCHECK(texture); - if (!layer_helper_.get()) - return true; + SetPaintToLayer(true); - if (!layer_helper_.get()) - layer_helper_.reset(new internal::LayerHelper()); - layer_helper_->SetExternalTexture(texture); + layer()->SetExternalTexture(texture); // Child views must not paint into the external texture. So make sure each // child view has its own layer to paint into. @@ -1128,18 +1086,9 @@ bool View::SetExternalTexture(ui::Texture* texture) { (*i)->SetPaintToLayer(true); SchedulePaintInRect(GetLocalBounds()); - return true; } -const ui::Compositor* View::GetCompositor() const { - return parent_ ? parent_->GetCompositor() : NULL; -} - -ui::Compositor* View::GetCompositor() { - return parent_ ? parent_->GetCompositor() : NULL; -} - void View::CalculateOffsetToAncestorWithLayer(gfx::Point* offset, ui::Layer** layer_parent) { if (layer()) { @@ -1154,13 +1103,6 @@ void View::CalculateOffsetToAncestorWithLayer(gfx::Point* offset, parent_->CalculateOffsetToAncestorWithLayer(offset, layer_parent); } -void View::CreateLayerIfNecessary() { - if (ShouldPaintToLayer()) - CreateLayer(); - - for (int i = 0, count = child_count(); i < count; ++i) - child_at(i)->CreateLayerIfNecessary(); -} void View::MoveLayerToParent(ui::Layer* parent_layer, const gfx::Point& point) { @@ -1169,29 +1111,24 @@ void View::MoveLayerToParent(ui::Layer* parent_layer, local_point.Offset(x(), y()); if (layer() && parent_layer != layer()) { parent_layer->Add(layer()); - layer()->SetBounds( - gfx::Rect(local_point.x(), local_point.y(), width(), height())); + layer()->SetBounds(gfx::Rect(local_point.x(), local_point.y(), + width(), height())); } else { for (int i = 0, count = child_count(); i < count; ++i) child_at(i)->MoveLayerToParent(parent_layer, local_point); } } -void View::DestroyLayerRecurse() { - for (int i = child_count() - 1; i >= 0; --i) - child_at(i)->DestroyLayerRecurse(); - DestroyLayer(); -} - -void View::UpdateLayerBounds(const gfx::Point& offset) { +void View::UpdateChildLayerBounds(const gfx::Point& offset) { if (layer()) { - layer_helper_->property_setter()->SetBounds( - layer(), - gfx::Rect(offset.x() + x(), offset.y() + y(), width(), height())); + layer_property_setter_->SetBounds(layer(), gfx::Rect(offset.x(), offset.y(), + width(), height())); } else { - gfx::Point new_offset(offset.x() + x(), offset.y() + y()); - for (int i = 0, count = child_count(); i < count; ++i) - child_at(i)->UpdateLayerBounds(new_offset); + for (int i = 0, count = child_count(); i < count; ++i) { + gfx::Point new_offset(offset.x() + child_at(i)->x(), + offset.y() + child_at(i)->y()); + child_at(i)->UpdateChildLayerBounds(new_offset); + } } } @@ -1485,7 +1422,6 @@ void View::DoRemoveChildView(View* view, if (GetWidget()) UnregisterChildrenForVisibleBoundsNotification(view); - view->DestroyLayerRecurse(); view->PropagateRemoveNotifications(this); view->parent_ = NULL; @@ -1547,6 +1483,9 @@ void View::ViewHierarchyChangedImpl(bool register_accelerators, } } + if (is_add && child == this && layer() && !layer()->parent()) + UpdateParentLayer(); + ViewHierarchyChanged(is_add, parent, child); parent->needs_layout_ = true; } @@ -1580,26 +1519,24 @@ void View::BoundsChanged(const gfx::Rect& previous_bounds) { gfx::Point offset; parent_->CalculateOffsetToAncestorWithLayer(&offset, NULL); offset.Offset(x(), y()); - layer_helper_->property_setter()->SetBounds( - layer(), gfx::Rect(offset, size())); + layer_property_setter_->SetBounds(layer(), gfx::Rect(offset, size())); } else { - layer_helper_->property_setter()->SetBounds(layer(), bounds_); + layer_property_setter_->SetBounds(layer(), bounds_); } + // TODO(beng): this seems redundant with the SchedulePaint at the top of + // this function. explore collapsing. if (previous_bounds.size() != bounds_.size() && !layer()->layer_updated_externally()) { // If our bounds have changed then we need to update the complete // texture. layer()->SchedulePaint(GetLocalBounds()); } - } else if (GetCompositor()) { + } else { // If our bounds have changed, then any descendant layer bounds may // have changed. Update them accordingly. gfx::Point offset; CalculateOffsetToAncestorWithLayer(&offset, NULL); - // CalculateOffsetToAncestorWithLayer includes our location as does - // UpdateLayerBounds. - offset.Offset(-x(), -y()); - UpdateLayerBounds(offset); + UpdateChildLayerBounds(offset); } } } @@ -1611,9 +1548,8 @@ void View::BoundsChanged(const gfx::Rect& previous_bounds) { Layout(); } - if (NeedsNotificationWhenVisibleBoundsChange()) { + if (NeedsNotificationWhenVisibleBoundsChange()) OnVisibleBoundsChanged(); - } // Notify interested Views that visible bounds within the root view may have // changed. @@ -1683,8 +1619,7 @@ bool View::GetTransformRelativeTo(const View* ancestor, const View* p = this; while (p && p != ancestor) { - if (p->transform()) - transform->ConcatTransform(*p->transform()); + transform->ConcatTransform(p->GetTransform()); transform->ConcatTranslate(static_cast<float>(p->GetMirroredX()), static_cast<float>(p->y())); @@ -1763,69 +1698,67 @@ bool View::ConvertPointFromAncestor(const View* ancestor, // Accelerated painting -------------------------------------------------------- -bool View::ShouldPaintToLayer() const { - return use_acceleration_when_possible && - ((layer_helper_.get() && layer_helper_->ShouldPaintToLayer()) || - (parent_ && parent_->layer() && - parent_->layer()->layer_updated_externally())); -} - void View::CreateLayer() { - if (!ShouldPaintToLayer() || layer()) - return; + layer_.reset(new ui::Layer(NULL)); + layer_->set_delegate(this); + if (layer_property_setter_.get()) + layer_property_setter_->Installed(layer()); + else + SetLayerPropertySetter(NULL); - ui::Compositor* compositor = GetCompositor(); - if (!compositor) - return; + UpdateParentLayers(); +} - DCHECK(layer_helper_.get()); +void View::UpdateParentLayers() { + // Attach all top-level un-parented layers. + if (layer() && !layer()->parent()) { + UpdateParentLayer(); + } else { + for (int i = 0, count = child_count(); i < count; ++i) + child_at(i)->UpdateParentLayers(); + } +} - ui::Layer* layer_parent = NULL; - gfx::Point offset; - CalculateOffsetToAncestorWithLayer(&offset, &layer_parent); +void View::UpdateParentLayer() { + if (!layer()) + return; - DCHECK(layer_parent || parent_ == NULL); + ui::Layer* parent_layer = NULL; + gfx::Point offset(x(), y()); + if (parent_) + parent_->CalculateOffsetToAncestorWithLayer(&offset, &parent_layer); - layer_helper_->SetLayer(new ui::Layer(compositor)); - layer()->set_delegate(this); - layer()->SetFillsBoundsOpaquely(layer_helper_->fills_bounds_opaquely()); - layer()->SetBounds(gfx::Rect(offset.x(), offset.y(), width(), height())); - layer()->SetTransform(GetTransform()); - if (layer_parent) - layer_parent->Add(layer()); - layer()->SchedulePaint(GetLocalBounds()); + ReparentLayer(offset, parent_layer); +} +void View::ReparentLayer(const gfx::Point& offset, ui::Layer* parent_layer) { + layer_->SetBounds(gfx::Rect(offset.x(), offset.y(), width(), height())); + DCHECK_NE(layer(), parent_layer); + if (parent_layer) + parent_layer->Add(layer()); + layer_->SchedulePaint(GetLocalBounds()); MoveLayerToParent(layer(), gfx::Point()); } -void View::DestroyLayerAndReparent() { - if (!layer()) - return; - +void View::DestroyLayer() { ui::Layer* new_parent = layer()->parent(); std::vector<ui::Layer*> children = layer()->children(); - for (size_t i = 0; i < children.size(); ++i) - new_parent->Add(children[i]); + for (size_t i = 0; i < children.size(); ++i) { + layer()->Remove(children[i]); + if (new_parent) + new_parent->Add(children[i]); + } + + if (layer_property_setter_.get()) + layer_property_setter_->Uninstalled(layer()); - DestroyLayer(); + layer_.reset(); gfx::Point offset; CalculateOffsetToAncestorWithLayer(&offset, NULL); - offset.Offset(-x(), -y()); - UpdateLayerBounds(offset); -} - -void View::DestroyLayer() { - if (!layer_helper_.get()) - return; + UpdateChildLayerBounds(offset); - if (!layer_helper_->property_setter_explicitly_set() && - !ShouldPaintToLayer() && - !layer_helper_->fills_bounds_opaquely() && - !layer_helper_->layer_updated_externally()) - layer_helper_.reset(); - else - layer_helper_->SetLayer(NULL); + SchedulePaint(); } // Input ----------------------------------------------------------------------- @@ -1889,8 +1822,8 @@ void View::ProcessMouseReleased(const MouseEvent& event) { } ui::TouchStatus View::ProcessTouchEvent(const TouchEvent& event) { - // TODO(rjkroege): Implement a grab scheme similar to as - // as is found in MousePressed. + // TODO(rjkroege): Implement a grab scheme similar to as as is found in + // MousePressed. return OnTouchEvent(event); } diff --git a/views/view.h b/views/view.h index 2ebd832..b83c6a2 100644 --- a/views/view.h +++ b/views/view.h @@ -23,7 +23,6 @@ #include "views/accelerator.h" #include "views/background.h" #include "views/border.h" -#include "views/layer_helper.h" using ui::OSExchangeData; @@ -256,9 +255,10 @@ class VIEWS_EXPORT View : public ui::LayerDelegate, virtual bool IsEnabled() const; // This indicates that the view completely fills its bounds in an opaque - // color. - // This doesn't affect compositing but is a hint to the compositor to optimize - // painting. + // color. This doesn't affect compositing but is a hint to the compositor to + // optimize painting. + // Note that this method does not implicitly create a layer if one does not + // already exist for the View, but is a no-op in that case. void SetFillsBoundsOpaquely(bool fills_bounds_opaquely); // Transformations ----------------------------------------------------------- @@ -284,18 +284,15 @@ class VIEWS_EXPORT View : public ui::LayerDelegate, // . SetPaintToLayer(true) has been invoked. // View creates the Layer only when it exists in a Widget with a non-NULL // Compositor. - void SetPaintToLayer(bool value); + void SetPaintToLayer(bool paint_to_layer); // Sets the LayerPropertySetter for this view. A value of NULL resets the - // LayerPropertySetter to the default (immediate). + // LayerPropertySetter to the default (immediate). Can only be called on a + // View that has a layer(). void SetLayerPropertySetter(LayerPropertySetter* setter); - const ui::Layer* layer() const { - return layer_helper_.get() ? layer_helper_->layer() : NULL; - } - ui::Layer* layer() { - return layer_helper_.get() ? layer_helper_->layer() : NULL; - } + const ui::Layer* layer() const { return layer_.get(); } + ui::Layer* layer() { return layer_.get(); } // RTL positioning ----------------------------------------------------------- @@ -972,19 +969,12 @@ class VIEWS_EXPORT View : public ui::LayerDelegate, // Returns false if it cannot create a layer to which to assign the texture. bool SetExternalTexture(ui::Texture* texture); - // Returns the Compositor. - virtual const ui::Compositor* GetCompositor() const; - virtual ui::Compositor* GetCompositor(); - // Returns the offset from this view to the nearest ancestor with a layer. // If |ancestor| is non-NULL it is set to the nearest ancestor with a layer. virtual void CalculateOffsetToAncestorWithLayer( gfx::Point* offset, ui::Layer** layer_parent); - // Creates a layer for this and recurses through all descendants. - virtual void CreateLayerIfNecessary(); - // If this view has a layer, the layer is reparented to |parent_layer| and its // bounds is set based on |point|. If this view does not have a layer, then // recurses through all children. This is used when adding a layer to an @@ -993,13 +983,9 @@ class VIEWS_EXPORT View : public ui::LayerDelegate, virtual void MoveLayerToParent(ui::Layer* parent_layer, const gfx::Point& point); - // Destroys the layer on this view and all descendants. Intended for when a - // view is being removed or made invisible. - virtual void DestroyLayerRecurse(); - - // Resets the bounds of the layer associated with this view and all - // descendants. - virtual void UpdateLayerBounds(const gfx::Point& offset); + // Called to update the bounds of any child layers within this View's + // hierarchy when something happens to the hierarchy. + virtual void UpdateChildLayerBounds(const gfx::Point& offset); // Overridden from ui::LayerDelegate: virtual void OnPaintLayer(gfx::Canvas* canvas) OVERRIDE; @@ -1235,27 +1221,26 @@ class VIEWS_EXPORT View : public ui::LayerDelegate, // hierarchy during time critical operations and this would not be needed. void set_painting_enabled(bool enabled) { painting_enabled_ = enabled; } - // Returns true if this view should paint to layer. - bool ShouldPaintToLayer() const; - // Creates the layer and related fields for this view. void CreateLayer(); - // Reparents any descendant layer to our current layer parent and destroys - // this views layer. - void DestroyLayerAndReparent(); + // Parents all un-parented layers within this view's hierarchy to this view's + // layer. + void UpdateParentLayers(); - // Destroys the layer and related fields of this view. This is intended for - // use from one of the other destroy methods, normally you shouldn't invoke - // this directly. - void DestroyLayer(); + // Updates the view's layer's parent. Called when a view is added to a view + // hierarchy, responsible for parenting the view's layer to the enclosing + // layer in the hierarchy. + void UpdateParentLayer(); - // Returns the transform, or NULL if no transform has been set or the identity - // transform was set. Be careful in using this as it may return NULL. Use - // GetTransform() if you always want a non-NULL transform. - const ui::Transform* transform() const { - return layer_helper_.get() ? layer_helper_->transform() : NULL; - } + // Parents this view's layer to |parent_layer|, and sets its bounds and other + // properties in accordance to |offset|, the view's offset from the + // |parent_layer|. + void ReparentLayer(const gfx::Point& offset, ui::Layer* parent_layer); + + // Destroys the layer associated with this view, and reparents any descendants + // to the destroyed layer's parent. + void DestroyLayer(); // Input --------------------------------------------------------------------- @@ -1392,7 +1377,9 @@ class VIEWS_EXPORT View : public ui::LayerDelegate, // Accelerated painting ------------------------------------------------------ - scoped_ptr<internal::LayerHelper> layer_helper_; + bool paint_to_layer_; + scoped_ptr<ui::Layer> layer_; + scoped_ptr<LayerPropertySetter> layer_property_setter_; // Accelerators -------------------------------------------------------------- diff --git a/views/view_unittest.cc b/views/view_unittest.cc index 3527ec2..a778436 100644 --- a/views/view_unittest.cc +++ b/views/view_unittest.cc @@ -2453,7 +2453,7 @@ TEST_F(ViewLayerTest, LayerToggling) { v1->SetPaintToLayer(true); root_layer->DrawTree(); EXPECT_EQ(1, ui::TestTexture::live_count()); - EXPECT_TRUE(v1->layer() == NULL); + EXPECT_TRUE(v1->layer() != NULL); v1->SetBounds(20, 30, 140, 150); content_view->AddChildView(v1); root_layer->DrawTree(); @@ -2627,7 +2627,7 @@ TEST_F(ViewLayerTest, ToggleVisibilityWithLayer) { EXPECT_TRUE(v1->layer()); v1->SetVisible(false); - EXPECT_TRUE(v1->layer() == NULL); + EXPECT_TRUE(v1->layer()); v1->SetVisible(true); EXPECT_TRUE(v1->layer()); @@ -2648,24 +2648,15 @@ TEST_F(ViewLayerTest, ToggleOpacityWithLayer) { child_view->SetBounds(50, 50, 100, 100); parent_view->AddChildView(child_view); - // Call SetFillsBoundsOpaquely before layer is created. ASSERT_TRUE(child_view->layer() == NULL); - child_view->SetFillsBoundsOpaquely(true); - child_view->SetPaintToLayer(true); + child_view->SetFillsBoundsOpaquely(true); ASSERT_TRUE(child_view->layer()); EXPECT_EQ( gfx::Rect(50, 50, 100, 100), parent_view->layer()->hole_rect()); child_view->SetFillsBoundsOpaquely(false); EXPECT_TRUE(parent_view->layer()->hole_rect().IsEmpty()); - - // Call SetFillsBoundsOpaquely after layer is created. - ASSERT_TRUE(parent_view->layer()); - - child_view->SetFillsBoundsOpaquely(true); - EXPECT_EQ( - gfx::Rect(50, 50, 100, 100), parent_view->layer()->hole_rect()); } // Test that a hole in a layer always corresponds to the bounds of opaque @@ -2722,8 +2713,8 @@ TEST_F(ViewLayerTest, ToggleVisibilityWithOpaqueLayer) { View* child_view = new View; child_view->SetBounds(50, 50, 100, 100); - child_view->SetFillsBoundsOpaquely(true); child_view->SetPaintToLayer(true); + child_view->SetFillsBoundsOpaquely(true); parent_view->AddChildView(child_view); EXPECT_EQ( gfx::Rect(50, 50, 100, 100), parent_view->layer()->hole_rect()); diff --git a/views/views.gyp b/views/views.gyp index e4d054e..7c36da5 100644 --- a/views/views.gyp +++ b/views/views.gyp @@ -297,8 +297,6 @@ 'ime/text_input_client.h', 'ime/text_input_type_tracker.h', 'ime/text_input_type_tracker.cc', - 'layer_helper.cc', - 'layer_helper.h', 'layer_property_setter.cc', 'layer_property_setter.h', 'layout/box_layout.cc', diff --git a/views/widget/native_widget_gtk.cc b/views/widget/native_widget_gtk.cc index 6ffa9a2..a8d3811 100644 --- a/views/widget/native_widget_gtk.cc +++ b/views/widget/native_widget_gtk.cc @@ -678,10 +678,12 @@ void NativeWidgetGtk::InitNativeWidget(const Widget::InitParams& params) { GDK_WINDOW_XID(window_contents_->window), gfx::Size(width, height)); } - if (compositor_.get()) - delegate_->AsWidget()->GetRootView()->SetPaintToLayer(true); - delegate_->AsWidget()->GetRootView()-> - SetFillsBoundsOpaquely(!transparent_); + if (compositor_.get()) { + View* root_view = delegate_->AsWidget()->GetRootView(); + root_view->SetPaintToLayer(true); + compositor_->SetRootLayer(root_view->layer()); + root_view->SetFillsBoundsOpaquely(!transparent_); + } } delegate_->OnNativeWidgetCreated(); diff --git a/views/widget/native_widget_view.cc b/views/widget/native_widget_view.cc index 059da47..1402aa3 100644 --- a/views/widget/native_widget_view.cc +++ b/views/widget/native_widget_view.cc @@ -5,6 +5,7 @@ #include "views/widget/native_widget_view.h" #include "ui/gfx/canvas.h" +#include "ui/gfx/compositor/layer.h" namespace views { namespace internal { @@ -55,9 +56,12 @@ std::string NativeWidgetView::PrintViewGraph(bool first) { void NativeWidgetView::ViewHierarchyChanged(bool is_add, View* parent, View* child) { - if (is_add && child == this && !sent_create_) { - sent_create_ = true; - delegate()->OnNativeWidgetCreated(); + if (is_add && child == this) { + GetAssociatedWidget()->GetRootView()->UpdateParentLayers(); + if (!sent_create_) { + sent_create_ = true; + delegate()->OnNativeWidgetCreated(); + } } } @@ -148,22 +152,11 @@ void NativeWidgetView::MoveLayerToParent(ui::Layer* parent_layer, } } -void NativeWidgetView::DestroyLayerRecurse() { - GetAssociatedWidget()->GetRootView()->DestroyLayerRecurse(); - View::DestroyLayerRecurse(); -} - -void NativeWidgetView::UpdateLayerBounds(const gfx::Point& offset) { - View::UpdateLayerBounds(offset); - if (!layer()) { - gfx::Point new_offset(offset.x() + x(), offset.y() + y()); - GetAssociatedWidget()->GetRootView()->UpdateLayerBounds(new_offset); - } -} - -void NativeWidgetView::CreateLayerIfNecessary() { - View::CreateLayerIfNecessary(); - GetAssociatedWidget()->GetRootView()->CreateLayerIfNecessary(); +void NativeWidgetView::UpdateChildLayerBounds(const gfx::Point& offset) { + gfx::Point new_offset(offset.x() + x(), offset.y() + y()); + View::UpdateChildLayerBounds(new_offset); + if (!layer()) + GetAssociatedWidget()->GetRootView()->UpdateChildLayerBounds(new_offset); } } // namespace internal diff --git a/views/widget/native_widget_view.h b/views/widget/native_widget_view.h index 6e1e086..813a16b 100644 --- a/views/widget/native_widget_view.h +++ b/views/widget/native_widget_view.h @@ -74,9 +74,7 @@ class VIEWS_EXPORT NativeWidgetView : public View { virtual std::string GetClassName() const OVERRIDE; virtual void MoveLayerToParent(ui::Layer* parent_layer, const gfx::Point& point) OVERRIDE; - virtual void DestroyLayerRecurse() OVERRIDE; - virtual void UpdateLayerBounds(const gfx::Point& offset) OVERRIDE; - virtual void CreateLayerIfNecessary() OVERRIDE; + virtual void UpdateChildLayerBounds(const gfx::Point& offset) OVERRIDE; internal::NativeWidgetDelegate* delegate() { return native_widget_->delegate(); diff --git a/views/widget/native_widget_views.cc b/views/widget/native_widget_views.cc index 515a9c5..dc7df81 100644 --- a/views/widget/native_widget_views.cc +++ b/views/widget/native_widget_views.cc @@ -131,13 +131,6 @@ void NativeWidgetViews::InitNativeWidget(const Widget::InitParams& params) { view_ = new internal::NativeWidgetView(this); view_->SetBoundsRect(params.bounds); -#if !defined(USE_AURA) - // TODO(beng): re-enable this once we have a consolidated layer tree. - view_->SetPaintToLayer(true); - if (View::get_use_acceleration_when_possible()) - view_->SetFillsBoundsOpaquely(!params.transparent); -#endif - view_->SetVisible(params.type == Widget::InitParams::TYPE_CONTROL); // With the default NATIVE_WIDGET_OWNS_WIDGET ownership, the @@ -150,7 +143,10 @@ void NativeWidgetViews::InitNativeWidget(const Widget::InitParams& params) { if (parent_view) parent_view->AddChildView(view_); - + view_->SetPaintToLayer(true); + if (View::get_use_acceleration_when_possible()) + view_->SetFillsBoundsOpaquely(!params.transparent); + view_->SetBoundsRect(params.bounds); // TODO(beng): SetInitParams(). } diff --git a/views/widget/native_widget_win.cc b/views/widget/native_widget_win.cc index a8b61b7..46a57e2 100644 --- a/views/widget/native_widget_win.cc +++ b/views/widget/native_widget_win.cc @@ -1286,8 +1286,10 @@ LRESULT NativeWidgetWin::OnCreate(CREATESTRUCT* create_struct) { hwnd(), gfx::Size(window_rect.Width(), window_rect.Height())); } - if (compositor_.get()) + if (compositor_.get()) { delegate_->AsWidget()->GetRootView()->SetPaintToLayer(true); + compositor_->SetRootLayer(delegate_->AsWidget()->GetRootView()->layer()); + } } #endif diff --git a/views/widget/root_view.cc b/views/widget/root_view.cc index 680ff1b..7c69e96 100644 --- a/views/widget/root_view.cc +++ b/views/widget/root_view.cc @@ -12,6 +12,7 @@ #include "ui/base/dragdrop/drag_drop_types.h" #include "ui/base/keycodes/keyboard_codes.h" #include "ui/gfx/canvas_skia.h" +#include "ui/gfx/compositor/layer.h" #include "views/focus/view_storage.h" #include "views/layout/fill_layout.h" #include "views/touchui/gesture_manager.h" @@ -155,10 +156,14 @@ std::string RootView::GetClassName() const { } void RootView::SchedulePaintInRect(const gfx::Rect& rect) { - gfx::Rect xrect = ConvertRectToParent(rect); - gfx::Rect invalid_rect = GetLocalBounds().Intersect(xrect); - if (!invalid_rect.IsEmpty()) - widget_->SchedulePaintInRect(invalid_rect); + if (layer()) { + layer()->SchedulePaint(rect); + } else { + gfx::Rect xrect = ConvertRectToParent(rect); + gfx::Rect invalid_rect = GetLocalBounds().Intersect(xrect); + if (!invalid_rect.IsEmpty()) + widget_->SchedulePaintInRect(invalid_rect); + } } bool RootView::OnMousePressed(const MouseEvent& event) { @@ -417,14 +422,6 @@ void RootView::OnPaint(gfx::Canvas* canvas) { #endif } -const ui::Compositor* RootView::GetCompositor() const { - return widget_->GetCompositor(); -} - -ui::Compositor* RootView::GetCompositor() { - return widget_->GetCompositor(); -} - void RootView::CalculateOffsetToAncestorWithLayer(gfx::Point* offset, ui::Layer** layer_parent) { View::CalculateOffsetToAncestorWithLayer(offset, layer_parent); diff --git a/views/widget/root_view.h b/views/widget/root_view.h index da8b7cf..3a2afb9 100644 --- a/views/widget/root_view.h +++ b/views/widget/root_view.h @@ -118,8 +118,6 @@ class VIEWS_EXPORT RootView : public View, public FocusTraversable { virtual void ViewHierarchyChanged(bool is_add, View* parent, View* child) OVERRIDE; virtual void OnPaint(gfx::Canvas* canvas) OVERRIDE; - virtual const ui::Compositor* GetCompositor() const OVERRIDE; - virtual ui::Compositor* GetCompositor() OVERRIDE; virtual void CalculateOffsetToAncestorWithLayer( gfx::Point* offset, ui::Layer** layer_parent) OVERRIDE; diff --git a/views/widget/widget.cc b/views/widget/widget.cc index 46ad02b..64b6670 100644 --- a/views/widget/widget.cc +++ b/views/widget/widget.cc @@ -952,7 +952,6 @@ bool Widget::OnNativeWidgetPaintAccelerated(const gfx::Rect& dirty_region) { } } - compositor->SetRootLayer(GetRootView()->layer()); compositor->Draw(force_clear); return true; } |