summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authoroshima@chromium.org <oshima@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2013-11-13 09:35:38 +0000
committeroshima@chromium.org <oshima@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2013-11-13 09:35:38 +0000
commit098c299ffc1d2c4e6fe4158598651a18bc77283f (patch)
tree31d99c54e87d79fea5418fca9860f64dde322dec
parent5f7a16e738cb888e24bf355525226a308d6be47c (diff)
downloadchromium_src-098c299ffc1d2c4e6fe4158598651a18bc77283f.zip
chromium_src-098c299ffc1d2c4e6fe4158598651a18bc77283f.tar.gz
chromium_src-098c299ffc1d2c4e6fe4158598651a18bc77283f.tar.bz2
Dont' update focus when moving mirror to docked mode
In this case, the root window is reassigned to another display, so no need to update the focus. BUG=283173 TEST=covered by unit test Review URL: https://codereview.chromium.org/70793002 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@234788 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r--ash/display/display_controller.cc10
-rw-r--r--ash/display/display_controller.h2
-rw-r--r--ash/display/display_controller_unittest.cc62
-rw-r--r--ash/display/display_manager.cc8
-rw-r--r--ash/display/display_manager.h4
5 files changed, 77 insertions, 9 deletions
diff --git a/ash/display/display_controller.cc b/ash/display/display_controller.cc
index 579975a..2204ac2 100644
--- a/ash/display/display_controller.cc
+++ b/ash/display/display_controller.cc
@@ -143,7 +143,7 @@ class FocusActivationStore {
active_(NULL) {
}
- void Store(bool display_removed) {
+ void Store(bool clear_focus) {
if (!activation_client_) {
aura::Window* root = Shell::GetPrimaryRootWindow();
activation_client_ = aura::client::GetActivationClient(root);
@@ -158,7 +158,7 @@ class FocusActivationStore {
tracker_.Add(active_);
// Deactivate the window to close menu / bubble windows.
- if (display_removed)
+ if (clear_focus)
activation_client_->DeactivateWindow(active_);
// Release capture if any.
@@ -167,7 +167,7 @@ class FocusActivationStore {
// window may be deleted when losing focus (fullscreen flash for
// example). If the focused window is still alive after move, it'll
// be re-focused below.
- if (display_removed)
+ if (clear_focus)
focus_client_->FocusWindow(NULL);
}
@@ -702,9 +702,9 @@ void DisplayController::CloseNonDesktopDisplay() {
virtual_keyboard_window_controller_->Close();
}
-void DisplayController::PreDisplayConfigurationChange(bool display_removed) {
+void DisplayController::PreDisplayConfigurationChange(bool clear_focus) {
FOR_EACH_OBSERVER(Observer, observers_, OnDisplayConfigurationChanging());
- focus_activation_store_->Store(display_removed);
+ focus_activation_store_->Store(clear_focus);
gfx::Point point_in_screen = Shell::GetScreen()->GetCursorScreenPoint();
gfx::Display display =
diff --git a/ash/display/display_controller.h b/ash/display/display_controller.h
index 005eebd..9dc20f5 100644
--- a/ash/display/display_controller.h
+++ b/ash/display/display_controller.h
@@ -163,7 +163,7 @@ class ASH_EXPORT DisplayController : public gfx::DisplayObserver,
virtual void CreateOrUpdateNonDesktopDisplay(
const internal::DisplayInfo& info) OVERRIDE;
virtual void CloseNonDesktopDisplay() OVERRIDE;
- virtual void PreDisplayConfigurationChange(bool dispay_removed) OVERRIDE;
+ virtual void PreDisplayConfigurationChange(bool clear_focus) OVERRIDE;
virtual void PostDisplayConfigurationChange() OVERRIDE;
private:
diff --git a/ash/display/display_controller_unittest.cc b/ash/display/display_controller_unittest.cc
index eff5755..b424aeb 100644
--- a/ash/display/display_controller_unittest.cc
+++ b/ash/display/display_controller_unittest.cc
@@ -15,6 +15,7 @@
#include "ash/test/ash_test_base.h"
#include "ash/test/cursor_manager_test_api.h"
#include "ash/test/display_manager_test_api.h"
+#include "ash/wm/window_state.h"
#include "base/command_line.h"
#include "ui/aura/client/activation_change_observer.h"
#include "ui/aura/client/activation_client.h"
@@ -439,6 +440,66 @@ TEST_F(DisplayControllerTest, SecondaryDisplayLayout) {
EXPECT_LE(1, observer.GetActivationChangedCountAndReset());
}
+namespace {
+
+internal::DisplayInfo CreateDisplayInfo(int64 id,
+ const gfx::Rect& bounds,
+ float device_scale_factor) {
+ internal::DisplayInfo info(id, "", false);
+ info.SetBounds(bounds);
+ info.set_device_scale_factor(device_scale_factor);
+ return info;
+}
+
+} // namespace
+
+TEST_F(DisplayControllerTest, MirrorToDockedWithFullscreen) {
+ // Creates windows to catch activation change event.
+ scoped_ptr<aura::Window> w1(CreateTestWindowInShellWithId(1));
+ w1->Focus();
+
+ // Docked mode.
+ internal::DisplayManager* display_manager =
+ Shell::GetInstance()->display_manager();
+
+ const internal::DisplayInfo internal_display_info =
+ CreateDisplayInfo(1, gfx::Rect(0, 0, 500, 500), 2.0f);
+ const internal::DisplayInfo external_display_info =
+ CreateDisplayInfo(2, gfx::Rect(0, 0, 500, 500), 1.0f);
+
+ std::vector<internal::DisplayInfo> display_info_list;
+ // Mirror.
+ display_info_list.push_back(internal_display_info);
+ display_info_list.push_back(external_display_info);
+ display_manager->OnNativeDisplaysChanged(display_info_list);
+ const int64 internal_display_id =
+ test::DisplayManagerTestApi(display_manager).
+ SetFirstDisplayAsInternalDisplay();
+ EXPECT_EQ(1, internal_display_id);
+ EXPECT_EQ(2U, display_manager->num_connected_displays());
+ EXPECT_EQ(1U, display_manager->GetNumDisplays());
+
+ wm::WindowState* window_state = wm::GetWindowState(w1.get());
+ window_state->ToggleFullscreen();
+ EXPECT_TRUE(window_state->IsFullscreen());
+ EXPECT_EQ("0,0 250x250", w1->bounds().ToString());
+ // Dock mode.
+ TestObserver observer;
+ display_info_list.clear();
+ display_info_list.push_back(external_display_info);
+ display_manager->OnNativeDisplaysChanged(display_info_list);
+ EXPECT_EQ(1U, display_manager->GetNumDisplays());
+ EXPECT_EQ(1U, display_manager->num_connected_displays());
+ EXPECT_EQ(0, observer.GetChangedDisplayIdAndReset());
+ EXPECT_EQ(0, observer.GetBoundsChangedCountAndReset());
+ EXPECT_EQ(1, observer.CountAndReset());
+ EXPECT_EQ(0, observer.GetFocusChangedCountAndReset());
+ EXPECT_EQ(0, observer.GetActivationChangedCountAndReset());
+
+ EXPECT_TRUE(window_state->IsFullscreen());
+ EXPECT_EQ("0,0 500x500", w1->bounds().ToString());
+}
+
TEST_F(DisplayControllerTest, BoundsUpdated) {
if (!SupportsMultipleDisplays())
return;
@@ -1180,7 +1241,6 @@ TEST_F(DisplayControllerTest, DockToSingle) {
display_info_list.push_back(internal_display_info);
display_info_list.push_back(external_display_info);
display_manager->OnNativeDisplaysChanged(display_info_list);
- EXPECT_EQ(2U, display_manager->GetNumDisplays());
const int64 internal_display_id =
test::DisplayManagerTestApi(display_manager).
SetFirstDisplayAsInternalDisplay();
diff --git a/ash/display/display_manager.cc b/ash/display/display_manager.cc
index a4c5f75..855221b 100644
--- a/ash/display/display_manager.cc
+++ b/ash/display/display_manager.cc
@@ -693,8 +693,14 @@ void DisplayManager::UpdateDisplays(
removed_displays.empty()) {
return;
}
+ // Clear focus if the display has been removed, but don't clear focus if
+ // the destkop has been moved from one display to another
+ // (mirror -> docked, docked -> single internal).
+ bool clear_focus =
+ !removed_displays.empty() &&
+ !(removed_displays.size() == 1 && added_display_indices.size() == 1);
if (delegate_)
- delegate_->PreDisplayConfigurationChange(!removed_displays.empty());
+ delegate_->PreDisplayConfigurationChange(clear_focus);
size_t updated_index;
if (UpdateSecondaryDisplayBoundsForLayout(&new_displays, &updated_index) &&
diff --git a/ash/display/display_manager.h b/ash/display/display_manager.h
index d79654b..4b53dac 100644
--- a/ash/display/display_manager.h
+++ b/ash/display/display_manager.h
@@ -59,7 +59,9 @@ class ASH_EXPORT DisplayManager
virtual void CloseNonDesktopDisplay() = 0;
// Called before and after the display configuration changes.
- virtual void PreDisplayConfigurationChange(bool display_removed) = 0;
+ // When |clear_focus| is true, the implementation should
+ // deactivate the active window and set the focus window to NULL.
+ virtual void PreDisplayConfigurationChange(bool clear_focus) = 0;
virtual void PostDisplayConfigurationChange() = 0;
};