Index: chrome/browser/ui/panels/panel_manager.cc |
=================================================================== |
--- chrome/browser/ui/panels/panel_manager.cc (revision 97392) |
+++ chrome/browser/ui/panels/panel_manager.cc (working copy) |
@@ -8,6 +8,7 @@ |
#include "base/logging.h" |
#include "base/memory/scoped_ptr.h" |
+#include "base/message_loop.h" |
#include "chrome/browser/ui/browser.h" |
#include "chrome/browser/ui/window_sizer.h" |
@@ -31,27 +32,39 @@ |
// Horizontal spacing between two panels. |
const int kPanelsHorizontalSpacing = 4; |
+// The delayed interval to do the check to ensure we bring up or down titlebars. |
+const int kDelayedBringUpOrDownTitlebarsCheckMs = 1000; |
+ |
// Single instance of PanelManager. |
-scoped_ptr<PanelManager> panel_instance; |
+scoped_refptr<PanelManager> panel_instance; |
jennb
2011/08/22 21:00:16
Rename this to panel_manager_instance? Took me a
jianli
2011/08/22 23:28:10
Done.
|
} // namespace |
// static |
PanelManager* PanelManager::GetInstance() { |
if (!panel_instance.get()) { |
- panel_instance.reset(new PanelManager()); |
+ panel_instance = new PanelManager(); |
+ panel_instance->Init(); |
} |
return panel_instance.get(); |
} |
+// static |
+void PanelManager::CreateForTesting(const gfx::Rect& work_area, |
jennb
2011/08/22 21:00:16
Alternative would be to have a method to set the A
jianli
2011/08/22 23:28:10
I've tried this but it caused crash if we call Pan
|
+ AutoHideBottomBar* auto_hide_bottom_bar) { |
+ DCHECK(!panel_instance.get()); |
+ panel_instance = new PanelManager(); |
+ panel_instance->auto_hide_bottom_bar_ = auto_hide_bottom_bar; |
+ panel_instance->SetWorkArea(work_area); |
+} |
+ |
PanelManager::PanelManager() |
: max_width_(0), |
max_height_(0), |
- min_x_(0), |
current_x_(0), |
- bottom_edge_y_(0), |
dragging_panel_index_(kInvalidPanelIndex), |
- dragging_panel_original_x_(0) { |
- OnDisplayChanged(); |
+ dragging_panel_original_x_(0), |
+ delayed_titlebar_action_(NO_ACTION), |
+ ALLOW_THIS_IN_INITIALIZER_LIST(method_factory_(this)) { |
} |
PanelManager::~PanelManager() { |
@@ -59,10 +72,16 @@ |
DCHECK(panels_pending_to_remove_.empty()); |
} |
+void PanelManager::Init() { |
+ auto_hide_bottom_bar_ = AutoHideBottomBar::Create(this); |
+ OnDisplayChanged(); |
+} |
+ |
void PanelManager::OnDisplayChanged() { |
scoped_ptr<WindowSizer::MonitorInfoProvider> info_provider( |
WindowSizer::CreateDefaultMonitorInfoProvider()); |
- SetWorkArea(info_provider->GetPrimaryMonitorWorkArea()); |
+ gfx::Rect work_area = info_provider->GetPrimaryMonitorWorkArea(); |
+ SetWorkArea(work_area); |
} |
void PanelManager::SetWorkArea(const gfx::Rect& work_area) { |
@@ -70,9 +89,9 @@ |
return; |
work_area_ = work_area; |
- min_x_ = work_area.x(); |
+ auto_hide_bottom_bar_->UpdateWorkArea(work_area); |
+ |
current_x_ = work_area.right(); |
- bottom_edge_y_ = work_area.bottom(); |
max_width_ = static_cast<int>(work_area.width() * kPanelMaxWidthFactor); |
max_height_ = static_cast<int>(work_area.height() * kPanelMaxHeightFactor); |
@@ -271,8 +290,14 @@ |
DelayedRemove(); |
} |
-bool PanelManager::ShouldBringUpTitlebarForAllMinimizedPanels( |
- int mouse_x, int mouse_y) const { |
+bool PanelManager::ShouldBringUpTitlebars(int mouse_x, int mouse_y) const { |
+ // We should always bring up the title-bar if the mouse is over the auto-hide |
+ // task-bar that becomes visible. |
+ if (auto_hide_bottom_bar_->Exists() && |
+ auto_hide_bottom_bar_->GetVisibility() == AutoHideBottomBar::VISIBLE && |
+ mouse_y >= work_area_.bottom() - auto_hide_bottom_bar_->GetHeight()) |
+ return true; |
+ |
for (Panels::const_iterator iter = panels_.begin(); |
iter != panels_.end(); ++iter) { |
if ((*iter)->ShouldBringUpTitlebar(mouse_x, mouse_y)) |
@@ -281,7 +306,52 @@ |
return false; |
} |
-void PanelManager::BringUpOrDownTitlebarForAllMinimizedPanels(bool bring_up) { |
+void PanelManager::BringUpOrDownTitlebars(bool bring_up) { |
+ // If the auto-hide bottom bar exists, delay the action until the bottom |
+ // bar is fully visible or hidden. We do not want both bottom bar and panel |
+ // titlebar to move at the same time but with different speeds. |
+ if (auto_hide_bottom_bar_->Exists()) { |
+ AutoHideBottomBar::Visibility visibility = |
+ auto_hide_bottom_bar_->GetVisibility(); |
+ if (visibility != (bring_up ? AutoHideBottomBar::VISIBLE |
+ : AutoHideBottomBar::HIDDEN)) { |
+ // OnAutoHideBottomBarVisibilityChanged will handle this. |
+ delayed_titlebar_action_ = bring_up ? BRING_UP : BRING_DOWN; |
+ |
+ // Sometimes, the bottom bar does not appear or hide promptly. Schedule |
+ // a delayed task to make sure our delayed action is performed. |
+ MessageLoop::current()->PostDelayedTask( |
+ FROM_HERE, |
+ method_factory_.NewRunnableMethod( |
+ &PanelManager::DelayedBringUpOrDownTitlebarsCheck), |
+ kDelayedBringUpOrDownTitlebarsCheckMs); |
+ |
+ return; |
+ } |
+ } |
+ |
+ DoBringUpOrDownTitlebars(bring_up); |
+} |
+ |
+void PanelManager::DelayedBringUpOrDownTitlebarsCheck() { |
+ switch (delayed_titlebar_action_) { |
+ case NO_ACTION: |
+ break; |
+ case BRING_UP: |
+ delayed_titlebar_action_ = NO_ACTION; |
+ DoBringUpOrDownTitlebars(true); |
+ break; |
+ case BRING_DOWN: |
+ delayed_titlebar_action_ = NO_ACTION; |
+ DoBringUpOrDownTitlebars(false); |
+ break; |
+ default: |
+ NOTREACHED(); |
+ break; |
+ } |
+} |
+ |
+void PanelManager::DoBringUpOrDownTitlebars(bool bring_up) { |
for (Panels::const_iterator iter = panels_.begin(); |
iter != panels_.end(); ++iter) { |
Panel* panel = *iter; |
@@ -300,6 +370,42 @@ |
} |
} |
+int PanelManager::GetBottomPositionForExpansionState( |
+ Panel::ExpansionState expansion_state) const { |
+ int bottom = work_area_.bottom(); |
+ if (expansion_state != Panel::MINIMIZED) |
+ bottom -= auto_hide_bottom_bar_->GetHeight(); |
+ return bottom; |
+} |
+ |
+void PanelManager::OnAutoHideBottomBarVisibilityChanged( |
+ AutoHideBottomBar::Visibility visibility) { |
+ switch (delayed_titlebar_action_) { |
+ case NO_ACTION: |
+ break; |
+ case BRING_UP: |
+ if (visibility == AutoHideBottomBar::VISIBLE) { |
+ delayed_titlebar_action_ = NO_ACTION; |
+ DoBringUpOrDownTitlebars(true); |
+ } |
+ break; |
+ case BRING_DOWN: |
+ if (visibility == AutoHideBottomBar::HIDDEN) { |
+ delayed_titlebar_action_ = NO_ACTION; |
+ DoBringUpOrDownTitlebars(false); |
+ } |
+ break; |
+ default: |
+ NOTREACHED(); |
+ break; |
+ } |
+} |
+ |
+void PanelManager::OnAutoHideBottomBarHeightChanged(int height) { |
+ current_x_ = work_area_.right(); |
+ Rearrange(panels_.begin()); |
+} |
+ |
void PanelManager::Rearrange(Panels::iterator iter_to_start) { |
if (iter_to_start == panels_.end()) |
return; |
@@ -336,9 +442,9 @@ |
} |
int x = current_x_ - width; |
- int y = bottom_edge_y_ - height; |
+ int y = work_area_.bottom() - auto_hide_bottom_bar_->GetHeight() - height; |
- if (x < min_x_) |
+ if (x < work_area_.x()) |
return false; |
current_x_ -= width + kPanelsHorizontalSpacing; |