root_window_transformers_unittest.cc revision 4e180b6a0b4720a9b8e9e959a882386f690f08ff
16c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne// Copyright 2013 The Chromium Authors. All rights reserved.
26c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne// Use of this source code is governed by a BSD-style license that can be
36c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne// found in the LICENSE file.
46c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne
56c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ash/display/root_window_transformers.h"
66c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne
76c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ash/display/display_controller.h"
86c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ash/display/display_info.h"
96c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ash/display/display_manager.h"
106c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ash/launcher/launcher.h"
116c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ash/magnifier/magnification_controller.h"
126c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ash/screen_ash.h"
136c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ash/shelf/shelf_widget.h"
146c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ash/shell.h"
156c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ash/test/ash_test_base.h"
16a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne#include "ash/test/cursor_manager_test_api.h"
17a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne#include "ash/test/mirror_window_test_api.h"
18a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne#include "base/synchronization/waitable_event.h"
193b844ba7d5be205a9b4f5f0b0d1b7978977f4b8cChandler Carruth#include "ui/aura/env.h"
203b844ba7d5be205a9b4f5f0b0d1b7978977f4b8cChandler Carruth#include "ui/aura/root_window.h"
213b844ba7d5be205a9b4f5f0b0d1b7978977f4b8cChandler Carruth#include "ui/aura/root_window_transformer.h"
22a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne#include "ui/aura/test/event_generator.h"
23a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne#include "ui/aura/window_tracker.h"
246c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ui/events/event_handler.h"
256c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ui/gfx/display.h"
266c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ui/gfx/rect_conversions.h"
276c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ui/gfx/screen.h"
286c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#include "ui/views/widget/widget.h"
296c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne
306c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbournenamespace ash {
31a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbournenamespace internal {
32a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
33a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbournenamespace {
34a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
35a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourneconst char kDesktopBackgroundView[] = "DesktopBackgroundView";
36a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
37a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourneclass TestEventHandler : public ui::EventHandler {
38a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne public:
396c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne  TestEventHandler() : target_root_(NULL),
406c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne                       touch_radius_x_(0.0),
41a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne                       touch_radius_y_(0.0),
42a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne                       scroll_x_offset_(0.0),
436c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne                       scroll_y_offset_(0.0),
446c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne                       scroll_x_offset_ordinal_(0.0),
456c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne                       scroll_y_offset_ordinal_(0.0) {}
466c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne  virtual ~TestEventHandler() {}
476c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne
48a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  virtual void OnMouseEvent(ui::MouseEvent* event) OVERRIDE {
49a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    if (event->flags() & ui::EF_IS_SYNTHESIZED)
50a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne      return;
51a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    aura::Window* target = static_cast<aura::Window*>(event->target());
52a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    mouse_location_ = event->root_location();
53a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    target_root_ = target->GetRootWindow();
54a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    event->StopPropagation();
55a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  }
56a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
57a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  virtual void OnTouchEvent(ui::TouchEvent* event) OVERRIDE {
58a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    aura::Window* target = static_cast<aura::Window*>(event->target());
59a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    // Only record when the target is the background which covers
60a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    // entire root window.
61a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    if (target->name() != kDesktopBackgroundView)
62a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne      return;
63a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    touch_radius_x_ = event->radius_x();
64a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    touch_radius_y_ = event->radius_y();
65a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    event->StopPropagation();
66a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  }
67a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
68a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  virtual void OnScrollEvent(ui::ScrollEvent* event) OVERRIDE {
69a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    aura::Window* target = static_cast<aura::Window*>(event->target());
70a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    // Only record when the target is the background which covers
71a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    // entire root window.
72a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    if (target->name() != kDesktopBackgroundView)
73a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne      return;
74a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
75a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    if (event->type() == ui::ET_SCROLL) {
76a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne      scroll_x_offset_ = event->x_offset();
77a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne      scroll_y_offset_ = event->y_offset();
78a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne      scroll_x_offset_ordinal_ = event->x_offset_ordinal();
79a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne      scroll_y_offset_ordinal_ = event->y_offset_ordinal();
80a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    }
81cfa88f893915ceb8ae4ce2f17c46c24a4d67502fDmitri Gribenko    event->StopPropagation();
82a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  }
83a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
84a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  std::string GetLocationAndReset() {
85a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    std::string result = mouse_location_.ToString();
86a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    mouse_location_.SetPoint(0, 0);
87a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    target_root_ = NULL;
88a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne    return result;
89a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  }
90a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
91a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  float touch_radius_x() const { return touch_radius_x_; }
92a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  float touch_radius_y() const { return touch_radius_y_; }
93a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  float scroll_x_offset() const { return scroll_x_offset_; }
94a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  float scroll_y_offset() const { return scroll_y_offset_; }
95a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  float scroll_x_offset_ordinal() const { return scroll_x_offset_ordinal_; }
96a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  float scroll_y_offset_ordinal() const { return scroll_y_offset_ordinal_; }
97a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
98a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne private:
99a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  gfx::Point mouse_location_;
100a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  aura::RootWindow* target_root_;
101a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
102a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  float touch_radius_x_;
103a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  float touch_radius_y_;
104a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  float scroll_x_offset_;
105a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  float scroll_y_offset_;
106a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  float scroll_x_offset_ordinal_;
107a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  float scroll_y_offset_ordinal_;
108a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
109a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  DISALLOW_COPY_AND_ASSIGN(TestEventHandler);
110a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne};
111a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
112a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbournegfx::Display::Rotation GetStoredRotation(int64 id) {
113a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  return Shell::GetInstance()->display_manager()->GetDisplayInfo(id).rotation();
114a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne}
115a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
116a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbournefloat GetStoredUIScale(int64 id) {
117a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne  return Shell::GetInstance()->display_manager()->GetDisplayInfo(id).ui_scale();
118a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne}
119a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne
120a4ae2294b6ebfb2554aacb6a6a0682fb5ed1f276Peter Collingbourne}  // namespace
1216c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne
1226c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbournetypedef test::AshTestBase RootWindowTransformersTest;
1236c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne
1246c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne#if defined(OS_WIN)
1256c0aa5ff6e6253db0f993053599e2a52b5b93b2dPeter Collingbourne// TODO(scottmg): RootWindow doesn't get resized on Windows
126// Ash. http://crbug.com/247916.
127#define MAYBE_RotateAndMagnify DISABLED_RotateAndMagniy
128#define MAYBE_TouchScaleAndMagnify DISABLED_TouchScaleAndMagnify
129#define MAYBE_ConvertHostToRootCoords DISABLED_ConvertHostToRootCoords
130#else
131#define MAYBE_RotateAndMagnify RotateAndMagniy
132#define MAYBE_TouchScaleAndMagnify TouchScaleAndMagnify
133#define MAYBE_ConvertHostToRootCoords ConvertHostToRootCoords
134#endif
135
136TEST_F(RootWindowTransformersTest, MAYBE_RotateAndMagnify) {
137  DisplayController* display_controller =
138      Shell::GetInstance()->display_controller();
139  MagnificationController* magnifier =
140      Shell::GetInstance()->magnification_controller();
141  DisplayManager* display_manager = Shell::GetInstance()->display_manager();
142
143  TestEventHandler event_handler;
144  Shell::GetInstance()->AddPreTargetHandler(&event_handler);
145
146  UpdateDisplay("120x200,300x400*2");
147  gfx::Display display1 = Shell::GetScreen()->GetPrimaryDisplay();
148  int64 display2_id = ScreenAsh::GetSecondaryDisplay().id();
149
150  Shell::RootWindowList root_windows = Shell::GetAllRootWindows();
151  aura::test::EventGenerator generator1(root_windows[0]);
152  aura::test::EventGenerator generator2(root_windows[1]);
153
154  magnifier->SetEnabled(true);
155  EXPECT_EQ(2.0f, magnifier->GetScale());
156  EXPECT_EQ("120x200", root_windows[0]->bounds().size().ToString());
157  EXPECT_EQ("150x200", root_windows[1]->bounds().size().ToString());
158  EXPECT_EQ("120,0 150x200",
159            ScreenAsh::GetSecondaryDisplay().bounds().ToString());
160  generator1.MoveMouseToInHost(40, 80);
161  EXPECT_EQ("50,90", event_handler.GetLocationAndReset());
162  EXPECT_EQ("50,90",
163            aura::Env::GetInstance()->last_mouse_location().ToString());
164  EXPECT_EQ(gfx::Display::ROTATE_0, GetStoredRotation(display1.id()));
165  EXPECT_EQ(gfx::Display::ROTATE_0, GetStoredRotation(display2_id));
166  magnifier->SetEnabled(false);
167
168  display_manager->SetDisplayRotation(display1.id(),
169                                      gfx::Display::ROTATE_90);
170  // Move the cursor to the center of the first root window.
171  generator1.MoveMouseToInHost(59, 100);
172
173  magnifier->SetEnabled(true);
174  EXPECT_EQ(2.0f, magnifier->GetScale());
175  EXPECT_EQ("200x120", root_windows[0]->bounds().size().ToString());
176  EXPECT_EQ("150x200", root_windows[1]->bounds().size().ToString());
177  EXPECT_EQ("200,0 150x200",
178            ScreenAsh::GetSecondaryDisplay().bounds().ToString());
179  generator1.MoveMouseToInHost(39, 120);
180  EXPECT_EQ("110,70", event_handler.GetLocationAndReset());
181  EXPECT_EQ("110,70",
182            aura::Env::GetInstance()->last_mouse_location().ToString());
183  EXPECT_EQ(gfx::Display::ROTATE_90, GetStoredRotation(display1.id()));
184  EXPECT_EQ(gfx::Display::ROTATE_0, GetStoredRotation(display2_id));
185  magnifier->SetEnabled(false);
186
187  DisplayLayout display_layout(DisplayLayout::BOTTOM, 50);
188  display_controller->SetLayoutForCurrentDisplays(display_layout);
189  EXPECT_EQ("50,120 150x200",
190            ScreenAsh::GetSecondaryDisplay().bounds().ToString());
191
192  display_manager->SetDisplayRotation(display2_id,
193                                      gfx::Display::ROTATE_270);
194  // Move the cursor to the center of the second root window.
195  generator2.MoveMouseToInHost(151, 199);
196
197  magnifier->SetEnabled(true);
198  EXPECT_EQ("200x120", root_windows[0]->bounds().size().ToString());
199  EXPECT_EQ("200x150", root_windows[1]->bounds().size().ToString());
200  EXPECT_EQ("50,120 200x150",
201            ScreenAsh::GetSecondaryDisplay().bounds().ToString());
202  generator2.MoveMouseToInHost(172, 219);
203  EXPECT_EQ("95,80", event_handler.GetLocationAndReset());
204  EXPECT_EQ("145,200",
205            aura::Env::GetInstance()->last_mouse_location().ToString());
206  EXPECT_EQ(gfx::Display::ROTATE_90, GetStoredRotation(display1.id()));
207  EXPECT_EQ(gfx::Display::ROTATE_270, GetStoredRotation(display2_id));
208  magnifier->SetEnabled(false);
209
210  display_manager->SetDisplayRotation(display1.id(),
211                                      gfx::Display::ROTATE_180);
212  // Move the cursor to the center of the first root window.
213  generator1.MoveMouseToInHost(59, 99);
214
215  magnifier->SetEnabled(true);
216  EXPECT_EQ("120x200", root_windows[0]->bounds().size().ToString());
217  EXPECT_EQ("200x150", root_windows[1]->bounds().size().ToString());
218  // Dislay must share at least 100, so the x's offset becomes 20.
219  EXPECT_EQ("20,200 200x150",
220            ScreenAsh::GetSecondaryDisplay().bounds().ToString());
221  generator1.MoveMouseToInHost(39, 59);
222  EXPECT_EQ("70,120", event_handler.GetLocationAndReset());
223  EXPECT_EQ(gfx::Display::ROTATE_180, GetStoredRotation(display1.id()));
224  EXPECT_EQ(gfx::Display::ROTATE_270, GetStoredRotation(display2_id));
225  magnifier->SetEnabled(false);
226
227  Shell::GetInstance()->RemovePreTargetHandler(&event_handler);
228}
229
230TEST_F(RootWindowTransformersTest, ScaleAndMagnify) {
231  if (!SupportsMultipleDisplays())
232    return;
233
234  TestEventHandler event_handler;
235  Shell::GetInstance()->AddPreTargetHandler(&event_handler);
236
237  UpdateDisplay("600x400*2@1.5,500x300");
238
239  gfx::Display display1 = Shell::GetScreen()->GetPrimaryDisplay();
240  gfx::Display::SetInternalDisplayId(display1.id());
241  gfx::Display display2 = ScreenAsh::GetSecondaryDisplay();
242  Shell::RootWindowList root_windows = Shell::GetAllRootWindows();
243  MagnificationController* magnifier =
244      Shell::GetInstance()->magnification_controller();
245
246  magnifier->SetEnabled(true);
247  EXPECT_EQ(2.0f, magnifier->GetScale());
248  EXPECT_EQ("0,0 450x300", display1.bounds().ToString());
249  EXPECT_EQ("0,0 450x300", root_windows[0]->bounds().ToString());
250  EXPECT_EQ("450,0 500x300", display2.bounds().ToString());
251  EXPECT_EQ(1.5f, GetStoredUIScale(display1.id()));
252  EXPECT_EQ(1.0f, GetStoredUIScale(display2.id()));
253
254  aura::test::EventGenerator generator(root_windows[0]);
255  generator.MoveMouseToInHost(500, 200);
256  EXPECT_EQ("299,150", event_handler.GetLocationAndReset());
257  magnifier->SetEnabled(false);
258
259  DisplayManager* display_manager = Shell::GetInstance()->display_manager();
260  display_manager->SetDisplayUIScale(display1.id(), 1.25);
261  display1 = Shell::GetScreen()->GetPrimaryDisplay();
262  display2 = ScreenAsh::GetSecondaryDisplay();
263  magnifier->SetEnabled(true);
264  EXPECT_EQ(2.0f, magnifier->GetScale());
265  EXPECT_EQ("0,0 375x250", display1.bounds().ToString());
266  EXPECT_EQ("0,0 375x250", root_windows[0]->bounds().ToString());
267  EXPECT_EQ("375,0 500x300", display2.bounds().ToString());
268  EXPECT_EQ(1.25f, GetStoredUIScale(display1.id()));
269  EXPECT_EQ(1.0f, GetStoredUIScale(display2.id()));
270  magnifier->SetEnabled(false);
271
272  Shell::GetInstance()->RemovePreTargetHandler(&event_handler);
273}
274
275TEST_F(RootWindowTransformersTest, MAYBE_TouchScaleAndMagnify) {
276  TestEventHandler event_handler;
277  Shell::GetInstance()->AddPreTargetHandler(&event_handler);
278
279  UpdateDisplay("200x200*2");
280  gfx::Display display = Shell::GetScreen()->GetPrimaryDisplay();
281  Shell::RootWindowList root_windows = Shell::GetAllRootWindows();
282  aura::RootWindow* root_window = root_windows[0];
283  aura::test::EventGenerator generator(root_window);
284  MagnificationController* magnifier =
285      Shell::GetInstance()->magnification_controller();
286
287  magnifier->SetEnabled(true);
288  EXPECT_FLOAT_EQ(2.0f, magnifier->GetScale());
289  magnifier->SetScale(2.5f, false);
290  EXPECT_FLOAT_EQ(2.5f, magnifier->GetScale());
291  generator.PressMoveAndReleaseTouchTo(50, 50);
292  // Default test touches have radius_x/y = 1.0, with device scale
293  // factor = 2, the scaled radius_x/y should be 0.5.
294  EXPECT_FLOAT_EQ(0.2f, event_handler.touch_radius_x());
295  EXPECT_FLOAT_EQ(0.2f, event_handler.touch_radius_y());
296
297  generator.ScrollSequence(gfx::Point(0,0),
298                           base::TimeDelta::FromMilliseconds(100),
299                           10.0, 1.0, 5, 1);
300
301  // ordinal_offset is invariant to the device scale factor.
302  EXPECT_FLOAT_EQ(event_handler.scroll_x_offset(),
303                  event_handler.scroll_x_offset_ordinal());
304  EXPECT_FLOAT_EQ(event_handler.scroll_y_offset(),
305                  event_handler.scroll_y_offset_ordinal());
306  magnifier->SetEnabled(false);
307
308  Shell::GetInstance()->RemovePreTargetHandler(&event_handler);
309}
310
311TEST_F(RootWindowTransformersTest, MAYBE_ConvertHostToRootCoords) {
312  TestEventHandler event_handler;
313  Shell::GetInstance()->AddPreTargetHandler(&event_handler);
314  MagnificationController* magnifier =
315      Shell::GetInstance()->magnification_controller();
316
317  // Test 1
318  UpdateDisplay("600x400*2/r@1.5");
319
320  gfx::Display display1 = Shell::GetScreen()->GetPrimaryDisplay();
321  Shell::RootWindowList root_windows = Shell::GetAllRootWindows();
322  EXPECT_EQ("0,0 300x450", display1.bounds().ToString());
323  EXPECT_EQ("0,0 300x450", root_windows[0]->bounds().ToString());
324  EXPECT_EQ(1.5f, GetStoredUIScale(display1.id()));
325
326  aura::test::EventGenerator generator(root_windows[0]);
327  generator.MoveMouseToInHost(300, 200);
328  magnifier->SetEnabled(true);
329  EXPECT_EQ("150,224", event_handler.GetLocationAndReset());
330  EXPECT_FLOAT_EQ(2.0f, magnifier->GetScale());
331
332  generator.MoveMouseToInHost(300, 200);
333  EXPECT_EQ("150,224", event_handler.GetLocationAndReset());
334  generator.MoveMouseToInHost(200, 300);
335  EXPECT_EQ("187,261", event_handler.GetLocationAndReset());
336  generator.MoveMouseToInHost(100, 400);
337  EXPECT_EQ("237,299", event_handler.GetLocationAndReset());
338  generator.MoveMouseToInHost(0, 0);
339  EXPECT_EQ("137,348", event_handler.GetLocationAndReset());
340
341  magnifier->SetEnabled(false);
342  EXPECT_FLOAT_EQ(1.0f, magnifier->GetScale());
343
344  // Test 2
345  UpdateDisplay("600x400*2/u@1.5");
346  display1 = Shell::GetScreen()->GetPrimaryDisplay();
347  root_windows = Shell::GetAllRootWindows();
348  EXPECT_EQ("0,0 450x300", display1.bounds().ToString());
349  EXPECT_EQ("0,0 450x300", root_windows[0]->bounds().ToString());
350  EXPECT_EQ(1.5f, GetStoredUIScale(display1.id()));
351
352  generator.MoveMouseToInHost(300, 200);
353  magnifier->SetEnabled(true);
354  EXPECT_EQ("224,149", event_handler.GetLocationAndReset());
355  EXPECT_FLOAT_EQ(2.0f, magnifier->GetScale());
356
357  generator.MoveMouseToInHost(300, 200);
358  EXPECT_EQ("224,148", event_handler.GetLocationAndReset());
359  generator.MoveMouseToInHost(200, 300);
360  EXPECT_EQ("261,111", event_handler.GetLocationAndReset());
361  generator.MoveMouseToInHost(100, 400);
362  EXPECT_EQ("299,60", event_handler.GetLocationAndReset());
363  generator.MoveMouseToInHost(0, 0);
364  EXPECT_EQ("348,159", event_handler.GetLocationAndReset());
365
366  magnifier->SetEnabled(false);
367  EXPECT_FLOAT_EQ(1.0f, magnifier->GetScale());
368
369  // Test 3
370  UpdateDisplay("600x400*2/l@1.5");
371  display1 = Shell::GetScreen()->GetPrimaryDisplay();
372  root_windows = Shell::GetAllRootWindows();
373  EXPECT_EQ("0,0 300x450", display1.bounds().ToString());
374  EXPECT_EQ("0,0 300x450", root_windows[0]->bounds().ToString());
375  EXPECT_EQ(1.5f, GetStoredUIScale(display1.id()));
376
377  generator.MoveMouseToInHost(300, 200);
378  magnifier->SetEnabled(true);
379  EXPECT_EQ("149,225", event_handler.GetLocationAndReset());
380  EXPECT_FLOAT_EQ(2.0f, magnifier->GetScale());
381
382  generator.MoveMouseToInHost(300, 200);
383  EXPECT_EQ("148,224", event_handler.GetLocationAndReset());
384  generator.MoveMouseToInHost(200, 300);
385  EXPECT_EQ("111,187", event_handler.GetLocationAndReset());
386  generator.MoveMouseToInHost(100, 400);
387  EXPECT_EQ("60,149", event_handler.GetLocationAndReset());
388  generator.MoveMouseToInHost(0, 0);
389  EXPECT_EQ("159,99", event_handler.GetLocationAndReset());
390
391  magnifier->SetEnabled(false);
392  EXPECT_FLOAT_EQ(1.0f, magnifier->GetScale());
393
394  Shell::GetInstance()->RemovePreTargetHandler(&event_handler);
395}
396
397TEST_F(RootWindowTransformersTest, LetterBoxPillarBox) {
398  if (!SupportsMultipleDisplays())
399    return;
400  test::MirrorWindowTestApi test_api;
401  DisplayManager* display_manager = Shell::GetInstance()->display_manager();
402  display_manager->SetSoftwareMirroring(true);
403  UpdateDisplay("400x200,500x500");
404  scoped_ptr<aura::RootWindowTransformer> transformer(
405      test_api.CreateCurrentRootWindowTransformer());
406  // Y margin must be margin is (500 - 500/400 * 200) / 2 = 125.
407  EXPECT_EQ("0,125,0,125", transformer->GetHostInsets().ToString());
408
409  UpdateDisplay("200x400,500x500");
410  // The aspect ratio is flipped, so X margin is now 125.
411  transformer = test_api.CreateCurrentRootWindowTransformer();
412  EXPECT_EQ("125,0,125,0", transformer->GetHostInsets().ToString());
413}
414
415}  // namespace test
416}  // namespace ash
417