Commit 43298a05 authored by Thomas Lukaszewicz's avatar Thomas Lukaszewicz Committed by Commit Bot

Views: Update MD rounded corners to use fast path

Currently MD rounded corners are using layer masking to achieve the
desired clip for client views. This CL updates client views to make
use of the ui:Layer SetRoundedCornerRadius() fast path that
significantly improves performance vs layer masking.

Bug: 822075
Change-Id: I113c6b0101145518962b22940f653fb2cc93381f
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2359027
Commit-Queue: Thomas Lukaszewicz <tluk@chromium.org>
Reviewed-by: default avatarElly Fong-Jones <ellyjones@chromium.org>
Cr-Commit-Position: refs/heads/master@{#798900}
parent 2ed50ff3
......@@ -18,6 +18,7 @@
#include "ui/compositor/layer_animation_element.h"
#include "ui/gfx/color_utils.h"
#include "ui/gfx/geometry/rect.h"
#include "ui/gfx/geometry/rounded_corners_f.h"
#include "ui/gfx/geometry/vector2d_conversions.h"
#include "ui/native_theme/native_theme.h"
#include "ui/views/bubble/bubble_frame_view.h"
......@@ -387,13 +388,17 @@ BubbleDialogDelegate::CreateNonClientFrameView(Widget* widget) {
ClientView* BubbleDialogDelegate::CreateClientView(Widget* widget) {
client_view_ = DialogDelegate::CreateClientView(widget);
// In order for the |client_view|'s content view hierarchy to respect its clip
// mask we must paint to a layer. This is necessary because layers do not
// respect the clip of a non-layer backed parent.
// In order for the |client_view|'s content view hierarchy to respect its
// rounded corner clip we must paint the client view to a layer. This is
// necessary because layers do not respect the clip of a non-layer backed
// parent.
if (base::FeatureList::IsEnabled(
features::kEnableMDRoundedCornersOnDialogs) &&
GetProperty(kPaintClientToLayer)) {
client_view_->SetPaintToLayer();
client_view_->layer()->SetRoundedCornerRadius(
gfx::RoundedCornersF(GetCornerRadius()));
client_view_->layer()->SetIsFastRoundedCorner(true);
}
return client_view_;
......
......@@ -185,6 +185,17 @@ bool BubbleFrameView::GetClientMask(const gfx::Size& size, SkPath* path) const {
DCHECK_EQ(GetBoundsForClientView().size(), size);
DCHECK_EQ(GetWidget()->client_view()->size(), size);
// BubbleFrameView only returns a SkPath for the purpose of clipping the
// client view's corners so that it fits within the borders of its rounded
// frame. With MD rounded coners if a client view is painted to a layer the
// rounding is handled by the |SetRoundedCornerRadius()| layer API, so we
// return false here.
if (base::FeatureList::IsEnabled(
features::kEnableMDRoundedCornersOnDialogs) &&
GetWidget()->client_view()->layer()) {
return false;
}
const gfx::RoundedCornersF corner_radii = GetClientCornerRadii();
// If corner radii are all zero we do not need to apply a mask.
......@@ -450,8 +461,16 @@ void BubbleFrameView::OnThemeChanged() {
void BubbleFrameView::ViewHierarchyChanged(
const ViewHierarchyChangedDetails& details) {
if (details.is_add && details.child == this)
if (details.is_add && details.child == this) {
OnThemeChanged();
UpdateClientLayerCornerRadius();
}
// We need to update the client view's corner radius whenever the header or
// footer are added/removed from the bubble frame so that the client view
// sits flush with both.
if (details.parent == this)
UpdateClientLayerCornerRadius();
if (!details.is_add && details.parent == footnote_container_ &&
footnote_container_->children().size() == 1 &&
......@@ -861,4 +880,13 @@ int BubbleFrameView::GetHeaderHeightForFrameWidth(int frame_width) const {
: 0;
}
void BubbleFrameView::UpdateClientLayerCornerRadius() {
if (GetWidget() && GetWidget()->client_view()->layer() &&
base::FeatureList::IsEnabled(
features::kEnableMDRoundedCornersOnDialogs)) {
GetWidget()->client_view()->layer()->SetRoundedCornerRadius(
GetClientCornerRadii());
}
}
} // namespace views
......@@ -241,6 +241,12 @@ class VIEWS_EXPORT BubbleFrameView : public NonClientFrameView,
// if there is no header view or if it is not visible.
int GetHeaderHeightForFrameWidth(int frame_width) const;
// Updates the corner radius of a layer backed client view for MD rounded
// corners.
// TODO(tluk): Use this and remove the need for GetClientMask() for clipping
// client views to the bubble border's bounds.
void UpdateClientLayerCornerRadius();
// The bubble border.
BubbleBorder* bubble_border_ = nullptr;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment