Home | History | Annotate | Download | only in panels
      1 // Copyright (c) 2012 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 #ifndef ASH_WM_PANELS_PANEL_LAYOUT_MANAGER_H_
      6 #define ASH_WM_PANELS_PANEL_LAYOUT_MANAGER_H_
      7 
      8 #include <list>
      9 
     10 #include "ash/ash_export.h"
     11 #include "ash/display/display_controller.h"
     12 #include "ash/shelf/shelf_icon_observer.h"
     13 #include "ash/shelf/shelf_layout_manager_observer.h"
     14 #include "ash/shell_observer.h"
     15 #include "ash/wm/window_state_observer.h"
     16 #include "base/basictypes.h"
     17 #include "base/compiler_specific.h"
     18 #include "base/memory/scoped_ptr.h"
     19 #include "base/memory/weak_ptr.h"
     20 #include "ui/aura/layout_manager.h"
     21 #include "ui/aura/window_observer.h"
     22 #include "ui/keyboard/keyboard_controller.h"
     23 #include "ui/keyboard/keyboard_controller_observer.h"
     24 #include "ui/wm/public/activation_change_observer.h"
     25 
     26 namespace aura {
     27 class Window;
     28 class WindowTracker;
     29 }
     30 
     31 namespace gfx {
     32 class Rect;
     33 }
     34 
     35 namespace views {
     36 class Widget;
     37 }
     38 
     39 namespace ash {
     40 class PanelCalloutWidget;
     41 class Shelf;
     42 class ShelfLayoutManager;
     43 
     44 // PanelLayoutManager is responsible for organizing panels within the
     45 // workspace. It is associated with a specific container window (i.e.
     46 // kShellWindowId_PanelContainer) and controls the layout of any windows
     47 // added to that container.
     48 //
     49 // The constructor takes a |panel_container| argument which is expected to set
     50 // its layout manager to this instance, e.g.:
     51 // panel_container->SetLayoutManager(new PanelLayoutManager(panel_container));
     52 
     53 class ASH_EXPORT PanelLayoutManager
     54     : public aura::LayoutManager,
     55       public ShelfIconObserver,
     56       public ShellObserver,
     57       public aura::WindowObserver,
     58       public wm::WindowStateObserver,
     59       public aura::client::ActivationChangeObserver,
     60       public keyboard::KeyboardControllerObserver,
     61       public DisplayController::Observer,
     62       public ShelfLayoutManagerObserver {
     63  public:
     64   explicit PanelLayoutManager(aura::Window* panel_container);
     65   virtual ~PanelLayoutManager();
     66 
     67   // Call Shutdown() before deleting children of panel_container.
     68   void Shutdown();
     69 
     70   void StartDragging(aura::Window* panel);
     71   void FinishDragging();
     72 
     73   void ToggleMinimize(aura::Window* panel);
     74 
     75   // Hide / Show the panel callout widgets.
     76   void SetShowCalloutWidgets(bool show);
     77 
     78   // Returns the callout widget (arrow) for |panel|.
     79   views::Widget* GetCalloutWidgetForPanel(aura::Window* panel);
     80 
     81   Shelf* shelf() { return shelf_; }
     82   void SetShelf(Shelf* shelf);
     83 
     84   // Overridden from aura::LayoutManager:
     85   virtual void OnWindowResized() OVERRIDE;
     86   virtual void OnWindowAddedToLayout(aura::Window* child) OVERRIDE;
     87   virtual void OnWillRemoveWindowFromLayout(aura::Window* child) OVERRIDE;
     88   virtual void OnWindowRemovedFromLayout(aura::Window* child) OVERRIDE;
     89   virtual void OnChildWindowVisibilityChanged(aura::Window* child,
     90                                               bool visibile) OVERRIDE;
     91   virtual void SetChildBounds(aura::Window* child,
     92                               const gfx::Rect& requested_bounds) OVERRIDE;
     93 
     94   // Overridden from ShelfIconObserver
     95   virtual void OnShelfIconPositionsChanged() OVERRIDE;
     96 
     97   // Overridden from ShellObserver
     98   virtual void OnShelfAlignmentChanged(aura::Window* root_window) OVERRIDE;
     99 
    100   // Overridden from aura::WindowObserver
    101   virtual void OnWindowPropertyChanged(aura::Window* window,
    102                                        const void* key,
    103                                        intptr_t old) OVERRIDE;
    104 
    105   // Overridden from ash::wm::WindowStateObserver
    106   virtual void OnPostWindowStateTypeChange(
    107       wm::WindowState* window_state,
    108       wm::WindowStateType old_type) OVERRIDE;
    109 
    110   // Overridden from aura::client::ActivationChangeObserver
    111   virtual void OnWindowActivated(aura::Window* gained_active,
    112                                  aura::Window* lost_active) OVERRIDE;
    113 
    114   // Overridden from DisplayController::Observer
    115   virtual void OnDisplayConfigurationChanged() OVERRIDE;
    116 
    117   // Overridden from ShelfLayoutManagerObserver
    118   virtual void WillChangeVisibilityState(
    119       ShelfVisibilityState new_state) OVERRIDE;
    120 
    121  private:
    122   friend class PanelLayoutManagerTest;
    123   friend class PanelWindowResizerTest;
    124   friend class DockedWindowResizerTest;
    125   friend class DockedWindowLayoutManagerTest;
    126   friend class WorkspaceControllerTest;
    127 
    128   views::Widget* CreateCalloutWidget();
    129 
    130   struct PanelInfo{
    131     PanelInfo() : window(NULL), callout_widget(NULL), slide_in(false) {}
    132 
    133     bool operator==(const aura::Window* other_window) const {
    134       return window == other_window;
    135     }
    136 
    137     // A weak pointer to the panel window.
    138     aura::Window* window;
    139     // The callout widget for this panel. This pointer must be managed
    140     // manually as this structure is used in a std::list. See
    141     // http://www.chromium.org/developers/smart-pointer-guidelines
    142     PanelCalloutWidget* callout_widget;
    143 
    144     // True on new and restored panel windows until the panel has been
    145     // positioned. The first time Relayout is called the panel will be shown,
    146     // and slide into position and this will be set to false.
    147     bool slide_in;
    148   };
    149 
    150   typedef std::list<PanelInfo> PanelList;
    151 
    152   void MinimizePanel(aura::Window* panel);
    153   void RestorePanel(aura::Window* panel);
    154 
    155   // Called whenever the panel layout might change.
    156   void Relayout();
    157 
    158   // Called whenever the panel stacking order needs to be updated (e.g. focus
    159   // changes or a panel is moved).
    160   void UpdateStacking(aura::Window* active_panel);
    161 
    162   // Update the callout arrows for all managed panels.
    163   void UpdateCallouts();
    164 
    165   // Overridden from keyboard::KeyboardControllerObserver:
    166   virtual void OnKeyboardBoundsChanging(
    167       const gfx::Rect& keyboard_bounds) OVERRIDE;
    168 
    169   // Parent window associated with this layout manager.
    170   aura::Window* panel_container_;
    171   // Protect against recursive calls to OnWindowAddedToLayout().
    172   bool in_add_window_;
    173   // Protect against recursive calls to Relayout().
    174   bool in_layout_;
    175   // Indicates if the panel callout widget should be created.
    176   bool show_callout_widgets_;
    177   // Ordered list of unowned pointers to panel windows.
    178   PanelList panel_windows_;
    179   // The panel being dragged.
    180   aura::Window* dragged_panel_;
    181   // The shelf we are observing for shelf icon changes.
    182   Shelf* shelf_;
    183   // The shelf layout manager being observed for visibility changes.
    184   ShelfLayoutManager* shelf_layout_manager_;
    185 
    186   // When not NULL, the shelf is hidden (i.e. full screen) and this tracks the
    187   // set of panel windows which have been temporarily hidden and need to be
    188   // restored when the shelf becomes visible again.
    189   scoped_ptr<aura::WindowTracker> restore_windows_on_shelf_visible_;
    190 
    191   // The last active panel. Used to maintain stacking order even if no panels
    192   // are currently focused.
    193   aura::Window* last_active_panel_;
    194   base::WeakPtrFactory<PanelLayoutManager> weak_factory_;
    195 
    196   DISALLOW_COPY_AND_ASSIGN(PanelLayoutManager);
    197 };
    198 
    199 }  // namespace ash
    200 
    201 #endif  // ASH_WM_PANELS_PANEL_LAYOUT_MANAGER_H_
    202