summaryrefslogtreecommitdiff
path: root/chromium/ui/views/bubble
diff options
context:
space:
mode:
Diffstat (limited to 'chromium/ui/views/bubble')
-rw-r--r--chromium/ui/views/bubble/bubble_border.cc87
-rw-r--r--chromium/ui/views/bubble/bubble_border.h39
-rw-r--r--chromium/ui/views/bubble/bubble_dialog_delegate_view.cc96
-rw-r--r--chromium/ui/views/bubble/bubble_dialog_delegate_view.h55
-rw-r--r--chromium/ui/views/bubble/bubble_dialog_delegate_view_unittest.cc40
-rw-r--r--chromium/ui/views/bubble/bubble_dialog_model_host.cc49
-rw-r--r--chromium/ui/views/bubble/bubble_frame_view.cc46
-rw-r--r--chromium/ui/views/bubble/bubble_frame_view.h7
-rw-r--r--chromium/ui/views/bubble/footnote_container_view.cc13
-rw-r--r--chromium/ui/views/bubble/info_bubble.cc2
-rw-r--r--chromium/ui/views/bubble/tooltip_icon.cc11
-rw-r--r--chromium/ui/views/bubble/tooltip_icon.h1
12 files changed, 280 insertions, 166 deletions
diff --git a/chromium/ui/views/bubble/bubble_border.cc b/chromium/ui/views/bubble/bubble_border.cc
index 7fb5850a438..03872cbaf0b 100644
--- a/chromium/ui/views/bubble/bubble_border.cc
+++ b/chromium/ui/views/bubble/bubble_border.cc
@@ -22,6 +22,7 @@
#include "ui/gfx/scoped_canvas.h"
#include "ui/gfx/shadow_value.h"
#include "ui/gfx/skia_paint_util.h"
+#include "ui/gfx/skia_util.h"
#include "ui/resources/grit/ui_resources.h"
#include "ui/views/layout/layout_provider.h"
#include "ui/views/painter.h"
@@ -54,6 +55,40 @@ gfx::Point RightCenter(const gfx::Rect& rect) {
return gfx::Point(rect.right(), rect.CenterPoint().y());
}
+SkColor GetKeyShadowColor(int elevation, const ui::NativeTheme* theme) {
+ switch (elevation) {
+ case 3: {
+ return theme->GetSystemColor(
+ ui::NativeTheme::kColorId_ShadowValueKeyShadowElevationThree);
+ }
+ case 16: {
+ return theme->GetSystemColor(
+ ui::NativeTheme::kColorId_ShadowValueKeyShadowElevationSixteen);
+ }
+ default:
+ // This surface has not been updated for Refresh. Fall back to the
+ // deprecated style.
+ return theme->GetSystemColor(ui::NativeTheme::kColorId_ShadowBase);
+ }
+}
+
+SkColor GetAmbientShadowColor(int elevation, const ui::NativeTheme* theme) {
+ switch (elevation) {
+ case 3: {
+ return theme->GetSystemColor(
+ ui::NativeTheme::kColorId_ShadowValueAmbientShadowElevationThree);
+ }
+ case 16: {
+ return theme->GetSystemColor(
+ ui::NativeTheme::kColorId_ShadowValueAmbientShadowElevationSixteen);
+ }
+ default:
+ // This surface has not been updated for Refresh. Fall back to the
+ // deprecated style.
+ return theme->GetSystemColor(ui::NativeTheme::kColorId_ShadowBase);
+ }
+}
+
} // namespace
BubbleBorder::BubbleBorder(Arrow arrow, Shadow shadow, SkColor color)
@@ -69,10 +104,10 @@ BubbleBorder::~BubbleBorder() = default;
// static
gfx::Insets BubbleBorder::GetBorderAndShadowInsets(
- base::Optional<int> elevation) {
+ absl::optional<int> elevation) {
// Borders with custom shadow elevations do not draw the 1px border.
if (elevation.has_value())
- return -gfx::ShadowValue::GetMargin(GetShadowValues(elevation));
+ return -gfx::ShadowValue::GetMargin(GetShadowValues(nullptr, elevation));
constexpr gfx::Insets blur(kShadowBlur + kBorderThicknessDip);
constexpr gfx::Insets offset(-kShadowVerticalOffset, 0, kShadowVerticalOffset,
@@ -217,7 +252,7 @@ void BubbleBorder::Paint(const views::View& view, gfx::Canvas* canvas) {
true /*doAntiAlias*/);
DrawBorderAndShadow(std::move(r_rect), &cc::PaintCanvas::drawRRect, canvas,
- md_shadow_elevation_, md_shadow_color_);
+ view.GetNativeTheme(), md_shadow_elevation_);
}
gfx::Insets BubbleBorder::GetInsets() const {
@@ -236,8 +271,16 @@ gfx::Size BubbleBorder::GetMinimumSize() const {
// static
const gfx::ShadowValues& BubbleBorder::GetShadowValues(
- base::Optional<int> elevation,
- SkColor color) {
+ const ui::NativeTheme* theme,
+ absl::optional<int> elevation) {
+ // If the theme does not exist the shadow values are being created in
+ // order to calculate Insets. In that case the color plays no role so always
+ // set those colors to gfx::kPlaceholderColor.
+
+ SkColor color =
+ theme ? theme->GetSystemColor(ui::NativeTheme::kColorId_ShadowBase)
+ : gfx::kPlaceholderColor;
+
// The shadows are always the same for any elevation and color combination, so
// construct them once and cache.
static base::NoDestructor<std::map<ShadowCacheKey, gfx::ShadowValues>>
@@ -250,12 +293,25 @@ const gfx::ShadowValues& BubbleBorder::GetShadowValues(
gfx::ShadowValues shadows;
if (elevation.has_value()) {
DCHECK_GE(elevation.value(), 0);
- shadows = LayoutProvider::Get()->MakeShadowValues(elevation.value(), color);
+ SkColor key_shadow_color = theme
+ ? GetKeyShadowColor(elevation.value(), theme)
+ : gfx::kPlaceholderColor;
+ SkColor ambient_shadow_color =
+ theme ? GetAmbientShadowColor(elevation.value(), theme)
+ : gfx::kPlaceholderColor;
+ shadows = gfx::ShadowValue::MakeShadowValues(
+ elevation.value(), key_shadow_color, ambient_shadow_color);
} else {
constexpr int kSmallShadowVerticalOffset = 2;
constexpr int kSmallShadowBlur = 4;
- SkColor kSmallShadowColor = SkColorSetA(color, 0x33);
- SkColor kLargeShadowColor = SkColorSetA(color, 0x1A);
+ SkColor kSmallShadowColor =
+ theme ? theme->GetSystemColor(
+ ui::NativeTheme::kColorId_BubbleBorderShadowSmall)
+ : gfx::kPlaceholderColor;
+ SkColor kLargeShadowColor =
+ theme ? theme->GetSystemColor(
+ ui::NativeTheme::kColorId_BubbleBorderShadowLarge)
+ : gfx::kPlaceholderColor;
// gfx::ShadowValue counts blur pixels both inside and outside the shape,
// whereas these blur values only describe the outside portion, hence they
// must be doubled.
@@ -273,23 +329,24 @@ const gfx::ShadowValues& BubbleBorder::GetShadowValues(
// static
const cc::PaintFlags& BubbleBorder::GetBorderAndShadowFlags(
- base::Optional<int> elevation,
- SkColor color) {
+ const ui::NativeTheme* theme,
+ absl::optional<int> elevation) {
// The flags are always the same for any elevation and color combination, so
// construct them once and cache.
static base::NoDestructor<std::map<ShadowCacheKey, cc::PaintFlags>> flag_map;
- ShadowCacheKey key(elevation.value_or(-1), color);
+ ShadowCacheKey key(
+ elevation.value_or(-1),
+ theme->GetSystemColor(ui::NativeTheme::kColorId_ShadowBase));
if (flag_map->find(key) != flag_map->end())
return flag_map->find(key)->second;
cc::PaintFlags flags;
- constexpr SkColor kBlurredBorderColor = SkColorSetA(SK_ColorBLACK, 0x26);
- flags.setColor(kBlurredBorderColor);
+ flags.setColor(theme->GetSystemColor(
+ ui::NativeTheme::kColorId_BubbleBorderWhenShadowPresent));
flags.setAntiAlias(true);
flags.setLooper(
- gfx::CreateShadowDrawLooper(GetShadowValues(elevation, color)));
-
+ gfx::CreateShadowDrawLooper(GetShadowValues(theme, elevation)));
flag_map->insert({key, flags});
return flag_map->find(key)->second;
}
diff --git a/chromium/ui/views/bubble/bubble_border.h b/chromium/ui/views/bubble/bubble_border.h
index 6622b5b978c..8330fcb9464 100644
--- a/chromium/ui/views/bubble/bubble_border.h
+++ b/chromium/ui/views/bubble/bubble_border.h
@@ -5,7 +5,6 @@
#ifndef UI_VIEWS_BUBBLE_BUBBLE_BORDER_H_
#define UI_VIEWS_BUBBLE_BUBBLE_BORDER_H_
-#include <memory>
#include "base/compiler_specific.h"
#include "base/gtest_prod_util.h"
@@ -69,7 +68,7 @@ class VIEWS_EXPORT BubbleBorder : public Border {
NO_SHADOW,
SHADOW_COUNT,
-#if defined(OS_APPLE)
+#if defined(OS_MAC)
// On Mac, the native window server should provide its own shadow for
// windows that could overlap the browser window.
DIALOG_SHADOW = NO_SHADOW,
@@ -124,18 +123,19 @@ class VIEWS_EXPORT BubbleBorder : public Border {
// |shadow_elevation|. This is only used for MD bubbles. A null
// |shadow_elevation| will yield the default BubbleBorder MD insets.
static gfx::Insets GetBorderAndShadowInsets(
- base::Optional<int> shadow_elevation = base::nullopt);
+ absl::optional<int> shadow_elevation = absl::nullopt);
// Draws a border and shadow based on |shadow_elevation| outside the |rect| on
// |canvas|, using |draw| as the draw function. Templated so as to accept
- // either SkRect or SkRRect.
+ // either SkRect or SkRRect. |theme| is passed into GetBorderAndShadowFlags to
+ // obtain the shadow color.
template <typename T>
static void DrawBorderAndShadow(
T rect,
void (cc::PaintCanvas::*draw)(const T&, const cc::PaintFlags&),
gfx::Canvas* canvas,
- base::Optional<int> shadow_elevation = base::nullopt,
- SkColor shadow_base_color = SK_ColorBLACK) {
+ const ui::NativeTheme* theme,
+ absl::optional<int> shadow_elevation = absl::nullopt) {
// Borders with custom shadow elevations do not draw the 1px border.
if (!shadow_elevation.has_value()) {
// Provide a 1 px border outside the bounds.
@@ -146,7 +146,7 @@ class VIEWS_EXPORT BubbleBorder : public Border {
}
(canvas->sk_canvas()->*draw)(
- rect, GetBorderAndShadowFlags(shadow_elevation, shadow_base_color));
+ rect, GetBorderAndShadowFlags(theme, shadow_elevation));
}
// Set the corner radius, enables Material Design.
@@ -184,11 +184,6 @@ class VIEWS_EXPORT BubbleBorder : public Border {
md_shadow_elevation_ = shadow_elevation;
}
- // Sets the shadow color for MD shadows. Defaults to SK_ColorBLACK.
- void set_md_shadow_color(SkColor shadow_color) {
- md_shadow_color_ = shadow_color;
- }
-
// Set a flag to avoid the bubble's shadow overlapping the anchor.
void set_avoid_shadow_overlap(bool value) { avoid_shadow_overlap_ = value; }
@@ -216,17 +211,21 @@ class VIEWS_EXPORT BubbleBorder : public Border {
// Returns the shadows based on |shadow_elevation| to use for painting the
// border and shadow, and for getting insets. This is only used for MD
// bubbles. A null |shadow_elevation| will yield the default BubbleBorder MD
- // ShadowValues.
+ // ShadowValues. Gets the shadow colors from |theme|. |theme| may be null in
+ // the case where GetShadowValues is called from
+ // BubbleBorder::GetBorderAndShadowInsets which only uses the ShadowValue to
+ // calculate the insets.
static const gfx::ShadowValues& GetShadowValues(
- base::Optional<int> shadow_elevation = base::nullopt,
- SkColor shadow_base_color = SK_ColorBLACK);
+ const ui::NativeTheme* theme,
+ absl::optional<int> shadow_elevation = absl::nullopt);
// Returns the paint flags to use for painting the border and shadow based on
// |shadow_elevation|. This is only used for MD bubbles. A null
// |shadow_elevation| will yield the default BubbleBorder MD PaintFlags.
+ // Gets the shadow colors from |theme|.
static const cc::PaintFlags& GetBorderAndShadowFlags(
- base::Optional<int> shadow_elevation = base::nullopt,
- SkColor shadow_base_color = SK_ColorBLACK);
+ const ui::NativeTheme* theme,
+ absl::optional<int> shadow_elevation = absl::nullopt);
// The border and arrow stroke size used in image assets, in pixels.
static constexpr int kStroke = 1;
@@ -254,13 +253,11 @@ class VIEWS_EXPORT BubbleBorder : public Border {
Shadow shadow_;
// Elevation for the MD shadow.
- base::Optional<int> md_shadow_elevation_;
- // Color for the MD shadow.
- SkColor md_shadow_color_ = SK_ColorBLACK;
+ absl::optional<int> md_shadow_elevation_;
SkColor background_color_;
bool use_theme_background_color_;
bool avoid_shadow_overlap_ = false;
- base::Optional<gfx::Insets> insets_;
+ absl::optional<gfx::Insets> insets_;
DISALLOW_COPY_AND_ASSIGN(BubbleBorder);
};
diff --git a/chromium/ui/views/bubble/bubble_dialog_delegate_view.cc b/chromium/ui/views/bubble/bubble_dialog_delegate_view.cc
index 25e492a5c66..469bdc918b1 100644
--- a/chromium/ui/views/bubble/bubble_dialog_delegate_view.cc
+++ b/chromium/ui/views/bubble/bubble_dialog_delegate_view.cc
@@ -14,7 +14,9 @@
#include "ui/accessibility/ax_node_data.h"
#include "ui/accessibility/ax_role_properties.h"
#include "ui/base/default_style.h"
+#include "ui/base/metadata/metadata_impl_macros.h"
#include "ui/base/resource/resource_bundle.h"
+#include "ui/compositor/layer.h"
#include "ui/compositor/layer_animation_element.h"
#include "ui/display/screen.h"
#include "ui/gfx/color_utils.h"
@@ -25,7 +27,6 @@
#include "ui/views/bubble/bubble_frame_view.h"
#include "ui/views/layout/layout_manager.h"
#include "ui/views/layout/layout_provider.h"
-#include "ui/views/metadata/metadata_impl_macros.h"
#include "ui/views/style/platform_style.h"
#include "ui/views/view_class_properties.h"
#include "ui/views/widget/widget.h"
@@ -35,7 +36,7 @@
#include "ui/base/win/shell.h"
#endif
-#if defined(OS_APPLE)
+#if defined(OS_MAC)
#include "ui/views/widget/widget_utils_mac.h"
#else
#include "ui/aura/window.h"
@@ -72,6 +73,14 @@ class BubbleWidget : public Widget {
return bubble_delegate->anchor_widget()->GetThemeProvider();
}
+ Widget* GetPrimaryWindowWidget() override {
+ BubbleDialogDelegateView* const bubble_delegate =
+ static_cast<BubbleDialogDelegateView*>(widget_delegate());
+ if (!bubble_delegate || !bubble_delegate->anchor_widget())
+ return Widget::GetPrimaryWindowWidget();
+ return bubble_delegate->anchor_widget()->GetPrimaryWindowWidget();
+ }
+
private:
DISALLOW_COPY_AND_ASSIGN(BubbleWidget);
};
@@ -102,6 +111,7 @@ bool CustomShadowsSupported() {
// Create a widget to host the bubble.
Widget* CreateBubbleWidget(BubbleDialogDelegate* bubble) {
+ DCHECK(bubble->owned_by_widget());
Widget* bubble_widget = new BubbleWidget();
Widget::InitParams bubble_params(Widget::InitParams::TYPE_BUBBLE);
bubble_params.delegate = bubble;
@@ -119,22 +129,24 @@ Widget* CreateBubbleWidget(BubbleDialogDelegate* bubble) {
bubble_params.shadow_type = Widget::InitParams::ShadowType::kNone;
else
bubble_params.shadow_type = Widget::InitParams::ShadowType::kDrop;
- if (bubble->parent_window()) {
- bubble_params.parent = bubble->parent_window();
- } else if (bubble->anchor_widget()) {
- bubble_params.parent = bubble->anchor_widget()->GetNativeView();
+ if (bubble->has_parent()) {
+ if (bubble->parent_window()) {
+ bubble_params.parent = bubble->parent_window();
+ } else if (bubble->anchor_widget()) {
+ bubble_params.parent = bubble->anchor_widget()->GetNativeView();
+ }
}
bubble_params.activatable = bubble->CanActivate()
- ? Widget::InitParams::ACTIVATABLE_YES
- : Widget::InitParams::ACTIVATABLE_NO;
+ ? Widget::InitParams::Activatable::kYes
+ : Widget::InitParams::Activatable::kNo;
bubble->OnBeforeBubbleWidgetInit(&bubble_params, bubble_widget);
- DCHECK(bubble_params.parent);
+ DCHECK(bubble_params.parent || !bubble->has_parent());
bubble_widget->Init(std::move(bubble_params));
-#if !defined(OS_APPLE)
+#if !defined(OS_MAC)
// On Mac, having a parent window creates a permanent stacking order, so
// there's no need to do this. Also, calling StackAbove() on Mac shows the
// bubble implicitly, for which the bubble is currently not ready.
- if (bubble_params.parent)
+ if (bubble->has_parent() && bubble_params.parent)
bubble_widget->StackAbove(bubble_params.parent);
#endif
return bubble_widget;
@@ -182,7 +194,7 @@ class BubbleDialogDelegate::AnchorViewObserver : public ViewObserver {
// This class is responsible for observing events on a BubbleDialogDelegate's
// anchor widget and notifying the BubbleDialogDelegate of them.
-#if defined(OS_APPLE)
+#if defined(OS_MAC)
class BubbleDialogDelegate::AnchorWidgetObserver : public WidgetObserver {
#else
class BubbleDialogDelegate::AnchorWidgetObserver : public WidgetObserver,
@@ -193,7 +205,7 @@ class BubbleDialogDelegate::AnchorWidgetObserver : public WidgetObserver,
AnchorWidgetObserver(BubbleDialogDelegate* owner, Widget* widget)
: owner_(owner) {
widget_observation_.Observe(widget);
-#if !defined(OS_APPLE)
+#if !defined(OS_MAC)
window_observation_.Observe(widget->GetNativeWindow());
#endif
}
@@ -201,7 +213,7 @@ class BubbleDialogDelegate::AnchorWidgetObserver : public WidgetObserver,
// WidgetObserver:
void OnWidgetDestroying(Widget* widget) override {
-#if !defined(OS_APPLE)
+#if !defined(OS_MAC)
DCHECK(window_observation_.IsObservingSource(widget->GetNativeWindow()));
window_observation_.Reset();
#endif
@@ -219,7 +231,7 @@ class BubbleDialogDelegate::AnchorWidgetObserver : public WidgetObserver,
owner_->OnAnchorBoundsChanged();
}
-#if !defined(OS_APPLE)
+#if !defined(OS_MAC)
// aura::WindowObserver:
void OnWindowTransformed(aura::Window* window,
ui::PropertyChangeReason reason) override {
@@ -239,7 +251,7 @@ class BubbleDialogDelegate::AnchorWidgetObserver : public WidgetObserver,
BubbleDialogDelegate* owner_;
base::ScopedObservation<views::Widget, views::WidgetObserver>
widget_observation_{this};
-#if !defined(OS_APPLE)
+#if !defined(OS_MAC)
base::ScopedObservation<aura::Window, aura::WindowObserver>
window_observation_{this};
#endif
@@ -301,16 +313,24 @@ class BubbleDialogDelegate::BubbleWidgetObserver : public WidgetObserver {
this};
};
-BubbleDialogDelegate::BubbleDialogDelegate() = default;
BubbleDialogDelegate::BubbleDialogDelegate(View* anchor_view,
BubbleBorder::Arrow arrow,
BubbleBorder::Shadow shadow)
- : arrow_(arrow), shadow_(shadow) {}
-BubbleDialogDelegate::~BubbleDialogDelegate() = default;
+ : arrow_(arrow), shadow_(shadow) {
+ SetAnchorView(anchor_view);
+ SetOwnedByWidget(true);
+}
+
+BubbleDialogDelegate::~BubbleDialogDelegate() {
+ SetAnchorView(nullptr);
+}
// static
Widget* BubbleDialogDelegate::CreateBubble(
- BubbleDialogDelegate* bubble_delegate) {
+ std::unique_ptr<BubbleDialogDelegate> bubble_delegate_unique) {
+ BubbleDialogDelegate* const bubble_delegate = bubble_delegate_unique.get();
+ DCHECK(bubble_delegate->owned_by_widget());
+
// On Mac, MODAL_TYPE_WINDOW is implemented using sheets, which can't be
// anchored at a specific point - they are always placed near the top center
// of the window. To avoid unpleasant surprises, disallow setting an anchor
@@ -323,7 +343,8 @@ Widget* BubbleDialogDelegate::CreateBubble(
bubble_delegate->Init();
// Get the latest anchor widget from the anchor view at bubble creation time.
bubble_delegate->SetAnchorView(bubble_delegate->GetAnchorView());
- Widget* bubble_widget = CreateBubbleWidget(bubble_delegate);
+ Widget* const bubble_widget =
+ CreateBubbleWidget(bubble_delegate_unique.release());
bubble_delegate->set_adjust_if_offscreen(
PlatformStyle::kAdjustBubbleIfOffscreen);
@@ -340,10 +361,12 @@ Widget* BubbleDialogDelegate::CreateBubble(
Widget* BubbleDialogDelegateView::CreateBubble(
std::unique_ptr<BubbleDialogDelegateView> delegate) {
- return CreateBubble(delegate.release());
+ DCHECK(delegate->owned_by_client());
+ return BubbleDialogDelegate::CreateBubble(std::move(delegate));
}
+
Widget* BubbleDialogDelegateView::CreateBubble(BubbleDialogDelegateView* view) {
- return BubbleDialogDelegate::CreateBubble(view);
+ return CreateBubble(base::WrapUnique(view));
}
BubbleDialogDelegateView::BubbleDialogDelegateView()
@@ -354,23 +377,30 @@ BubbleDialogDelegateView::BubbleDialogDelegateView(View* anchor_view,
BubbleBorder::Shadow shadow)
: BubbleDialogDelegate(anchor_view, arrow, shadow) {
set_owned_by_client();
- SetOwnedByWidget(true);
WidgetDelegate::SetShowCloseButton(false);
SetArrow(arrow);
LayoutProvider* provider = LayoutProvider::Get();
// An individual bubble should override these margins if its layout differs
// from the typical title/text/buttons.
- set_margins(provider->GetDialogInsetsForContentType(TEXT, TEXT));
+ set_margins(provider->GetDialogInsetsForContentType(
+ DialogContentType::kText, DialogContentType::kText));
set_title_margins(provider->GetInsetsMetric(INSETS_DIALOG_TITLE));
- if (anchor_view)
- SetAnchorView(anchor_view);
- UpdateColorsFromTheme();
UMA_HISTOGRAM_BOOLEAN("Dialog.BubbleDialogDelegateView.Create", true);
}
BubbleDialogDelegateView::~BubbleDialogDelegateView() {
+ // TODO(pbos): Investigate if this is actually still needed, and if so
+ // document here why that's the case. If it's due to specific client layout
+ // managers, push this down to client destructors.
SetLayoutManager(nullptr);
+ // TODO(pbos): See if we can resolve this better. This currently prevents a
+ // crash that shows up in BubbleFrameViewTest.WidthSnaps. This crash seems to
+ // happen at GetWidget()->IsVisible() inside SetAnchorView(nullptr) and seems
+ // to be as a result of WidgetDelegate's widget_ not getting updated during
+ // destruction when BubbleDialogDelegateView::DeleteDelegate() doesn't delete
+ // itself, as Widget drops a reference to widget_delegate_ and can't inform it
+ // of WidgetDeleting in ~Widget.
SetAnchorView(nullptr);
}
@@ -451,7 +481,7 @@ void BubbleDialogDelegate::OnAnchorWidgetDestroying() {
}
void BubbleDialogDelegate::OnBubbleWidgetActivationChanged(bool active) {
-#if defined(OS_APPLE)
+#if defined(OS_MAC)
// Install |mac_bubble_closer_| the first time the widget becomes active.
if (active && !mac_bubble_closer_) {
mac_bubble_closer_ = std::make_unique<ui::BubbleCloser>(
@@ -543,9 +573,8 @@ gfx::Rect BubbleDialogDelegate::GetAnchorRect() const {
return anchor_rect_.value_or(gfx::Rect());
anchor_rect_ = GetAnchorView()->GetAnchorBoundsInScreen();
- anchor_rect_->Inset(anchor_view_insets_);
-#if !defined(OS_APPLE)
+#if !defined(OS_MAC)
// GetAnchorBoundsInScreen returns values that take anchor widget's
// translation into account, so undo that here. Without this, features which
// apply transforms on windows such as ChromeOS overview mode will see bubbles
@@ -654,6 +683,9 @@ gfx::Rect BubbleDialogDelegate::GetBubbleBounds() {
}
ax::mojom::Role BubbleDialogDelegate::GetAccessibleWindowRole() {
+ if (WidgetDelegate::GetAccessibleWindowRole() == ax::mojom::Role::kNone)
+ return ax::mojom::Role::kNone;
+
// If something in the dialog has initial focus, use the dialog role.
// Screen readers understand what to announce when focus moves within one.
if (GetInitiallyFocusedView())
@@ -753,7 +785,7 @@ void BubbleDialogDelegate::SetAnchorRect(const gfx::Rect& rect) {
void BubbleDialogDelegate::SizeToContents() {
gfx::Rect bubble_bounds = GetBubbleBounds();
-#if defined(OS_APPLE)
+#if defined(OS_MAC)
// GetBubbleBounds() doesn't take the Mac NativeWindow's style mask into
// account, so we need to adjust the size.
gfx::Size actual_size =
diff --git a/chromium/ui/views/bubble/bubble_dialog_delegate_view.h b/chromium/ui/views/bubble/bubble_dialog_delegate_view.h
index 922e14c6ae2..28dffe7255b 100644
--- a/chromium/ui/views/bubble/bubble_dialog_delegate_view.h
+++ b/chromium/ui/views/bubble/bubble_dialog_delegate_view.h
@@ -12,16 +12,16 @@
#include "build/build_config.h"
#include "ui/accessibility/ax_enums.mojom-forward.h"
#include "ui/base/class_property.h"
+#include "ui/base/metadata/metadata_header_macros.h"
#include "ui/views/bubble/bubble_border.h"
#include "ui/views/bubble/bubble_frame_view.h"
-#include "ui/views/metadata/metadata_header_macros.h"
#include "ui/views/metadata/view_factory.h"
#include "ui/views/view_tracker.h"
#include "ui/views/widget/widget.h"
#include "ui/views/widget/widget_observer.h"
#include "ui/views/window/dialog_delegate.h"
-#if defined(OS_APPLE)
+#if defined(OS_MAC)
#include "ui/base/cocoa/bubble_closer.h"
#endif
@@ -36,16 +36,10 @@ class Button;
class VIEWS_EXPORT BubbleDialogDelegate : public DialogDelegate,
public ui::PropertyHandler {
public:
- enum class CloseReason {
- DEACTIVATION,
- CLOSE_BUTTON,
- UNKNOWN,
- };
-
- BubbleDialogDelegate();
- BubbleDialogDelegate(View* anchor_view,
- BubbleBorder::Arrow arrow,
- BubbleBorder::Shadow shadow);
+ BubbleDialogDelegate(
+ View* anchor_view,
+ BubbleBorder::Arrow arrow,
+ BubbleBorder::Shadow shadow = BubbleBorder::DIALOG_SHADOW);
BubbleDialogDelegate(const BubbleDialogDelegate& other) = delete;
BubbleDialogDelegate& operator=(const BubbleDialogDelegate& other) = delete;
~BubbleDialogDelegate() override;
@@ -57,6 +51,10 @@ class VIEWS_EXPORT BubbleDialogDelegate : public DialogDelegate,
ClientView* CreateClientView(Widget* widget) override;
ax::mojom::Role GetAccessibleWindowRole() override;
+ // Create and initialize the bubble Widget with proper bounds.
+ static Widget* CreateBubble(
+ std::unique_ptr<BubbleDialogDelegate> bubble_delegate);
+
//////////////////////////////////////////////////////////////////////////////
// The anchor view and rectangle:
//
@@ -79,18 +77,9 @@ class VIEWS_EXPORT BubbleDialogDelegate : public DialogDelegate,
// TODO(ellyjones): Remove overrides of GetAnchorRect() and make this not
// virtual.
virtual gfx::Rect GetAnchorRect() const;
- const base::Optional<gfx::Rect>& anchor_rect() const { return anchor_rect_; }
+ const absl::optional<gfx::Rect>& anchor_rect() const { return anchor_rect_; }
void SetAnchorRect(const gfx::Rect& rect);
- // The anchor view insets are applied to the anchor view's bounds. This is
- // used to align the bubble properly with the visual center of the anchor View
- // when the anchor View's visual center is not the same as the center of its
- // bounding box.
- // TODO(https://crbug.com/869928): Remove this concept in favor of
- // View::GetAnchorBoundsInScreen().
- const gfx::Insets& anchor_view_insets() const { return anchor_view_insets_; }
- void set_anchor_view_insets(const gfx::Insets& i) { anchor_view_insets_ = i; }
-
//////////////////////////////////////////////////////////////////////////////
// The anchor widget:
//
@@ -178,6 +167,9 @@ class VIEWS_EXPORT BubbleDialogDelegate : public DialogDelegate,
gfx::NativeView parent_window() const { return parent_window_; }
void set_parent_window(gfx::NativeView window) { parent_window_ = window; }
+ bool has_parent() { return has_parent_; }
+ void set_has_parent(bool has_parent) { has_parent_ = has_parent; }
+
// Whether the bubble accepts mouse events or not.
bool accept_events() const { return accept_events_; }
void set_accept_events(bool accept_events) { accept_events_ = accept_events; }
@@ -244,9 +236,6 @@ class VIEWS_EXPORT BubbleDialogDelegate : public DialogDelegate,
gfx::Rect screen_rect);
protected:
- // Create and initialize the bubble Widget with proper bounds.
- static Widget* CreateBubble(BubbleDialogDelegate* bubble_delegate);
-
// Override this method if you want to position the bubble regardless of its
// anchor, while retaining the other anchor view logic.
virtual gfx::Rect GetBubbleBounds();
@@ -266,6 +255,7 @@ class VIEWS_EXPORT BubbleDialogDelegate : public DialogDelegate,
// Override this to perform initialization after the Widget is created but
// before it is shown.
+ // TODO(pbos): Turn this into a (Once?)Callback and add set_init(cb).
virtual void Init() {}
// TODO(ellyjones): Replace uses of this with uses of set_color(), and/or
@@ -337,9 +327,6 @@ class VIEWS_EXPORT BubbleDialogDelegate : public DialogDelegate,
bool focus_traversable_from_anchor_view_ = true;
ViewTracker highlighted_button_tracker_;
- // Insets applied to the |anchor_view_| bounds.
- gfx::Insets anchor_view_insets_;
-
// A flag controlling bubble closure on deactivation.
bool close_on_deactivate_ = true;
@@ -347,15 +334,18 @@ class VIEWS_EXPORT BubbleDialogDelegate : public DialogDelegate,
// provided) should be highlighted when this bubble is shown.
bool highlight_button_when_shown_ = true;
- mutable base::Optional<gfx::Rect> anchor_rect_;
+ mutable absl::optional<gfx::Rect> anchor_rect_;
bool accept_events_ = true;
gfx::NativeView parent_window_ = nullptr;
+ // By default, all BubbleDialogDelegates have parent windows.
+ bool has_parent_ = true;
+
// Pointer to this bubble's ClientView.
ClientView* client_view_ = nullptr;
-#if defined(OS_APPLE)
+#if defined(OS_MAC)
// Special handler for close_on_deactivate() on Mac. Window (de)activation is
// suppressed by the WindowServer when clicking rapidly, so the bubble must
// monitor clicks as well for the desired behavior.
@@ -364,8 +354,9 @@ class VIEWS_EXPORT BubbleDialogDelegate : public DialogDelegate,
};
// BubbleDialogDelegateView is a BubbleDialogDelegate that is also a View.
-// If you can, it is better to subclass View and construct a
-// BubbleDialogDelegate instance as a member of your subclass.
+// TODO(pbos): Finish moving functionality from BubbleDialogDelegateView into
+// BubbleDialogDelegate, then document here that it's better to subclass View
+// and construct a BubbleDialogDelegate.
class VIEWS_EXPORT BubbleDialogDelegateView : public BubbleDialogDelegate,
public View {
public:
diff --git a/chromium/ui/views/bubble/bubble_dialog_delegate_view_unittest.cc b/chromium/ui/views/bubble/bubble_dialog_delegate_view_unittest.cc
index da5c3df3d05..31647fb653c 100644
--- a/chromium/ui/views/bubble/bubble_dialog_delegate_view_unittest.cc
+++ b/chromium/ui/views/bubble/bubble_dialog_delegate_view_unittest.cc
@@ -298,6 +298,21 @@ TEST_F(BubbleDialogDelegateViewTest, ResetAnchorWidget) {
EXPECT_TRUE(bubble_observer.widget_closed());
}
+TEST_F(BubbleDialogDelegateViewTest, NoParentWidget) {
+ test_views_delegate()->set_use_desktop_native_widgets(true);
+#if defined(OS_CHROMEOS)
+ test_views_delegate()->set_context(GetContext());
+#endif
+ BubbleDialogDelegateView* bubble_delegate =
+ new TestBubbleDialogDelegateView(nullptr);
+ bubble_delegate->set_has_parent(false);
+ WidgetAutoclosePtr bubble_widget(
+ BubbleDialogDelegateView::CreateBubble(std::move(bubble_delegate)));
+ EXPECT_EQ(bubble_delegate, bubble_widget->widget_delegate());
+ EXPECT_EQ(bubble_widget.get(), bubble_delegate->GetWidget());
+ EXPECT_EQ(nullptr, bubble_widget->parent());
+}
+
TEST_F(BubbleDialogDelegateViewTest, InitiallyFocusedView) {
std::unique_ptr<Widget> anchor_widget =
CreateTestWidget(Widget::InitParams::TYPE_WINDOW);
@@ -359,6 +374,17 @@ TEST_F(BubbleDialogDelegateViewTest, VisibleWhenAnchorWidgetBoundsChanged) {
EXPECT_TRUE(bubble_widget->IsVisible());
}
+TEST_F(BubbleDialogDelegateViewTest, GetPrimaryWindowWidget) {
+ std::unique_ptr<Widget> anchor_widget =
+ CreateTestWidget(Widget::InitParams::TYPE_WINDOW);
+ BubbleDialogDelegateView* bubble_delegate =
+ new TestBubbleDialogDelegateView(anchor_widget->GetContentsView());
+ Widget* bubble_widget =
+ BubbleDialogDelegateView::CreateBubble(bubble_delegate);
+ EXPECT_EQ(anchor_widget.get(), anchor_widget->GetPrimaryWindowWidget());
+ EXPECT_EQ(anchor_widget.get(), bubble_widget->GetPrimaryWindowWidget());
+}
+
// Test that setting WidgetDelegate::SetCanActivate() to false makes the
// widget created via BubbleDialogDelegateView::CreateBubble() not activatable.
TEST_F(BubbleDialogDelegateViewTest, NotActivatable) {
@@ -452,8 +478,8 @@ TEST_F(BubbleDialogDelegateViewTest, CustomTitle) {
title_view->bounds().right());
LayoutProvider* provider = LayoutProvider::Get();
- const gfx::Insets content_margins =
- provider->GetDialogInsetsForContentType(views::TEXT, views::TEXT);
+ const gfx::Insets content_margins = provider->GetDialogInsetsForContentType(
+ views::DialogContentType::kText, views::DialogContentType::kText);
const gfx::Insets title_margins =
provider->GetInsetsMetric(INSETS_DIALOG_TITLE);
EXPECT_EQ(content_margins, bubble_delegate->margins());
@@ -539,7 +565,8 @@ TEST_F(BubbleDialogDelegateViewTest, AttachedWidgetShowsInkDropWhenVisible) {
anchor_widget->SetContentsView(std::make_unique<LabelButton>(
Button::PressedCallback(), std::u16string()));
TestInkDrop* ink_drop = new TestInkDrop();
- test::InkDropHostViewTestApi(button).SetInkDrop(base::WrapUnique(ink_drop));
+ test::InkDropHostTestApi(button->ink_drop())
+ .SetInkDrop(base::WrapUnique(ink_drop));
TestBubbleDialogDelegateView* bubble_delegate =
new TestBubbleDialogDelegateView(nullptr);
bubble_delegate->set_parent_window(anchor_widget->GetNativeView());
@@ -568,7 +595,8 @@ TEST_F(BubbleDialogDelegateViewTest, VisibleWidgetShowsInkDropOnAttaching) {
anchor_widget->SetContentsView(std::make_unique<LabelButton>(
Button::PressedCallback(), std::u16string()));
TestInkDrop* ink_drop = new TestInkDrop();
- test::InkDropHostViewTestApi(button).SetInkDrop(base::WrapUnique(ink_drop));
+ test::InkDropHostTestApi(button->ink_drop())
+ .SetInkDrop(base::WrapUnique(ink_drop));
TestBubbleDialogDelegateView* bubble_delegate =
new TestBubbleDialogDelegateView(nullptr);
bubble_delegate->set_parent_window(anchor_widget->GetNativeView());
@@ -599,13 +627,13 @@ TEST_F(BubbleDialogDelegateViewTest, VisibleAnchorChanges) {
Widget* bubble_widget =
BubbleDialogDelegateView::CreateBubble(bubble_delegate);
bubble_widget->Show();
-#if defined(OS_APPLE)
+#if defined(OS_MAC)
// All child widgets make the parent paint as active on Mac.
// See https://crbug.com/1046540
EXPECT_TRUE(anchor_widget->ShouldPaintAsActive());
#else
EXPECT_FALSE(anchor_widget->ShouldPaintAsActive());
-#endif // defined(OS_APPLE)
+#endif // defined(OS_MAC)
bubble_delegate->SetAnchorView(anchor_widget->GetContentsView());
EXPECT_TRUE(anchor_widget->ShouldPaintAsActive());
diff --git a/chromium/ui/views/bubble/bubble_dialog_model_host.cc b/chromium/ui/views/bubble/bubble_dialog_model_host.cc
index 09dd2414288..cecebb97222 100644
--- a/chromium/ui/views/bubble/bubble_dialog_model_host.cc
+++ b/chromium/ui/views/bubble/bubble_dialog_model_host.cc
@@ -9,6 +9,8 @@
#include "ui/accessibility/ax_enums.mojom.h"
#include "ui/base/class_property.h"
#include "ui/base/l10n/l10n_util.h"
+#include "ui/base/metadata/metadata_header_macros.h"
+#include "ui/base/metadata/metadata_impl_macros.h"
#include "ui/base/models/combobox_model.h"
#include "ui/views/controls/button/checkbox.h"
#include "ui/views/controls/button/label_button_border.h"
@@ -21,8 +23,6 @@
#include "ui/views/layout/box_layout_view.h"
#include "ui/views/layout/fill_layout.h"
#include "ui/views/layout/layout_provider.h"
-#include "ui/views/metadata/metadata_header_macros.h"
-#include "ui/views/metadata/metadata_impl_macros.h"
#include "ui/views/view_class_properties.h"
namespace views {
@@ -31,18 +31,18 @@ namespace {
DialogContentType FieldTypeToContentType(ui::DialogModelField::Type type) {
switch (type) {
case ui::DialogModelField::kButton:
- return DialogContentType::CONTROL;
+ return DialogContentType::kControl;
case ui::DialogModelField::kBodyText:
- return DialogContentType::TEXT;
+ return DialogContentType::kText;
case ui::DialogModelField::kCheckbox:
- return DialogContentType::CONTROL;
+ return DialogContentType::kControl;
case ui::DialogModelField::kTextfield:
- return DialogContentType::CONTROL;
+ return DialogContentType::kControl;
case ui::DialogModelField::kCombobox:
- return DialogContentType::CONTROL;
+ return DialogContentType::kControl;
}
NOTREACHED();
- return DialogContentType::CONTROL;
+ return DialogContentType::kControl;
}
// A subclass of Checkbox that allows using an external Label/StyledLabel view
@@ -56,9 +56,8 @@ class CheckboxControl : public Checkbox {
: label_line_height_(label_line_height) {
auto* layout = SetLayoutManager(std::make_unique<BoxLayout>());
layout->set_between_child_spacing(LayoutProvider::Get()->GetDistanceMetric(
- views::DISTANCE_RELATED_LABEL_HORIZONTAL));
- layout->set_cross_axis_alignment(
- views::BoxLayout::CrossAxisAlignment::kStart);
+ DISTANCE_RELATED_LABEL_HORIZONTAL));
+ layout->set_cross_axis_alignment(BoxLayout::CrossAxisAlignment::kStart);
SetAssociatedLabel(label.get());
@@ -254,8 +253,8 @@ BubbleDialogModelHost::BubbleDialogModelHost(
set_close_on_deactivate(model_->close_on_deactivate(GetPassKey()));
set_fixed_width(LayoutProvider::Get()->GetDistanceMetric(
- anchor_view ? views::DISTANCE_BUBBLE_PREFERRED_WIDTH
- : views::DISTANCE_MODAL_DIALOG_PREFERRED_WIDTH));
+ anchor_view ? DISTANCE_BUBBLE_PREFERRED_WIDTH
+ : DISTANCE_MODAL_DIALOG_PREFERRED_WIDTH));
AddInitialFields();
}
@@ -284,7 +283,7 @@ View* BubbleDialogModelHost::GetInitiallyFocusedView() {
if (!model_)
return BubbleDialogDelegateView::GetInitiallyFocusedView();
- base::Optional<int> unique_id = model_->initially_focused_field(GetPassKey());
+ absl::optional<int> unique_id = model_->initially_focused_field(GetPassKey());
if (!unique_id)
return BubbleDialogDelegateView::GetInitiallyFocusedView();
@@ -363,7 +362,7 @@ void BubbleDialogModelHost::AddInitialFields() {
void BubbleDialogModelHost::UpdateSpacingAndMargins() {
const DialogContentType first_field_content_type =
children().empty()
- ? DialogContentType::CONTROL
+ ? DialogContentType::kControl
: FieldTypeToContentType(FindDialogModelHostField(children().front())
.dialog_model_field->type(GetPassKey()));
DialogContentType last_field_content_type = first_field_content_type;
@@ -378,8 +377,8 @@ void BubbleDialogModelHost::UpdateSpacingAndMargins() {
} else {
int padding_margin = LayoutProvider::Get()->GetDistanceMetric(
DISTANCE_UNRELATED_CONTROL_VERTICAL);
- if (last_field_content_type == DialogContentType::CONTROL &&
- field_content_type == DialogContentType::CONTROL) {
+ if (last_field_content_type == DialogContentType::kControl &&
+ field_content_type == DialogContentType::kControl) {
// TODO(pbos): Move DISTANCE_CONTROL_LIST_VERTICAL to
// views::LayoutProvider and replace "12" here.
padding_margin = 12;
@@ -464,17 +463,19 @@ void BubbleDialogModelHost::AddOrUpdateCombobox(
combobox->SetCallback(base::BindRepeating(
[](ui::DialogModelCombobox* model_field,
base::PassKey<DialogModelHost> pass_key, Combobox* combobox) {
- // TODO(pbos): This should be a subscription through the Combobox
- // directly, but Combobox right now doesn't support listening to
- // selected-index changes.
- model_field->OnSelectedIndexChanged(pass_key,
- combobox->GetSelectedIndex());
model_field->OnPerformAction(pass_key);
},
model_field, GetPassKey(), combobox.get()));
- // TODO(pbos): Add subscription to combobox selected-index changes.
combobox->SetSelectedIndex(model_field->selected_index());
+ property_changed_subscriptions_.push_back(
+ combobox->AddSelectedIndexChangedCallback(base::BindRepeating(
+ [](ui::DialogModelCombobox* model_field,
+ base::PassKey<DialogModelHost> pass_key, Combobox* combobox) {
+ model_field->OnSelectedIndexChanged(pass_key,
+ combobox->GetSelectedIndex());
+ },
+ model_field, GetPassKey(), combobox.get())));
const gfx::FontList& font_list = combobox->GetFontList();
AddViewForLabelAndField(model_field, model_field->label(GetPassKey()),
std::move(combobox), font_list);
@@ -493,7 +494,7 @@ void BubbleDialogModelHost::AddOrUpdateTextfield(
// If this textfield is initially focused the text should be initially
// selected as well.
- base::Optional<int> initially_focused_field_id =
+ absl::optional<int> initially_focused_field_id =
model_->initially_focused_field(GetPassKey());
if (initially_focused_field_id &&
model_field->unique_id(GetPassKey()) == initially_focused_field_id) {
diff --git a/chromium/ui/views/bubble/bubble_frame_view.cc b/chromium/ui/views/bubble/bubble_frame_view.cc
index a2380fa3ac5..a6672c5b529 100644
--- a/chromium/ui/views/bubble/bubble_frame_view.cc
+++ b/chromium/ui/views/bubble/bubble_frame_view.cc
@@ -13,7 +13,9 @@
#include "ui/base/default_style.h"
#include "ui/base/hit_test.h"
#include "ui/base/l10n/l10n_util.h"
+#include "ui/base/metadata/metadata_impl_macros.h"
#include "ui/base/resource/resource_bundle.h"
+#include "ui/compositor/layer.h"
#include "ui/compositor/paint_recorder.h"
#include "ui/display/display.h"
#include "ui/display/screen.h"
@@ -33,7 +35,6 @@
#include "ui/views/controls/image_view.h"
#include "ui/views/layout/box_layout.h"
#include "ui/views/layout/layout_provider.h"
-#include "ui/views/metadata/metadata_impl_macros.h"
#include "ui/views/paint_info.h"
#include "ui/views/resources/grit/views_resources.h"
#include "ui/views/view_class_properties.h"
@@ -316,7 +317,7 @@ void BubbleFrameView::SetTitleView(std::unique_ptr<View> title_view) {
AddChildViewAt(title_view.release(), GetIndexOf(title_icon_) + 1);
}
-void BubbleFrameView::SetProgress(base::Optional<double> progress) {
+void BubbleFrameView::SetProgress(absl::optional<double> progress) {
bool visible = progress.has_value();
progress_indicator_->SetVisible(visible);
progress_indicator_->GetViewAccessibility().OverrideIsIgnored(!visible);
@@ -324,10 +325,10 @@ void BubbleFrameView::SetProgress(base::Optional<double> progress) {
progress_indicator_->SetValue(progress.value());
}
-base::Optional<double> BubbleFrameView::GetProgress() const {
+absl::optional<double> BubbleFrameView::GetProgress() const {
if (progress_indicator_->GetVisible())
return progress_indicator_->GetValue();
- return base::nullopt;
+ return absl::nullopt;
}
gfx::Size BubbleFrameView::CalculatePreferredSize() const {
@@ -352,7 +353,7 @@ gfx::Size BubbleFrameView::GetMaximumSize() const {
// the OS doesn't give the user controls to resize a bubble.
return gfx::Size();
#else
-#if defined(OS_APPLE)
+#if defined(OS_MAC)
// Allow BubbleFrameView dialogs to be resizable on Mac.
if (GetWidget()->widget_delegate()->CanResize()) {
gfx::Size client_size = GetWidget()->client_view()->GetMaximumSize();
@@ -360,7 +361,7 @@ gfx::Size BubbleFrameView::GetMaximumSize() const {
return client_size;
return GetWindowBoundsForClientBounds(gfx::Rect(client_size)).size();
}
-#endif // OS_APPLE
+#endif // OS_MAC
// Non-dialog bubbles should be non-resizable, so its max size is its
// preferred size.
return GetPreferredSize();
@@ -391,8 +392,20 @@ void BubbleFrameView::Layout() {
header_bottom = header_view_->bounds().bottom();
}
- if (bounds.IsEmpty())
+ // Only account for footnote_container_'s height if it's visible, because
+ // content_margins_ adds extra padding even if all child views are invisible.
+ if (footnote_container_ && footnote_container_->GetVisible()) {
+ const int width = contents_bounds.width();
+ const int height = footnote_container_->GetHeightForWidth(width);
+ footnote_container_->SetBounds(
+ contents_bounds.x(), contents_bounds.bottom() - height, width, height);
+ }
+
+ NonClientFrameView::Layout();
+
+ if (bounds.IsEmpty()) {
return;
+ }
// The buttons are positioned somewhat closer to the edge of the bubble.
const int close_margin =
@@ -442,15 +455,6 @@ void BubbleFrameView::Layout() {
title_icon_->SetBounds(bounds.x(), bounds.y(), title_icon_pref_size.width(),
title_height);
-
- // Only account for footnote_container_'s height if it's visible, because
- // content_margins_ adds extra padding even if all child views are invisible.
- if (footnote_container_ && footnote_container_->GetVisible()) {
- const int width = contents_bounds.width();
- const int height = footnote_container_->GetHeightForWidth(width);
- footnote_container_->SetBounds(
- contents_bounds.x(), contents_bounds.bottom() - height, width, height);
- }
}
void BubbleFrameView::OnThemeChanged() {
@@ -469,10 +473,8 @@ void BubbleFrameView::OnThemeChanged() {
void BubbleFrameView::ViewHierarchyChanged(
const ViewHierarchyChangedDetails& details) {
- if (details.is_add && details.child == this) {
- OnThemeChanged();
+ if (details.is_add && details.child == this)
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
@@ -927,16 +929,14 @@ void BubbleFrameView::UpdateClientLayerCornerRadius() {
}
BEGIN_METADATA(BubbleFrameView, NonClientFrameView)
-ADD_PROPERTY_METADATA(base::Optional<double>, Progress)
+ADD_PROPERTY_METADATA(absl::optional<double>, Progress)
ADD_PROPERTY_METADATA(gfx::Insets, ContentMargins)
ADD_PROPERTY_METADATA(gfx::Insets, FootnoteMargins)
ADD_PROPERTY_METADATA(BubbleFrameView::PreferredArrowAdjustment,
PreferredArrowAdjustment)
ADD_PROPERTY_METADATA(int, CornerRadius)
ADD_PROPERTY_METADATA(BubbleBorder::Arrow, Arrow)
-ADD_PROPERTY_METADATA(SkColor,
- BackgroundColor,
- views::metadata::SkColorConverter)
+ADD_PROPERTY_METADATA(SkColor, BackgroundColor, ui::metadata::SkColorConverter)
END_METADATA
} // namespace views
diff --git a/chromium/ui/views/bubble/bubble_frame_view.h b/chromium/ui/views/bubble/bubble_frame_view.h
index fae2a20e1af..a2963715455 100644
--- a/chromium/ui/views/bubble/bubble_frame_view.h
+++ b/chromium/ui/views/bubble/bubble_frame_view.h
@@ -10,7 +10,7 @@
#include "base/compiler_specific.h"
#include "base/gtest_prod_util.h"
#include "base/macros.h"
-#include "base/time/time.h"
+#include "ui/base/metadata/metadata_header_macros.h"
#include "ui/gfx/font_list.h"
#include "ui/gfx/geometry/insets.h"
#include "ui/views/bubble/bubble_border.h"
@@ -18,7 +18,6 @@
#include "ui/views/controls/label.h"
#include "ui/views/controls/progress_bar.h"
#include "ui/views/input_event_activation_protector.h"
-#include "ui/views/metadata/metadata_header_macros.h"
#include "ui/views/window/non_client_view.h"
namespace gfx {
@@ -72,10 +71,10 @@ class VIEWS_EXPORT BubbleFrameView : public NonClientFrameView {
// Updates the current progress value of |progress_indicator_|. If progress is
// absent, hides |the progress_indicator|.
- void SetProgress(base::Optional<double> progress);
+ void SetProgress(absl::optional<double> progress);
// Returns the current progress value of |progress_indicator_| if
// |progress_indicator_| is visible.
- base::Optional<double> GetProgress() const;
+ absl::optional<double> GetProgress() const;
// View:
gfx::Size CalculatePreferredSize() const override;
diff --git a/chromium/ui/views/bubble/footnote_container_view.cc b/chromium/ui/views/bubble/footnote_container_view.cc
index 4c4f2c548d6..56581edb8f7 100644
--- a/chromium/ui/views/bubble/footnote_container_view.cc
+++ b/chromium/ui/views/bubble/footnote_container_view.cc
@@ -8,6 +8,7 @@
#include <utility>
#include "cc/paint/paint_flags.h"
+#include "ui/base/metadata/metadata_impl_macros.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/color_palette.h"
#include "ui/gfx/geometry/rect_f.h"
@@ -15,7 +16,6 @@
#include "ui/views/background.h"
#include "ui/views/border.h"
#include "ui/views/layout/box_layout.h"
-#include "ui/views/metadata/metadata_impl_macros.h"
namespace views {
@@ -54,10 +54,10 @@ class HalfRoundedRectBackground : public Background {
FootnoteContainerView::FootnoteContainerView(const gfx::Insets& margins,
std::unique_ptr<View> child_view,
- float corner_radius) {
+ float corner_radius)
+ : corner_radius_(corner_radius) {
SetLayoutManager(std::make_unique<BoxLayout>(
BoxLayout::Orientation::kVertical, margins, 0));
- SetCornerRadius(corner_radius);
auto* child_view_ptr = AddChildView(std::move(child_view));
SetVisible(child_view_ptr->GetVisible());
}
@@ -66,7 +66,8 @@ FootnoteContainerView::~FootnoteContainerView() = default;
void FootnoteContainerView::SetCornerRadius(float corner_radius) {
corner_radius_ = corner_radius;
- ResetBackground();
+ if (GetWidget())
+ ResetBackground();
}
void FootnoteContainerView::OnThemeChanged() {
@@ -81,6 +82,8 @@ void FootnoteContainerView::ChildVisibilityChanged(View* child) {
}
void FootnoteContainerView::ResetBackground() {
+ if (!GetWidget())
+ return;
SkColor background_color = GetNativeTheme()->GetSystemColor(
ui::NativeTheme::kColorId_BubbleFooterBackground);
SetBackground(std::make_unique<HalfRoundedRectBackground>(background_color,
@@ -88,6 +91,8 @@ void FootnoteContainerView::ResetBackground() {
}
void FootnoteContainerView::ResetBorder() {
+ if (!GetWidget())
+ return;
SetBorder(CreateSolidSidedBorder(
1, 0, 0, 0, GetNativeTheme()->GetSystemColor(
ui::NativeTheme::kColorId_FootnoteContainerBorder)));
diff --git a/chromium/ui/views/bubble/info_bubble.cc b/chromium/ui/views/bubble/info_bubble.cc
index 8126ba8b4b0..874d69ccc0d 100644
--- a/chromium/ui/views/bubble/info_bubble.cc
+++ b/chromium/ui/views/bubble/info_bubble.cc
@@ -7,6 +7,7 @@
#include <memory>
#include <utility>
+#include "ui/base/metadata/metadata_impl_macros.h"
#include "ui/gfx/geometry/point.h"
#include "ui/gfx/geometry/rect.h"
#include "ui/gfx/geometry/size.h"
@@ -15,7 +16,6 @@
#include "ui/views/controls/label.h"
#include "ui/views/layout/fill_layout.h"
#include "ui/views/layout/layout_provider.h"
-#include "ui/views/metadata/metadata_impl_macros.h"
#include "ui/views/widget/widget.h"
namespace views {
diff --git a/chromium/ui/views/bubble/tooltip_icon.cc b/chromium/ui/views/bubble/tooltip_icon.cc
index a28440a4194..ad55cfa5eb3 100644
--- a/chromium/ui/views/bubble/tooltip_icon.cc
+++ b/chromium/ui/views/bubble/tooltip_icon.cc
@@ -8,10 +8,10 @@
#include "components/vector_icons/vector_icons.h"
#include "ui/accessibility/ax_enums.mojom.h"
#include "ui/accessibility/ax_node_data.h"
+#include "ui/base/metadata/metadata_impl_macros.h"
#include "ui/gfx/paint_vector_icon.h"
#include "ui/views/bubble/bubble_frame_view.h"
#include "ui/views/bubble/info_bubble.h"
-#include "ui/views/metadata/metadata_impl_macros.h"
#include "ui/views/mouse_watcher_view_host.h"
namespace views {
@@ -21,9 +21,7 @@ TooltipIcon::TooltipIcon(const std::u16string& tooltip, int tooltip_icon_size)
tooltip_icon_size_(tooltip_icon_size),
mouse_inside_(false),
bubble_(nullptr),
- preferred_width_(0) {
- SetDrawAsHovered(false);
-}
+ preferred_width_(0) {}
TooltipIcon::~TooltipIcon() {
for (auto& observer : observers_)
@@ -58,6 +56,11 @@ void TooltipIcon::GetAccessibleNodeData(ui::AXNodeData* node_data) {
node_data->SetName(tooltip_);
}
+void TooltipIcon::OnThemeChanged() {
+ ImageView::OnThemeChanged();
+ SetDrawAsHovered(false);
+}
+
void TooltipIcon::MouseMovedOutOfHost() {
if (IsMouseHovered()) {
mouse_watcher_->Start(GetWidget()->GetNativeWindow());
diff --git a/chromium/ui/views/bubble/tooltip_icon.h b/chromium/ui/views/bubble/tooltip_icon.h
index 8d42550efe7..ccc303fda33 100644
--- a/chromium/ui/views/bubble/tooltip_icon.h
+++ b/chromium/ui/views/bubble/tooltip_icon.h
@@ -47,6 +47,7 @@ class VIEWS_EXPORT TooltipIcon : public ImageView,
bool OnMousePressed(const ui::MouseEvent& event) override;
void OnGestureEvent(ui::GestureEvent* event) override;
void GetAccessibleNodeData(ui::AXNodeData* node_data) override;
+ void OnThemeChanged() override;
// MouseWatcherListener:
void MouseMovedOutOfHost() override;