| Index: ash/system/tray/tray_bubble_view.cc
|
| diff --git a/ash/system/tray/tray_bubble_view.cc b/ash/system/tray/tray_bubble_view.cc
|
| index e8ee90853ee780b57b3e0cd369953339df60b77c..96897d89de866562446b5a3bb00293ffc0d442b1 100644
|
| --- a/ash/system/tray/tray_bubble_view.cc
|
| +++ b/ash/system/tray/tray_bubble_view.cc
|
| @@ -4,14 +4,6 @@
|
|
|
| #include "ash/system/tray/tray_bubble_view.h"
|
|
|
| -#include "ash/root_window_controller.h"
|
| -#include "ash/shell.h"
|
| -#include "ash/shell_window_ids.h"
|
| -#include "ash/system/tray/tray_constants.h"
|
| -#include "ash/wm/property_util.h"
|
| -#include "ash/wm/shelf_layout_manager.h"
|
| -#include "ash/wm/window_animations.h"
|
| -#include "grit/ash_strings.h"
|
| #include "third_party/skia/include/core/SkCanvas.h"
|
| #include "third_party/skia/include/core/SkColor.h"
|
| #include "third_party/skia/include/core/SkPaint.h"
|
| @@ -24,21 +16,20 @@
|
| #include "ui/gfx/canvas.h"
|
| #include "ui/gfx/insets.h"
|
| #include "ui/gfx/path.h"
|
| -#include "ui/gfx/screen.h"
|
| #include "ui/gfx/skia_util.h"
|
| #include "ui/views/bubble/bubble_frame_view.h"
|
| #include "ui/views/layout/box_layout.h"
|
| #include "ui/views/widget/widget.h"
|
|
|
| -namespace ash {
|
| -
|
| -namespace internal {
|
| +namespace {
|
|
|
| // Inset the arrow a bit from the edge.
|
| const int kArrowMinOffset = 20;
|
| const int kBubbleSpacing = 20;
|
|
|
| -const int kAnimationDurationForPopupMS = 200;
|
| +} // namespace
|
| +
|
| +namespace ash {
|
|
|
| // Custom border for TrayBubbleView. Contains special logic for GetBounds()
|
| // to stack bubbles with no arrows correctly. Also calculates the arrow offset.
|
| @@ -46,9 +37,8 @@ class TrayBubbleBorder : public views::BubbleBorder {
|
| public:
|
| TrayBubbleBorder(views::View* owner,
|
| views::View* anchor,
|
| - views::BubbleBorder::ArrowLocation arrow_location,
|
| TrayBubbleView::InitParams params)
|
| - : views::BubbleBorder(arrow_location, params.shadow),
|
| + : views::BubbleBorder(params.arrow_location, params.shadow),
|
| owner_(owner),
|
| anchor_(anchor),
|
| tray_arrow_offset_(params.arrow_offset) {
|
| @@ -87,7 +77,7 @@ class TrayBubbleBorder : public views::BubbleBorder {
|
| arrow_location() == views::BubbleBorder::BOTTOM_LEFT) {
|
| // Note: tray_arrow_offset_ is relative to the anchor widget.
|
| if (tray_arrow_offset_ ==
|
| - internal::TrayBubbleView::InitParams::kArrowDefaultOffset) {
|
| + TrayBubbleView::InitParams::kArrowDefaultOffset) {
|
| arrow_offset = kArrowMinOffset;
|
| } else {
|
| const int width = owner_->GetWidget()->GetContentsView()->width();
|
| @@ -103,7 +93,7 @@ class TrayBubbleBorder : public views::BubbleBorder {
|
| }
|
| } else {
|
| if (tray_arrow_offset_ ==
|
| - internal::TrayBubbleView::InitParams::kArrowDefaultOffset) {
|
| + TrayBubbleView::InitParams::kArrowDefaultOffset) {
|
| arrow_offset = kArrowMinOffset;
|
| } else {
|
| gfx::Point pt(0, tray_arrow_offset_);
|
| @@ -185,7 +175,7 @@ class TrayBubbleBackground : public views::Background {
|
| // enough height. Otherwise, makes sure the bottom rows are visible.
|
| class BottomAlignedBoxLayout : public views::BoxLayout {
|
| public:
|
| - explicit BottomAlignedBoxLayout(internal::TrayBubbleView* bubble_view)
|
| + explicit BottomAlignedBoxLayout(TrayBubbleView* bubble_view)
|
| : views::BoxLayout(views::BoxLayout::kVertical, 0, 0, 0),
|
| bubble_view_(bubble_view) {
|
| }
|
| @@ -213,7 +203,7 @@ class BottomAlignedBoxLayout : public views::BoxLayout {
|
| }
|
| }
|
|
|
| - internal::TrayBubbleView* bubble_view_;
|
| + TrayBubbleView* bubble_view_;
|
|
|
| DISALLOW_COPY_AND_ASSIGN(BottomAlignedBoxLayout);
|
| };
|
| @@ -222,62 +212,60 @@ class BottomAlignedBoxLayout : public views::BoxLayout {
|
| const int TrayBubbleView::InitParams::kArrowDefaultOffset = -1;
|
|
|
| TrayBubbleView::InitParams::InitParams(AnchorType anchor_type,
|
| - ShelfAlignment shelf_alignment)
|
| + AnchorAlignment anchor_alignment,
|
| + int bubble_width)
|
| : anchor_type(anchor_type),
|
| - shelf_alignment(shelf_alignment),
|
| - bubble_width(kTrayPopupWidth),
|
| + anchor_alignment(anchor_alignment),
|
| + bubble_width(bubble_width),
|
| max_height(0),
|
| can_activate(false),
|
| close_on_deactivate(true),
|
| top_color(SK_ColorBLACK),
|
| arrow_color(SK_ColorBLACK),
|
| + arrow_location(views::BubbleBorder::NONE),
|
| arrow_offset(kArrowDefaultOffset),
|
| shadow(views::BubbleBorder::BIG_SHADOW) {
|
| }
|
|
|
| -TrayBubbleView* TrayBubbleView::Create(views::View* anchor,
|
| - Host* host,
|
| - const InitParams& init_params) {
|
| +TrayBubbleView* TrayBubbleView::Create(aura::Window* parent_window,
|
| + views::View* anchor,
|
| + Delegate* delegate,
|
| + InitParams* init_params) {
|
| // Set arrow_location here so that it can be passed correctly to the
|
| // BubbleView constructor.
|
| - views::BubbleBorder::ArrowLocation arrow_location;
|
| - if (init_params.anchor_type == ANCHOR_TYPE_TRAY) {
|
| - if (init_params.shelf_alignment == SHELF_ALIGNMENT_BOTTOM) {
|
| - arrow_location = base::i18n::IsRTL() ?
|
| + if (init_params->anchor_type == ANCHOR_TYPE_TRAY) {
|
| + if (init_params->anchor_alignment == ANCHOR_ALIGNMENT_BOTTOM) {
|
| + init_params->arrow_location = base::i18n::IsRTL() ?
|
| views::BubbleBorder::BOTTOM_LEFT : views::BubbleBorder::BOTTOM_RIGHT;
|
| - } else if (init_params.shelf_alignment == SHELF_ALIGNMENT_LEFT) {
|
| - arrow_location = views::BubbleBorder::LEFT_BOTTOM;
|
| + } else if (init_params->anchor_alignment == ANCHOR_ALIGNMENT_LEFT) {
|
| + init_params->arrow_location = views::BubbleBorder::LEFT_BOTTOM;
|
| } else {
|
| - arrow_location = views::BubbleBorder::RIGHT_BOTTOM;
|
| + init_params->arrow_location = views::BubbleBorder::RIGHT_BOTTOM;
|
| }
|
| } else {
|
| - arrow_location = views::BubbleBorder::NONE;
|
| + init_params->arrow_location = views::BubbleBorder::NONE;
|
| }
|
|
|
| - return new TrayBubbleView(init_params, arrow_location, anchor, host);
|
| + return new TrayBubbleView(parent_window, anchor, delegate, *init_params);
|
| }
|
|
|
| -TrayBubbleView::TrayBubbleView(
|
| - const InitParams& init_params,
|
| - views::BubbleBorder::ArrowLocation arrow_location,
|
| - views::View* anchor,
|
| - Host* host)
|
| - : views::BubbleDelegateView(anchor, arrow_location),
|
| +TrayBubbleView::TrayBubbleView(aura::Window* parent_window,
|
| + views::View* anchor,
|
| + Delegate* delegate,
|
| + const InitParams& init_params)
|
| + : views::BubbleDelegateView(anchor, init_params.arrow_location),
|
| params_(init_params),
|
| - host_(host),
|
| + delegate_(delegate),
|
| bubble_border_(NULL),
|
| bubble_background_(NULL),
|
| is_gesture_dragging_(false) {
|
| - set_parent_window(Shell::GetContainer(
|
| - anchor->GetWidget()->GetNativeWindow()->GetRootWindow(),
|
| - internal::kShellWindowId_SettingBubbleContainer));
|
| + set_parent_window(parent_window);
|
| set_notify_enter_exit_on_child(true);
|
| set_close_on_deactivate(init_params.close_on_deactivate);
|
| SetPaintToLayer(true);
|
| SetFillsBoundsOpaquely(true);
|
|
|
| - bubble_border_ = new TrayBubbleBorder(
|
| - this, anchor_view(), arrow_location, params_);
|
| + bubble_border_ = new TrayBubbleBorder(this, anchor_view(), params_);
|
|
|
| bubble_background_ = new TrayBubbleBackground(
|
| bubble_border_, init_params.top_color, init_params.arrow_color);
|
| @@ -290,8 +278,17 @@ TrayBubbleView::TrayBubbleView(
|
|
|
| TrayBubbleView::~TrayBubbleView() {
|
| // Inform host items (models) that their views are being destroyed.
|
| - if (host_)
|
| - host_->BubbleViewDestroyed();
|
| + if (delegate_)
|
| + delegate_->BubbleViewDestroyed();
|
| +}
|
| +
|
| +void TrayBubbleView::InitializeAndShowBubble() {
|
| + // Must occur after call to BubbleDelegateView::CreateBubble().
|
| + SetAlignment(views::BubbleBorder::ALIGN_EDGE_TO_ANCHOR_EDGE);
|
| + bubble_border_->UpdateArrowOffset();
|
| +
|
| + Show();
|
| + UpdateBubble();
|
| }
|
|
|
| void TrayBubbleView::UpdateBubble() {
|
| @@ -305,6 +302,10 @@ void TrayBubbleView::SetMaxHeight(int height) {
|
| SizeToContents();
|
| }
|
|
|
| +void TrayBubbleView::GetBorderInsets(gfx::Insets* insets) const {
|
| + bubble_border_->GetInsets(insets);
|
| +}
|
| +
|
| void TrayBubbleView::Init() {
|
| views::BoxLayout* layout = new BottomAlignedBoxLayout(this);
|
| layout->set_spread_blank_space(true);
|
| @@ -312,47 +313,11 @@ void TrayBubbleView::Init() {
|
| }
|
|
|
| gfx::Rect TrayBubbleView::GetAnchorRect() {
|
| - gfx::Rect rect;
|
| -
|
| - if (anchor_widget() && anchor_widget()->IsVisible()) {
|
| - rect = anchor_widget()->GetWindowBoundsInScreen();
|
| - if (params_.anchor_type == ANCHOR_TYPE_TRAY) {
|
| - if (params_.shelf_alignment == SHELF_ALIGNMENT_BOTTOM) {
|
| - bool rtl = base::i18n::IsRTL();
|
| - rect.Inset(
|
| - rtl ? kPaddingFromRightEdgeOfScreenBottomAlignment : 0,
|
| - 0,
|
| - rtl ? 0 : kPaddingFromRightEdgeOfScreenBottomAlignment,
|
| - kPaddingFromBottomOfScreenBottomAlignment);
|
| - } else if (params_.shelf_alignment == SHELF_ALIGNMENT_LEFT) {
|
| - rect.Inset(0, 0, kPaddingFromInnerEdgeOfLauncherVerticalAlignment,
|
| - kPaddingFromBottomOfScreenVerticalAlignment);
|
| - } else {
|
| - rect.Inset(kPaddingFromInnerEdgeOfLauncherVerticalAlignment,
|
| - 0, 0, kPaddingFromBottomOfScreenVerticalAlignment);
|
| - }
|
| - } else if (params_.anchor_type == ANCHOR_TYPE_BUBBLE) {
|
| - // Invert the offsets to align with the bubble below.
|
| - if (params_.shelf_alignment == SHELF_ALIGNMENT_LEFT) {
|
| - rect.Inset(kPaddingFromInnerEdgeOfLauncherVerticalAlignment,
|
| - 0, 0, kPaddingFromBottomOfScreenVerticalAlignment);
|
| - } else if (params_.shelf_alignment == SHELF_ALIGNMENT_RIGHT) {
|
| - rect.Inset(0, 0, kPaddingFromInnerEdgeOfLauncherVerticalAlignment,
|
| - kPaddingFromBottomOfScreenVerticalAlignment);
|
| - }
|
| - }
|
| - }
|
| -
|
| - // TODO(jennyz): May need to add left/right alignment in the following code.
|
| - if (rect.IsEmpty()) {
|
| - rect = Shell::GetScreen()->GetPrimaryDisplay().bounds();
|
| - rect = gfx::Rect(
|
| - base::i18n::IsRTL() ? kPaddingFromRightEdgeOfScreenBottomAlignment :
|
| - rect.width() - kPaddingFromRightEdgeOfScreenBottomAlignment,
|
| - rect.height() - kPaddingFromBottomOfScreenBottomAlignment,
|
| - 0, 0);
|
| - }
|
| - return rect;
|
| + if (!delegate_)
|
| + return gfx::Rect();
|
| + return delegate_->GetAnchorRect(anchor_widget(),
|
| + params_.anchor_type,
|
| + params_.anchor_alignment);
|
| }
|
|
|
| bool TrayBubbleView::CanActivate() const {
|
| @@ -386,19 +351,19 @@ gfx::Size TrayBubbleView::GetPreferredSize() {
|
| }
|
|
|
| void TrayBubbleView::OnMouseEntered(const ui::MouseEvent& event) {
|
| - if (host_)
|
| - host_->OnMouseEnteredView();
|
| + if (delegate_)
|
| + delegate_->OnMouseEnteredView();
|
| }
|
|
|
| void TrayBubbleView::OnMouseExited(const ui::MouseEvent& event) {
|
| - if (host_)
|
| - host_->OnMouseExitedView();
|
| + if (delegate_)
|
| + delegate_->OnMouseExitedView();
|
| }
|
|
|
| void TrayBubbleView::GetAccessibleState(ui::AccessibleViewState* state) {
|
| if (params_.can_activate) {
|
| state->role = ui::AccessibilityTypes::ROLE_WINDOW;
|
| - state->name = host_->GetAccessibleName();
|
| + state->name = delegate_->GetAccessibleName();
|
| }
|
| }
|
|
|
| @@ -416,101 +381,4 @@ void TrayBubbleView::ViewHierarchyChanged(bool is_add,
|
| }
|
| }
|
|
|
| -TrayBubbleView::Host::Host()
|
| - : widget_(NULL),
|
| - bubble_view_(NULL),
|
| - tray_view_(NULL) {
|
| - Shell::GetInstance()->AddEnvEventFilter(this);
|
| -}
|
| -
|
| -TrayBubbleView::Host::~Host() {
|
| - Shell::GetInstance()->RemoveEnvEventFilter(this);
|
| -}
|
| -
|
| -void TrayBubbleView::Host::InitializeAndShowBubble(views::Widget* widget,
|
| - TrayBubbleView* bubble_view,
|
| - views::View* tray_view) {
|
| - widget_ = widget;
|
| - bubble_view_ = bubble_view;
|
| - tray_view_ = tray_view;
|
| -
|
| - // Must occur after call to BubbleDelegateView::CreateBubble().
|
| - bubble_view->SetAlignment(views::BubbleBorder::ALIGN_EDGE_TO_ANCHOR_EDGE);
|
| -
|
| - bubble_view->bubble_border()->UpdateArrowOffset();
|
| -
|
| - // Setup animation.
|
| - ash::SetWindowVisibilityAnimationType(
|
| - widget->GetNativeWindow(),
|
| - ash::WINDOW_VISIBILITY_ANIMATION_TYPE_FADE);
|
| - ash::SetWindowVisibilityAnimationTransition(
|
| - widget->GetNativeWindow(),
|
| - ash::ANIMATE_BOTH);
|
| - ash::SetWindowVisibilityAnimationDuration(
|
| - widget->GetNativeWindow(),
|
| - base::TimeDelta::FromMilliseconds(kAnimationDurationForPopupMS));
|
| -
|
| - bubble_view->Show();
|
| - bubble_view->UpdateBubble();
|
| -}
|
| -
|
| -bool TrayBubbleView::Host::PreHandleKeyEvent(aura::Window* target,
|
| - ui::KeyEvent* event) {
|
| - return false;
|
| -}
|
| -
|
| -bool TrayBubbleView::Host::PreHandleMouseEvent(aura::Window* target,
|
| - ui::MouseEvent* event) {
|
| - if (event->type() == ui::ET_MOUSE_PRESSED)
|
| - ProcessLocatedEvent(target, *event);
|
| - return false;
|
| -}
|
| -
|
| -ui::TouchStatus TrayBubbleView::Host::PreHandleTouchEvent(
|
| - aura::Window* target,
|
| - ui::TouchEvent* event) {
|
| - if (event->type() == ui::ET_TOUCH_PRESSED)
|
| - ProcessLocatedEvent(target, *event);
|
| - return ui::TOUCH_STATUS_UNKNOWN;
|
| -}
|
| -
|
| -ui::EventResult TrayBubbleView::Host::PreHandleGestureEvent(
|
| - aura::Window* target,
|
| - ui::GestureEvent* event) {
|
| - return ui::ER_UNHANDLED;
|
| -}
|
| -
|
| -void TrayBubbleView::Host::ProcessLocatedEvent(
|
| - aura::Window* target, const ui::LocatedEvent& event) {
|
| - if (target) {
|
| - // Don't process events that occurred inside an embedded menu.
|
| - RootWindowController* root_controller =
|
| - GetRootWindowController(target->GetRootWindow());
|
| - if (root_controller && root_controller->GetContainer(
|
| - ash::internal::kShellWindowId_MenuContainer)->Contains(target)) {
|
| - return;
|
| - }
|
| - }
|
| - if (!widget_)
|
| - return;
|
| - gfx::Rect bounds = widget_->GetWindowBoundsInScreen();
|
| - gfx::Insets insets;
|
| - bubble_view_->bubble_border()->GetInsets(&insets);
|
| - bounds.Inset(insets);
|
| - if (bounds.Contains(event.root_location()))
|
| - return;
|
| - if (tray_view_) {
|
| - // If the user clicks on the parent tray, don't process the event here,
|
| - // let the tray logic handle the event and determine show/hide behavior.
|
| - bounds = tray_view_->GetWidget()->GetClientAreaBoundsInScreen();
|
| - if (bounds.Contains(event.root_location()))
|
| - return;
|
| - }
|
| - // Handle clicking outside the bubble and tray. We don't block the event, so
|
| - // it will also be handled by whatever widget was clicked on.
|
| - OnClickedOutsideView();
|
| -}
|
| -
|
| -
|
| -} // namespace internal
|
| } // namespace ash
|
|
|