Commit ad7e5862 authored by Tatsuhisa Yamaguchi's avatar Tatsuhisa Yamaguchi Committed by Commit Bot

Unified: Anchor system tray bubble to the shelf rect.

The design spec states tray bubble should be anchored to:
- right-bottom (when the shelf is positioned to the bottom or right)
- or left-bottom (when the shelf is positioned to the left)
corner of the workspace.

The bubble went to wrong positions when changing the device mode
between tablet and laptop, or rotating the screen, while the system
tray bubble is opened. This change is a fix for it.


Bug: 864939, 812536
Change-Id: I1392a2d96c72e06c4e8e159f22901720da72747a
Reviewed-on: https://chromium-review.googlesource.com/1246082
Commit-Queue: Tatsuhisa Yamaguchi <yamaguchi@chromium.org>
Reviewed-by: default avatarYoshiki Iguchi <yoshiki@chromium.org>
Reviewed-by: default avatarXiyuan Xia <xiyuan@chromium.org>
Cr-Commit-Position: refs/heads/master@{#594630}
parent ca393e72
...@@ -209,7 +209,7 @@ int Shelf::GetDockedMagnifierHeight() const { ...@@ -209,7 +209,7 @@ int Shelf::GetDockedMagnifierHeight() const {
: 0; : 0;
} }
gfx::Rect Shelf::GetIdealBounds() { gfx::Rect Shelf::GetIdealBounds() const {
return shelf_layout_manager_->GetIdealBounds(); return shelf_layout_manager_->GetIdealBounds();
} }
...@@ -298,6 +298,21 @@ TrayBackgroundView* Shelf::GetSystemTrayAnchor() const { ...@@ -298,6 +298,21 @@ TrayBackgroundView* Shelf::GetSystemTrayAnchor() const {
return GetStatusAreaWidget()->GetSystemTrayAnchor(); return GetStatusAreaWidget()->GetSystemTrayAnchor();
} }
gfx::Rect Shelf::GetSystemTrayAnchorRect() const {
gfx::Rect shelf_bounds = GetIdealBounds();
switch (alignment_) {
case SHELF_ALIGNMENT_BOTTOM:
case SHELF_ALIGNMENT_BOTTOM_LOCKED:
return gfx::Rect(shelf_bounds.right(), shelf_bounds.y(), 0, 0);
case SHELF_ALIGNMENT_LEFT:
return gfx::Rect(shelf_bounds.right(), shelf_bounds.bottom(), 0, 0);
case SHELF_ALIGNMENT_RIGHT:
return gfx::Rect(shelf_bounds.x(), shelf_bounds.bottom(), 0, 0);
}
NOTREACHED();
return gfx::Rect();
}
bool Shelf::ShouldHideOnSecondaryDisplay(session_manager::SessionState state) { bool Shelf::ShouldHideOnSecondaryDisplay(session_manager::SessionState state) {
if (Shell::GetPrimaryRootWindowController()->shelf() == this) if (Shell::GetPrimaryRootWindowController()->shelf() == this)
return false; return false;
......
...@@ -102,7 +102,7 @@ class ASH_EXPORT Shelf : public ShelfLayoutManagerObserver { ...@@ -102,7 +102,7 @@ class ASH_EXPORT Shelf : public ShelfLayoutManagerObserver {
int GetDockedMagnifierHeight() const; int GetDockedMagnifierHeight() const;
// Returns the ideal bounds of the shelf assuming it is visible. // Returns the ideal bounds of the shelf assuming it is visible.
gfx::Rect GetIdealBounds(); gfx::Rect GetIdealBounds() const;
gfx::Rect GetUserWorkAreaBounds() const; gfx::Rect GetUserWorkAreaBounds() const;
...@@ -140,6 +140,12 @@ class ASH_EXPORT Shelf : public ShelfLayoutManagerObserver { ...@@ -140,6 +140,12 @@ class ASH_EXPORT Shelf : public ShelfLayoutManagerObserver {
// bubble will be anchored. See also: StatusAreaWidget::GetSystemTrayAnchor() // bubble will be anchored. See also: StatusAreaWidget::GetSystemTrayAnchor()
TrayBackgroundView* GetSystemTrayAnchor() const; TrayBackgroundView* GetSystemTrayAnchor() const;
// Get the anchor rect that the system tray bubble and the notification center
// bubble will be anchored.
// x() and y() designates anchor point, but width() and height() are dummy.
// See also: BubbleDialogDelegateView::GetBubbleBounds()
gfx::Rect GetSystemTrayAnchorRect() const;
void set_is_tablet_mode_animation_running(bool value) { void set_is_tablet_mode_animation_running(bool value) {
is_tablet_mode_animation_running_ = value; is_tablet_mode_animation_running_ = value;
} }
......
...@@ -210,7 +210,7 @@ bool ShelfLayoutManager::IsVisible() const { ...@@ -210,7 +210,7 @@ bool ShelfLayoutManager::IsVisible() const {
state_.auto_hide_state == SHELF_AUTO_HIDE_SHOWN)); state_.auto_hide_state == SHELF_AUTO_HIDE_SHOWN));
} }
gfx::Rect ShelfLayoutManager::GetIdealBounds() { gfx::Rect ShelfLayoutManager::GetIdealBounds() const {
const int shelf_size = ShelfConstants::shelf_size(); const int shelf_size = ShelfConstants::shelf_size();
aura::Window* shelf_window = shelf_widget_->GetNativeWindow(); aura::Window* shelf_window = shelf_widget_->GetNativeWindow();
gfx::Rect rect(screen_util::GetDisplayBoundsInParent(shelf_window)); gfx::Rect rect(screen_util::GetDisplayBoundsInParent(shelf_window));
......
...@@ -80,7 +80,7 @@ class ASH_EXPORT ShelfLayoutManager ...@@ -80,7 +80,7 @@ class ASH_EXPORT ShelfLayoutManager
bool IsVisible() const; bool IsVisible() const;
// Returns the ideal bounds of the shelf assuming it is visible. // Returns the ideal bounds of the shelf assuming it is visible.
gfx::Rect GetIdealBounds(); gfx::Rect GetIdealBounds() const;
// Returns the preferred size of the shelf for the target visibility state. // Returns the preferred size of the shelf for the target visibility state.
gfx::Size GetPreferredSize(); gfx::Size GetPreferredSize();
......
...@@ -231,6 +231,11 @@ TrayBubbleView::TrayBubbleView(const InitParams& init_params) ...@@ -231,6 +231,11 @@ TrayBubbleView::TrayBubbleView(const InitParams& init_params)
auto layout = std::make_unique<BottomAlignedBoxLayout>(this); auto layout = std::make_unique<BottomAlignedBoxLayout>(this);
layout->SetDefaultFlex(1); layout->SetDefaultFlex(1);
layout_ = SetLayoutManager(std::move(layout)); layout_ = SetLayoutManager(std::move(layout));
if (init_params.anchor_mode == AnchorMode::kRect) {
SetAnchorView(nullptr);
SetAnchorRect(init_params.anchor_rect);
}
} }
TrayBubbleView::~TrayBubbleView() { TrayBubbleView::~TrayBubbleView() {
...@@ -306,9 +311,20 @@ void TrayBubbleView::ResetDelegate() { ...@@ -306,9 +311,20 @@ void TrayBubbleView::ResetDelegate() {
} }
void TrayBubbleView::ChangeAnchorView(views::View* anchor_view) { void TrayBubbleView::ChangeAnchorView(views::View* anchor_view) {
DCHECK(params_.anchor_mode == AnchorMode::kView);
BubbleDialogDelegateView::SetAnchorView(anchor_view); BubbleDialogDelegateView::SetAnchorView(anchor_view);
} }
void TrayBubbleView::ChangeAnchorRect(const gfx::Rect& rect) {
DCHECK(params_.anchor_mode == AnchorMode::kRect);
BubbleDialogDelegateView::SetAnchorRect(rect);
}
void TrayBubbleView::ChangeAnchorAlignment(
TrayBubbleView::AnchorAlignment alignment) {
SetArrow(GetArrowAlignment(alignment));
}
int TrayBubbleView::GetDialogButtons() const { int TrayBubbleView::GetDialogButtons() const {
return ui::DIALOG_BUTTON_NONE; return ui::DIALOG_BUTTON_NONE;
} }
......
...@@ -12,6 +12,7 @@ ...@@ -12,6 +12,7 @@
#include "base/optional.h" #include "base/optional.h"
#include "ui/accessibility/ax_enums.mojom.h" #include "ui/accessibility/ax_enums.mojom.h"
#include "ui/events/event.h" #include "ui/events/event.h"
#include "ui/gfx/geometry/rect.h"
#include "ui/gfx/native_widget_types.h" #include "ui/gfx/native_widget_types.h"
#include "ui/views/bubble/bubble_dialog_delegate_view.h" #include "ui/views/bubble/bubble_dialog_delegate_view.h"
#include "ui/views/mouse_watcher.h" #include "ui/views/mouse_watcher.h"
...@@ -85,12 +86,23 @@ class ASH_EXPORT TrayBubbleView : public views::BubbleDialogDelegateView, ...@@ -85,12 +86,23 @@ class ASH_EXPORT TrayBubbleView : public views::BubbleDialogDelegateView,
DISALLOW_COPY_AND_ASSIGN(Delegate); DISALLOW_COPY_AND_ASSIGN(Delegate);
}; };
// Anchor mode being set at creation.
enum class AnchorMode {
// Anchor to |anchor_view|. This is the default.
kView,
// Anchor to |anchor_rect|. Used for anchoring to the shelf.
kRect
};
struct ASH_EXPORT InitParams { struct ASH_EXPORT InitParams {
InitParams(); InitParams();
InitParams(const InitParams& other); InitParams(const InitParams& other);
Delegate* delegate = nullptr; Delegate* delegate = nullptr;
gfx::NativeWindow parent_window = nullptr; gfx::NativeWindow parent_window = nullptr;
View* anchor_view = nullptr; View* anchor_view = nullptr;
AnchorMode anchor_mode = AnchorMode::kView;
// Only used if anchor_mode == AnchorMode::kRect.
gfx::Rect anchor_rect;
AnchorAlignment anchor_alignment = ANCHOR_ALIGNMENT_BOTTOM; AnchorAlignment anchor_alignment = ANCHOR_ALIGNMENT_BOTTOM;
int min_width = 0; int min_width = 0;
int max_width = 0; int max_width = 0;
...@@ -135,8 +147,16 @@ class ASH_EXPORT TrayBubbleView : public views::BubbleDialogDelegateView, ...@@ -135,8 +147,16 @@ class ASH_EXPORT TrayBubbleView : public views::BubbleDialogDelegateView,
void ResetDelegate(); void ResetDelegate();
// Anchors the bubble to |anchor_view|. // Anchors the bubble to |anchor_view|.
// Only eligible if anchor_mode == AnchorMode::kView.
void ChangeAnchorView(views::View* anchor_view); void ChangeAnchorView(views::View* anchor_view);
// Anchors the bubble to |anchor_rect|. Exclusive with ChangeAnchorView().
// Only eligible if anchor_mode == AnchorMode::kRect.
void ChangeAnchorRect(const gfx::Rect& anchor_rect);
// Change anchor alignment mode when anchoring either the rect or view.
void ChangeAnchorAlignment(AnchorAlignment alignment);
Delegate* delegate() { return delegate_; } Delegate* delegate() { return delegate_; }
void set_gesture_dragging(bool dragging) { is_gesture_dragging_ = dragging; } void set_gesture_dragging(bool dragging) { is_gesture_dragging_ = dragging; }
......
...@@ -76,6 +76,8 @@ UnifiedSystemTrayBubble::UnifiedSystemTrayBubble(UnifiedSystemTray* tray, ...@@ -76,6 +76,8 @@ UnifiedSystemTrayBubble::UnifiedSystemTrayBubble(UnifiedSystemTray* tray,
init_params.parent_window = tray->GetBubbleWindowContainer(); init_params.parent_window = tray->GetBubbleWindowContainer();
init_params.anchor_view = init_params.anchor_view =
tray->shelf()->GetSystemTrayAnchor()->GetBubbleAnchor(); tray->shelf()->GetSystemTrayAnchor()->GetBubbleAnchor();
init_params.anchor_mode = TrayBubbleView::AnchorMode::kRect;
init_params.anchor_rect = tray->shelf()->GetSystemTrayAnchorRect();
init_params.corner_radius = kUnifiedTrayCornerRadius; init_params.corner_radius = kUnifiedTrayCornerRadius;
init_params.has_shadow = false; init_params.has_shadow = false;
init_params.show_by_click = show_by_click; init_params.show_by_click = show_by_click;
...@@ -294,22 +296,8 @@ void UnifiedSystemTrayBubble::UpdateBubbleBounds() { ...@@ -294,22 +296,8 @@ void UnifiedSystemTrayBubble::UpdateBubbleBounds() {
int max_height = CalculateMaxHeight(); int max_height = CalculateMaxHeight();
unified_view_->SetMaxHeight(max_height); unified_view_->SetMaxHeight(max_height);
bubble_view_->SetMaxHeight(max_height); bubble_view_->SetMaxHeight(max_height);
// If the bubble is open while switching to and from tablet mode, change the bubble_view_->ChangeAnchorAlignment(tray_->GetAnchorAlignment());
// bubble anchor if needed. The new anchor view may also have a translation bubble_view_->ChangeAnchorRect(tray_->shelf()->GetSystemTrayAnchorRect());
// applied to it so shift the bubble bounds so that it appears in the correct
// location.
bubble_view_->ChangeAnchorView(
tray_->shelf()->GetSystemTrayAnchor()->GetBubbleAnchor());
gfx::Rect bounds =
bubble_view_->GetWidget()->GetNativeWindow()->GetBoundsInScreen();
const gfx::Vector2dF translation = tray_->shelf()
->GetSystemTrayAnchor()
->layer()
->transform()
.To2dTranslation();
bounds.set_x(bounds.x() - translation.x());
bounds.set_y(bounds.y() - translation.y());
bubble_view_->GetWidget()->GetNativeWindow()->SetBounds(bounds);
} }
void UnifiedSystemTrayBubble::CreateBlurLayerForAnimation() { void UnifiedSystemTrayBubble::CreateBlurLayerForAnimation() {
......
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