Index: chrome/browser/ui/panels/panel_manager.cc |
=================================================================== |
--- chrome/browser/ui/panels/panel_manager.cc (revision 97852) |
+++ 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,42 @@ |
// Horizontal spacing between two panels. |
const int kPanelsHorizontalSpacing = 4; |
+// Occasionally some system, like Windows, might not bring up or down the bottom |
+// bar when the mouse enters or leaves the bottom screen area. This is the |
+// maximum time we will wait for the bottom bar visibility change notification. |
+// After the time expires, we bring up/down the titlebars as planned. |
+const int kMaxTimeWaitForBottomBarVisibilityChange = 1000; |
jennb
2011/08/23 20:28:34
s/Time/<name of time unit>
jianli
2011/08/26 00:18:16
Done.
|
+ |
// Single instance of PanelManager. |
-scoped_ptr<PanelManager> panel_instance; |
+scoped_refptr<PanelManager> panel_instance; |
} // 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::CreateForTestingHelper( |
+ const gfx::Rect& work_area, 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,6 +75,11 @@ |
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()); |
@@ -70,9 +91,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 +292,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_->IsEnabled() && |
+ 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 +308,55 @@ |
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_->IsEnabled()) { |
+ 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; |
+ |
+ // Occasionally some system, like Windows, might not bring up or down the |
+ // bottom bar when the mouse enters or leaves the bottom screen area. |
+ // Thus, we schedule a delayed task to do the work if we do not receive |
+ // the bottom bar visibility change notification within a certain period |
+ // of time. |
+ MessageLoop::current()->PostDelayedTask( |
+ FROM_HERE, |
+ method_factory_.NewRunnableMethod( |
+ &PanelManager::DelayedBringUpOrDownTitlebarsCheck), |
+ kMaxTimeWaitForBottomBarVisibilityChange); |
+ |
+ return; |
+ } |
+ } |
+ |
+ DoBringUpOrDownTitlebars(bring_up); |
+} |
+ |
+void PanelManager::DelayedBringUpOrDownTitlebarsCheck() { |
jennb
2011/08/23 20:28:34
Seems like this could be coded more compactly:
if
jianli
2011/08/26 00:18:16
Done.
|
+ 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 +375,42 @@ |
} |
} |
+int PanelManager::GetBottomPositionForExpansionState( |
jennb
2011/08/23 20:28:34
As discussed, some logic error computing bottom he
jianli
2011/08/26 00:18:16
Done.
|
+ 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_) { |
jennb
2011/08/23 20:28:34
Feels like this method can be coded more compactly
jianli
2011/08/26 00:18:16
Done.
|
+ 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(); |
jennb
2011/08/23 20:28:34
Why does current_x_ get updated when height change
jianli
2011/08/26 00:18:16
Changed the logic such that current_x_ is removed.
|
+ Rearrange(panels_.begin()); |
+} |
+ |
void PanelManager::Rearrange(Panels::iterator iter_to_start) { |
if (iter_to_start == panels_.end()) |
return; |
@@ -336,9 +447,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; |