Home | History | Annotate | Download | only in shelf
      1 // Copyright 2013 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #include "ash/shelf/overflow_bubble.h"
      6 
      7 #include "ash/root_window_controller.h"
      8 #include "ash/shelf/overflow_bubble_view.h"
      9 #include "ash/shelf/shelf_layout_manager.h"
     10 #include "ash/shelf/shelf_view.h"
     11 #include "ash/shelf/shelf_widget.h"
     12 #include "ash/shell.h"
     13 #include "ash/system/tray/system_tray.h"
     14 #include "ui/aura/client/screen_position_client.h"
     15 #include "ui/aura/window_event_dispatcher.h"
     16 #include "ui/events/event.h"
     17 #include "ui/gfx/screen.h"
     18 #include "ui/views/widget/widget.h"
     19 
     20 namespace ash {
     21 
     22 OverflowBubble::OverflowBubble()
     23     : bubble_(NULL),
     24       anchor_(NULL),
     25       shelf_view_(NULL) {
     26 }
     27 
     28 OverflowBubble::~OverflowBubble() {
     29   Hide();
     30 }
     31 
     32 void OverflowBubble::Show(views::View* anchor, ShelfView* shelf_view) {
     33   Hide();
     34 
     35   bubble_ = new OverflowBubbleView();
     36   bubble_->InitOverflowBubble(anchor, shelf_view);
     37   shelf_view_ = shelf_view;
     38   anchor_ = anchor;
     39 
     40   Shell::GetInstance()->AddPreTargetHandler(this);
     41 
     42   RootWindowController::ForWindow(anchor->GetWidget()->GetNativeView())->
     43       GetSystemTray()->InitializeBubbleAnimations(bubble_->GetWidget());
     44   bubble_->GetWidget()->AddObserver(this);
     45   bubble_->GetWidget()->Show();
     46 }
     47 
     48 void OverflowBubble::Hide() {
     49   if (!IsShowing())
     50     return;
     51 
     52   Shell::GetInstance()->RemovePreTargetHandler(this);
     53   bubble_->GetWidget()->RemoveObserver(this);
     54   bubble_->GetWidget()->Close();
     55   bubble_ = NULL;
     56   anchor_ = NULL;
     57   shelf_view_ = NULL;
     58 }
     59 
     60 void OverflowBubble::HideBubbleAndRefreshButton() {
     61   if (!IsShowing())
     62     return;
     63 
     64   views::View* anchor = anchor_;
     65   Hide();
     66   // Update overflow button (|anchor|) status when overflow bubble is hidden
     67   // by outside event of overflow button.
     68   anchor->SchedulePaint();
     69 }
     70 
     71 void OverflowBubble::ProcessPressedEvent(ui::LocatedEvent* event) {
     72   aura::Window* target = static_cast<aura::Window*>(event->target());
     73   gfx::Point event_location_in_screen = event->location();
     74   aura::client::GetScreenPositionClient(target->GetRootWindow())->
     75       ConvertPointToScreen(target, &event_location_in_screen);
     76   if (!shelf_view_->IsShowingMenu() &&
     77       !bubble_->GetBoundsInScreen().Contains(event_location_in_screen) &&
     78       !anchor_->GetBoundsInScreen().Contains(event_location_in_screen)) {
     79     HideBubbleAndRefreshButton();
     80   }
     81 }
     82 
     83 void OverflowBubble::OnMouseEvent(ui::MouseEvent* event) {
     84   if (event->type() == ui::ET_MOUSE_PRESSED)
     85     ProcessPressedEvent(event);
     86 }
     87 
     88 void OverflowBubble::OnTouchEvent(ui::TouchEvent* event) {
     89   if (event->type() == ui::ET_TOUCH_PRESSED)
     90     ProcessPressedEvent(event);
     91 }
     92 
     93 void OverflowBubble::OnWidgetDestroying(views::Widget* widget) {
     94   DCHECK(widget == bubble_->GetWidget());
     95   bubble_ = NULL;
     96   anchor_ = NULL;
     97   shelf_view_ = NULL;
     98   ShelfLayoutManager::ForShelf(
     99       widget->GetNativeView())->shelf_widget()->shelf()->SchedulePaint();
    100 }
    101 
    102 }  // namespace ash
    103