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.
5 #include "ash/display/display_manager.h"
7 #include "ash/ash_switches.h"
8 #include "ash/display/display_controller.h"
9 #include "ash/display/display_info.h"
10 #include "ash/display/display_layout_store.h"
11 #include "ash/display/display_util.h"
12 #include "ash/display/mirror_window_controller.h"
13 #include "ash/screen_util.h"
14 #include "ash/shell.h"
15 #include "ash/test/ash_test_base.h"
16 #include "ash/test/display_manager_test_api.h"
17 #include "ash/test/mirror_window_test_api.h"
18 #include "ash/wm/window_state.h"
19 #include "base/command_line.h"
20 #include "base/format_macros.h"
21 #include "base/strings/string_number_conversions.h"
22 #include "base/strings/stringprintf.h"
23 #include "ui/aura/client/aura_constants.h"
24 #include "ui/aura/env.h"
25 #include "ui/aura/window_observer.h"
26 #include "ui/aura/window_tree_host.h"
27 #include "ui/events/test/event_generator.h"
28 #include "ui/gfx/display.h"
29 #include "ui/gfx/display_observer.h"
30 #include "ui/gfx/font_render_params.h"
31 #include "ui/gfx/screen.h"
32 #include "ui/gfx/screen_type_delegate.h"
39 using base::StringPrintf
;
43 std::string
ToDisplayName(int64 id
) {
44 return "x-" + base::Int64ToString(id
);
49 class DisplayManagerTest
: public test::AshTestBase
,
50 public gfx::DisplayObserver
,
51 public aura::WindowObserver
{
55 root_window_destroyed_(false),
56 changed_metrics_(0U) {
58 ~DisplayManagerTest() override
{}
60 void SetUp() override
{
62 Shell::GetScreen()->AddObserver(this);
63 Shell::GetPrimaryRootWindow()->AddObserver(this);
65 void TearDown() override
{
66 Shell::GetPrimaryRootWindow()->RemoveObserver(this);
67 Shell::GetScreen()->RemoveObserver(this);
68 AshTestBase::TearDown();
71 DisplayManager
* display_manager() {
72 return Shell::GetInstance()->display_manager();
74 const vector
<gfx::Display
>& changed() const { return changed_
; }
75 const vector
<gfx::Display
>& added() const { return added_
; }
76 uint32_t changed_metrics() const { return changed_metrics_
; }
78 string
GetCountSummary() const {
79 return StringPrintf("%" PRIuS
" %" PRIuS
" %" PRIuS
,
80 changed_
.size(), added_
.size(), removed_count_
);
87 changed_metrics_
= 0U;
88 root_window_destroyed_
= false;
91 bool root_window_destroyed() const {
92 return root_window_destroyed_
;
95 const DisplayInfo
& GetDisplayInfo(const gfx::Display
& display
) {
96 return display_manager()->GetDisplayInfo(display
.id());
99 const DisplayInfo
& GetDisplayInfoAt(int index
) {
100 return GetDisplayInfo(display_manager()->GetDisplayAt(index
));
103 const gfx::Display
& GetDisplayForId(int64 id
) {
104 return display_manager()->GetDisplayForId(id
);
107 const DisplayInfo
& GetDisplayInfoForId(int64 id
) {
108 return GetDisplayInfo(display_manager()->GetDisplayForId(id
));
111 // aura::DisplayObserver overrides:
112 void OnDisplayMetricsChanged(const gfx::Display
& display
,
113 uint32_t changed_metrics
) override
{
114 changed_
.push_back(display
);
115 changed_metrics_
|= changed_metrics
;
117 void OnDisplayAdded(const gfx::Display
& new_display
) override
{
118 added_
.push_back(new_display
);
120 void OnDisplayRemoved(const gfx::Display
& old_display
) override
{
124 // aura::WindowObserver overrides:
125 void OnWindowDestroying(aura::Window
* window
) override
{
126 ASSERT_EQ(Shell::GetPrimaryRootWindow(), window
);
127 root_window_destroyed_
= true;
131 vector
<gfx::Display
> changed_
;
132 vector
<gfx::Display
> added_
;
133 size_t removed_count_
;
134 bool root_window_destroyed_
;
135 uint32_t changed_metrics_
;
137 DISALLOW_COPY_AND_ASSIGN(DisplayManagerTest
);
140 TEST_F(DisplayManagerTest
, UpdateDisplayTest
) {
141 if (!SupportsMultipleDisplays())
144 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
146 // Update primary and add seconary.
147 UpdateDisplay("100+0-500x500,0+501-400x400");
148 EXPECT_EQ(2U, display_manager()->GetNumDisplays());
149 EXPECT_EQ("0,0 500x500",
150 display_manager()->GetDisplayAt(0).bounds().ToString());
152 EXPECT_EQ("1 1 0", GetCountSummary());
153 EXPECT_EQ(display_manager()->GetDisplayAt(0).id(), changed()[0].id());
154 EXPECT_EQ(display_manager()->GetDisplayAt(1).id(), added()[0].id());
155 EXPECT_EQ("0,0 500x500", changed()[0].bounds().ToString());
156 // Secondary display is on right.
157 EXPECT_EQ("500,0 400x400", added()[0].bounds().ToString());
158 EXPECT_EQ("0,501 400x400",
159 GetDisplayInfo(added()[0]).bounds_in_native().ToString());
163 UpdateDisplay("100+0-500x500");
164 EXPECT_EQ("0 0 1", GetCountSummary());
168 UpdateDisplay("1+1-1000x600");
169 EXPECT_EQ("1 0 0", GetCountSummary());
170 EXPECT_EQ(display_manager()->GetDisplayAt(0).id(), changed()[0].id());
171 EXPECT_EQ("0,0 1000x600", changed()[0].bounds().ToString());
175 UpdateDisplay("1+1-1000x600,1002+0-600x400");
176 EXPECT_EQ(2U, display_manager()->GetNumDisplays());
177 EXPECT_EQ("0 1 0", GetCountSummary());
178 EXPECT_EQ(display_manager()->GetDisplayAt(1).id(), added()[0].id());
179 // Secondary display is on right.
180 EXPECT_EQ("1000,0 600x400", added()[0].bounds().ToString());
181 EXPECT_EQ("1002,0 600x400",
182 GetDisplayInfo(added()[0]).bounds_in_native().ToString());
185 // Secondary removed, primary changed.
186 UpdateDisplay("1+1-800x300");
187 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
188 EXPECT_EQ("1 0 1", GetCountSummary());
189 EXPECT_EQ(display_manager()->GetDisplayAt(0).id(), changed()[0].id());
190 EXPECT_EQ("0,0 800x300", changed()[0].bounds().ToString());
193 // # of display can go to zero when screen is off.
194 const vector
<DisplayInfo
> empty
;
195 display_manager()->OnNativeDisplaysChanged(empty
);
196 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
197 EXPECT_EQ("0 0 0", GetCountSummary());
198 EXPECT_FALSE(root_window_destroyed());
199 // Display configuration stays the same
200 EXPECT_EQ("0,0 800x300",
201 display_manager()->GetDisplayAt(0).bounds().ToString());
204 // Connect to display again
205 UpdateDisplay("100+100-500x400");
206 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
207 EXPECT_EQ("1 0 0", GetCountSummary());
208 EXPECT_FALSE(root_window_destroyed());
209 EXPECT_EQ("0,0 500x400", changed()[0].bounds().ToString());
210 EXPECT_EQ("100,100 500x400",
211 GetDisplayInfo(changed()[0]).bounds_in_native().ToString());
214 // Go back to zero and wake up with multiple displays.
215 display_manager()->OnNativeDisplaysChanged(empty
);
216 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
217 EXPECT_FALSE(root_window_destroyed());
221 UpdateDisplay("0+0-1000x600,1000+1000-600x400");
222 EXPECT_EQ(2U, display_manager()->GetNumDisplays());
223 EXPECT_EQ("0,0 1000x600",
224 display_manager()->GetDisplayAt(0).bounds().ToString());
225 // Secondary display is on right.
226 EXPECT_EQ("1000,0 600x400",
227 display_manager()->GetDisplayAt(1).bounds().ToString());
228 EXPECT_EQ("1000,1000 600x400",
229 GetDisplayInfoAt(1).bounds_in_native().ToString());
232 // Changing primary will update secondary as well.
233 UpdateDisplay("0+0-800x600,1000+1000-600x400");
234 EXPECT_EQ("2 0 0", GetCountSummary());
236 EXPECT_EQ("0,0 800x600",
237 display_manager()->GetDisplayAt(0).bounds().ToString());
238 EXPECT_EQ("800,0 600x400",
239 display_manager()->GetDisplayAt(1).bounds().ToString());
242 TEST_F(DisplayManagerTest
, ScaleOnlyChange
) {
243 if (!SupportsMultipleDisplays())
245 display_manager()->ToggleDisplayScaleFactor();
246 EXPECT_TRUE(changed_metrics() & gfx::DisplayObserver::DISPLAY_METRIC_BOUNDS
);
247 EXPECT_TRUE(changed_metrics() &
248 gfx::DisplayObserver::DISPLAY_METRIC_WORK_AREA
);
251 // Test in emulation mode (use_fullscreen_host_window=false)
252 TEST_F(DisplayManagerTest
, EmulatorTest
) {
253 if (!SupportsMultipleDisplays())
256 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
258 display_manager()->AddRemoveDisplay();
259 // Update primary and add seconary.
260 EXPECT_EQ(2U, display_manager()->GetNumDisplays());
261 EXPECT_EQ("0 1 0", GetCountSummary());
264 display_manager()->AddRemoveDisplay();
265 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
266 EXPECT_EQ("0 0 1", GetCountSummary());
269 display_manager()->AddRemoveDisplay();
270 EXPECT_EQ(2U, display_manager()->GetNumDisplays());
271 EXPECT_EQ("0 1 0", GetCountSummary());
275 // Tests support for 3 displays.
276 TEST_F(DisplayManagerTest
, UpdateThreeDisplaysTest
) {
277 if (!SupportsMultipleDisplays())
280 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
282 // Test with three displays.
283 UpdateDisplay("0+0-640x480,640+0-320x200,960+0-400x300");
284 EXPECT_EQ(3U, display_manager()->GetNumDisplays());
285 EXPECT_EQ("0,0 640x480",
286 display_manager()->GetDisplayAt(0).bounds().ToString());
287 EXPECT_EQ("640,0 320x200",
288 display_manager()->GetDisplayAt(1).bounds().ToString());
289 EXPECT_EQ("960,0 400x300",
290 display_manager()->GetDisplayAt(2).bounds().ToString());
292 EXPECT_EQ("1 2 0", GetCountSummary());
293 EXPECT_EQ(display_manager()->GetDisplayAt(0).id(), changed()[0].id());
294 EXPECT_EQ(display_manager()->GetDisplayAt(1).id(), added()[0].id());
295 EXPECT_EQ(display_manager()->GetDisplayAt(2).id(), added()[1].id());
296 EXPECT_EQ("0,0 640x480", changed()[0].bounds().ToString());
297 // Secondary and terniary displays are on right.
298 EXPECT_EQ("640,0 320x200", added()[0].bounds().ToString());
299 EXPECT_EQ("640,0 320x200",
300 GetDisplayInfo(added()[0]).bounds_in_native().ToString());
301 EXPECT_EQ("960,0 400x300", added()[1].bounds().ToString());
302 EXPECT_EQ("960,0 400x300",
303 GetDisplayInfo(added()[1]).bounds_in_native().ToString());
307 TEST_F(DisplayManagerTest
, OverscanInsetsTest
) {
308 if (!SupportsMultipleDisplays())
311 UpdateDisplay("0+0-500x500,0+501-400x400");
313 ASSERT_EQ(2u, display_manager()->GetNumDisplays());
314 const DisplayInfo
& display_info1
= GetDisplayInfoAt(0);
315 const DisplayInfo
& display_info2
= GetDisplayInfoAt(1);
316 display_manager()->SetOverscanInsets(
317 display_info2
.id(), gfx::Insets(13, 12, 11, 10));
319 std::vector
<gfx::Display
> changed_displays
= changed();
320 EXPECT_EQ(1u, changed_displays
.size());
321 EXPECT_EQ(display_info2
.id(), changed_displays
[0].id());
322 EXPECT_EQ("0,0 500x500",
323 GetDisplayInfoAt(0).bounds_in_native().ToString());
324 DisplayInfo updated_display_info2
= GetDisplayInfoAt(1);
325 EXPECT_EQ("0,501 400x400",
326 updated_display_info2
.bounds_in_native().ToString());
328 updated_display_info2
.size_in_pixel().ToString());
329 EXPECT_EQ("13,12,11,10",
330 updated_display_info2
.overscan_insets_in_dip().ToString());
331 EXPECT_EQ("500,0 378x376",
332 ScreenUtil::GetSecondaryDisplay().bounds().ToString());
334 // Make sure that SetOverscanInsets() is idempotent.
335 display_manager()->SetOverscanInsets(display_info1
.id(), gfx::Insets());
336 display_manager()->SetOverscanInsets(
337 display_info2
.id(), gfx::Insets(13, 12, 11, 10));
338 EXPECT_EQ("0,0 500x500",
339 GetDisplayInfoAt(0).bounds_in_native().ToString());
340 updated_display_info2
= GetDisplayInfoAt(1);
341 EXPECT_EQ("0,501 400x400",
342 updated_display_info2
.bounds_in_native().ToString());
344 updated_display_info2
.size_in_pixel().ToString());
345 EXPECT_EQ("13,12,11,10",
346 updated_display_info2
.overscan_insets_in_dip().ToString());
348 display_manager()->SetOverscanInsets(
349 display_info2
.id(), gfx::Insets(10, 11, 12, 13));
350 EXPECT_EQ("0,0 500x500",
351 GetDisplayInfoAt(0).bounds_in_native().ToString());
353 GetDisplayInfoAt(1).size_in_pixel().ToString());
354 EXPECT_EQ("10,11,12,13",
355 GetDisplayInfoAt(1).overscan_insets_in_dip().ToString());
357 // Recreate a new 2nd display. It won't apply the overscan inset because the
358 // new display has a different ID.
359 UpdateDisplay("0+0-500x500");
360 UpdateDisplay("0+0-500x500,0+501-400x400");
361 EXPECT_EQ("0,0 500x500",
362 GetDisplayInfoAt(0).bounds_in_native().ToString());
363 EXPECT_EQ("0,501 400x400",
364 GetDisplayInfoAt(1).bounds_in_native().ToString());
366 // Recreate the displays with the same ID. It should apply the overscan
368 UpdateDisplay("0+0-500x500");
369 std::vector
<DisplayInfo
> display_info_list
;
370 display_info_list
.push_back(display_info1
);
371 display_info_list
.push_back(display_info2
);
372 display_manager()->OnNativeDisplaysChanged(display_info_list
);
373 EXPECT_EQ("1,1 500x500",
374 GetDisplayInfoAt(0).bounds_in_native().ToString());
375 updated_display_info2
= GetDisplayInfoAt(1);
377 updated_display_info2
.size_in_pixel().ToString());
378 EXPECT_EQ("10,11,12,13",
379 updated_display_info2
.overscan_insets_in_dip().ToString());
381 // HiDPI but overscan display. The specified insets size should be doubled.
382 UpdateDisplay("0+0-500x500,0+501-400x400*2");
383 display_manager()->SetOverscanInsets(
384 display_manager()->GetDisplayAt(1).id(), gfx::Insets(4, 5, 6, 7));
385 EXPECT_EQ("0,0 500x500",
386 GetDisplayInfoAt(0).bounds_in_native().ToString());
387 updated_display_info2
= GetDisplayInfoAt(1);
388 EXPECT_EQ("0,501 400x400",
389 updated_display_info2
.bounds_in_native().ToString());
391 updated_display_info2
.size_in_pixel().ToString());
393 updated_display_info2
.overscan_insets_in_dip().ToString());
394 EXPECT_EQ("8,10,12,14",
395 updated_display_info2
.GetOverscanInsetsInPixel().ToString());
397 // Make sure switching primary display applies the overscan offset only once.
398 ash::Shell::GetInstance()->display_controller()->SetPrimaryDisplay(
399 ScreenUtil::GetSecondaryDisplay());
400 EXPECT_EQ("-500,0 500x500",
401 ScreenUtil::GetSecondaryDisplay().bounds().ToString());
402 EXPECT_EQ("0,0 500x500",
403 GetDisplayInfo(ScreenUtil::GetSecondaryDisplay()).
404 bounds_in_native().ToString());
405 EXPECT_EQ("0,501 400x400",
406 GetDisplayInfo(Shell::GetScreen()->GetPrimaryDisplay()).
407 bounds_in_native().ToString());
408 EXPECT_EQ("0,0 188x190",
409 Shell::GetScreen()->GetPrimaryDisplay().bounds().ToString());
411 // Make sure just moving the overscan area should property notify observers.
412 UpdateDisplay("0+0-500x500");
413 int64 primary_id
= Shell::GetScreen()->GetPrimaryDisplay().id();
414 display_manager()->SetOverscanInsets(primary_id
, gfx::Insets(0, 0, 20, 20));
415 EXPECT_EQ("0,0 480x480",
416 Shell::GetScreen()->GetPrimaryDisplay().bounds().ToString());
418 display_manager()->SetOverscanInsets(primary_id
, gfx::Insets(10, 10, 10, 10));
419 EXPECT_TRUE(changed_metrics() & gfx::DisplayObserver::DISPLAY_METRIC_BOUNDS
);
421 changed_metrics() & gfx::DisplayObserver::DISPLAY_METRIC_WORK_AREA
);
422 EXPECT_EQ("0,0 480x480",
423 Shell::GetScreen()->GetPrimaryDisplay().bounds().ToString());
425 display_manager()->SetOverscanInsets(primary_id
, gfx::Insets(0, 0, 0, 0));
426 EXPECT_TRUE(changed_metrics() & gfx::DisplayObserver::DISPLAY_METRIC_BOUNDS
);
428 changed_metrics() & gfx::DisplayObserver::DISPLAY_METRIC_WORK_AREA
);
429 EXPECT_EQ("0,0 500x500",
430 Shell::GetScreen()->GetPrimaryDisplay().bounds().ToString());
433 TEST_F(DisplayManagerTest
, ZeroOverscanInsets
) {
434 if (!SupportsMultipleDisplays())
437 // Make sure the display change events is emitted for overscan inset changes.
438 UpdateDisplay("0+0-500x500,0+501-400x400");
439 ASSERT_EQ(2u, display_manager()->GetNumDisplays());
440 int64 display2_id
= display_manager()->GetDisplayAt(1).id();
443 display_manager()->SetOverscanInsets(display2_id
, gfx::Insets(0, 0, 0, 0));
444 EXPECT_EQ(0u, changed().size());
447 display_manager()->SetOverscanInsets(display2_id
, gfx::Insets(1, 0, 0, 0));
448 EXPECT_EQ(1u, changed().size());
449 EXPECT_EQ(display2_id
, changed()[0].id());
452 display_manager()->SetOverscanInsets(display2_id
, gfx::Insets(0, 0, 0, 0));
453 EXPECT_EQ(1u, changed().size());
454 EXPECT_EQ(display2_id
, changed()[0].id());
457 TEST_F(DisplayManagerTest
, TestDeviceScaleOnlyChange
) {
458 if (!SupportsHostWindowResize())
461 UpdateDisplay("1000x600");
462 aura::WindowTreeHost
* host
= Shell::GetPrimaryRootWindow()->GetHost();
463 EXPECT_EQ(1, host
->compositor()->device_scale_factor());
464 EXPECT_EQ("1000x600",
465 Shell::GetPrimaryRootWindow()->bounds().size().ToString());
466 EXPECT_EQ("1 0 0", GetCountSummary());
468 UpdateDisplay("1000x600*2");
469 EXPECT_EQ(2, host
->compositor()->device_scale_factor());
470 EXPECT_EQ("2 0 0", GetCountSummary());
472 Shell::GetPrimaryRootWindow()->bounds().size().ToString());
475 DisplayInfo
CreateDisplayInfo(int64 id
, const gfx::Rect
& bounds
) {
476 DisplayInfo
info(id
, ToDisplayName(id
), false);
477 info
.SetBounds(bounds
);
481 TEST_F(DisplayManagerTest
, TestNativeDisplaysChanged
) {
482 const int64 internal_display_id
=
483 test::DisplayManagerTestApi(display_manager()).
484 SetFirstDisplayAsInternalDisplay();
485 const int external_id
= 10;
486 const int mirror_id
= 11;
487 const int64 invalid_id
= gfx::Display::kInvalidDisplayID
;
488 const DisplayInfo internal_display_info
=
489 CreateDisplayInfo(internal_display_id
, gfx::Rect(0, 0, 500, 500));
490 const DisplayInfo external_display_info
=
491 CreateDisplayInfo(external_id
, gfx::Rect(1, 1, 100, 100));
492 const DisplayInfo mirroring_display_info
=
493 CreateDisplayInfo(mirror_id
, gfx::Rect(0, 0, 500, 500));
495 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
496 EXPECT_EQ(1U, display_manager()->num_connected_displays());
497 std::string default_bounds
=
498 display_manager()->GetDisplayAt(0).bounds().ToString();
500 std::vector
<DisplayInfo
> display_info_list
;
501 // Primary disconnected.
502 display_manager()->OnNativeDisplaysChanged(display_info_list
);
503 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
504 EXPECT_EQ(default_bounds
,
505 display_manager()->GetDisplayAt(0).bounds().ToString());
506 EXPECT_EQ(1U, display_manager()->num_connected_displays());
507 EXPECT_FALSE(display_manager()->IsInMirrorMode());
509 if (!SupportsMultipleDisplays())
512 // External connected while primary was disconnected.
513 display_info_list
.push_back(external_display_info
);
514 display_manager()->OnNativeDisplaysChanged(display_info_list
);
515 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
517 EXPECT_EQ(invalid_id
, GetDisplayForId(internal_display_id
).id());
518 EXPECT_EQ("1,1 100x100",
519 GetDisplayInfoForId(external_id
).bounds_in_native().ToString());
520 EXPECT_EQ(1U, display_manager()->num_connected_displays());
521 EXPECT_FALSE(display_manager()->IsInMirrorMode());
522 EXPECT_EQ(external_id
, Shell::GetScreen()->GetPrimaryDisplay().id());
524 EXPECT_EQ(internal_display_id
, gfx::Display::InternalDisplayId());
526 // Primary connected, with different bounds.
527 display_info_list
.clear();
528 display_info_list
.push_back(internal_display_info
);
529 display_info_list
.push_back(external_display_info
);
530 display_manager()->OnNativeDisplaysChanged(display_info_list
);
531 EXPECT_EQ(2U, display_manager()->GetNumDisplays());
532 EXPECT_EQ(internal_display_id
, Shell::GetScreen()->GetPrimaryDisplay().id());
534 // This combinatino is new, so internal display becomes primary.
535 EXPECT_EQ("0,0 500x500",
536 GetDisplayForId(internal_display_id
).bounds().ToString());
537 EXPECT_EQ("1,1 100x100",
538 GetDisplayInfoForId(10).bounds_in_native().ToString());
539 EXPECT_EQ(2U, display_manager()->num_connected_displays());
540 EXPECT_FALSE(display_manager()->IsInMirrorMode());
541 EXPECT_EQ(ToDisplayName(internal_display_id
),
542 display_manager()->GetDisplayNameForId(internal_display_id
));
545 display_info_list
.clear();
546 display_manager()->OnNativeDisplaysChanged(display_info_list
);
547 EXPECT_EQ(2U, display_manager()->GetNumDisplays());
548 EXPECT_EQ("0,0 500x500",
549 GetDisplayForId(internal_display_id
).bounds().ToString());
550 EXPECT_EQ("1,1 100x100",
551 GetDisplayInfoForId(10).bounds_in_native().ToString());
552 EXPECT_EQ(2U, display_manager()->num_connected_displays());
553 EXPECT_FALSE(display_manager()->IsInMirrorMode());
554 EXPECT_EQ(ToDisplayName(internal_display_id
),
555 display_manager()->GetDisplayNameForId(internal_display_id
));
557 // External display has disconnected then resumed.
558 display_info_list
.push_back(internal_display_info
);
559 display_manager()->OnNativeDisplaysChanged(display_info_list
);
560 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
561 EXPECT_EQ("0,0 500x500",
562 GetDisplayForId(internal_display_id
).bounds().ToString());
563 EXPECT_EQ(1U, display_manager()->num_connected_displays());
564 EXPECT_FALSE(display_manager()->IsInMirrorMode());
566 // External display was changed during suspend.
567 display_info_list
.push_back(external_display_info
);
568 display_manager()->OnNativeDisplaysChanged(display_info_list
);
569 EXPECT_EQ(2U, display_manager()->GetNumDisplays());
570 EXPECT_EQ(2U, display_manager()->num_connected_displays());
571 EXPECT_FALSE(display_manager()->IsInMirrorMode());
574 display_info_list
.clear();
575 display_manager()->OnNativeDisplaysChanged(display_info_list
);
576 EXPECT_EQ(2U, display_manager()->GetNumDisplays());
577 EXPECT_EQ(2U, display_manager()->num_connected_displays());
578 EXPECT_FALSE(display_manager()->IsInMirrorMode());
580 // and resume with different external display.
581 display_info_list
.push_back(internal_display_info
);
582 display_info_list
.push_back(CreateDisplayInfo(12, gfx::Rect(1, 1, 100, 100)));
583 display_manager()->OnNativeDisplaysChanged(display_info_list
);
584 EXPECT_EQ(2U, display_manager()->GetNumDisplays());
585 EXPECT_EQ(2U, display_manager()->num_connected_displays());
586 EXPECT_FALSE(display_manager()->IsInMirrorMode());
587 EXPECT_FALSE(display_manager()->IsInMirrorMode());
590 display_info_list
.clear();
591 display_info_list
.push_back(internal_display_info
);
592 display_info_list
.push_back(mirroring_display_info
);
593 display_manager()->OnNativeDisplaysChanged(display_info_list
);
594 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
595 EXPECT_EQ("0,0 500x500",
596 GetDisplayForId(internal_display_id
).bounds().ToString());
597 EXPECT_EQ(2U, display_manager()->num_connected_displays());
598 EXPECT_EQ(11U, display_manager()->mirroring_display_id());
599 EXPECT_TRUE(display_manager()->IsInMirrorMode());
601 // Test display name.
602 EXPECT_EQ(ToDisplayName(internal_display_id
),
603 display_manager()->GetDisplayNameForId(internal_display_id
));
604 EXPECT_EQ("x-10", display_manager()->GetDisplayNameForId(10));
605 EXPECT_EQ("x-11", display_manager()->GetDisplayNameForId(11));
606 EXPECT_EQ("x-12", display_manager()->GetDisplayNameForId(12));
607 // Default name for the id that doesn't exist.
608 EXPECT_EQ("Display 100", display_manager()->GetDisplayNameForId(100));
610 // and exit mirroring.
611 display_info_list
.clear();
612 display_info_list
.push_back(internal_display_info
);
613 display_info_list
.push_back(external_display_info
);
614 display_manager()->OnNativeDisplaysChanged(display_info_list
);
615 EXPECT_EQ(2U, display_manager()->GetNumDisplays());
616 EXPECT_EQ(2U, display_manager()->num_connected_displays());
617 EXPECT_FALSE(display_manager()->IsInMirrorMode());
618 EXPECT_EQ("0,0 500x500",
619 GetDisplayForId(internal_display_id
).bounds().ToString());
620 EXPECT_EQ("500,0 100x100",
621 GetDisplayForId(10).bounds().ToString());
624 display_info_list
.clear();
625 display_info_list
.push_back(external_display_info
);
626 display_manager()->OnNativeDisplaysChanged(display_info_list
);
627 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
628 EXPECT_EQ(invalid_id
, GetDisplayForId(internal_display_id
).id());
629 EXPECT_EQ("1,1 100x100",
630 GetDisplayInfoForId(external_id
).bounds_in_native().ToString());
631 EXPECT_EQ(1U, display_manager()->num_connected_displays());
632 EXPECT_FALSE(display_manager()->IsInMirrorMode());
634 // Switched to another display
635 display_info_list
.clear();
636 display_info_list
.push_back(internal_display_info
);
637 display_manager()->OnNativeDisplaysChanged(display_info_list
);
638 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
641 GetDisplayInfoForId(internal_display_id
).bounds_in_native().ToString());
642 EXPECT_EQ(1U, display_manager()->num_connected_displays());
643 EXPECT_FALSE(display_manager()->IsInMirrorMode());
646 // Make sure crash does not happen if add and remove happens at the same time.
647 // See: crbug.com/414394
648 TEST_F(DisplayManagerTest
, DisplayAddRemoveAtTheSameTime
) {
649 if (!SupportsMultipleDisplays())
652 UpdateDisplay("100+0-500x500,0+501-400x400");
654 const int64 primary_id
= DisplayController::GetPrimaryDisplayId();
655 const int64 secondary_id
= ScreenUtil::GetSecondaryDisplay().id();
657 DisplayInfo primary_info
= display_manager()->GetDisplayInfo(primary_id
);
658 DisplayInfo secondary_info
= display_manager()->GetDisplayInfo(secondary_id
);
660 // An id which is different from primary and secondary.
661 const int64 third_id
= primary_id
+ secondary_id
;
663 DisplayInfo third_info
=
664 CreateDisplayInfo(third_id
, gfx::Rect(0, 0, 600, 600));
666 std::vector
<DisplayInfo
> display_info_list
;
667 display_info_list
.push_back(third_info
);
668 display_info_list
.push_back(secondary_info
);
669 display_manager()->OnNativeDisplaysChanged(display_info_list
);
671 EXPECT_EQ(third_id
, DisplayController::GetPrimaryDisplayId());
672 EXPECT_EQ("600x600", GetDisplayForId(third_id
).size().ToString());
673 EXPECT_EQ(secondary_id
, ScreenUtil::GetSecondaryDisplay().id());
677 // TODO(scottmg): RootWindow doesn't get resized on Windows
678 // Ash. http://crbug.com/247916.
679 #define MAYBE_TestNativeDisplaysChangedNoInternal \
680 DISABLED_TestNativeDisplaysChangedNoInternal
682 #define MAYBE_TestNativeDisplaysChangedNoInternal \
683 TestNativeDisplaysChangedNoInternal
686 TEST_F(DisplayManagerTest
, MAYBE_TestNativeDisplaysChangedNoInternal
) {
687 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
689 // Don't change the display info if all displays are disconnected.
690 std::vector
<DisplayInfo
> display_info_list
;
691 display_manager()->OnNativeDisplaysChanged(display_info_list
);
692 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
694 // Connect another display which will become primary.
695 const DisplayInfo external_display_info
=
696 CreateDisplayInfo(10, gfx::Rect(1, 1, 100, 100));
697 display_info_list
.push_back(external_display_info
);
698 display_manager()->OnNativeDisplaysChanged(display_info_list
);
699 EXPECT_EQ(1U, display_manager()->GetNumDisplays());
700 EXPECT_EQ("1,1 100x100",
701 GetDisplayInfoForId(10).bounds_in_native().ToString());
702 EXPECT_EQ("100x100", ash::Shell::GetPrimaryRootWindow()->GetHost()->
703 GetBounds().size().ToString());
706 TEST_F(DisplayManagerTest
, NativeDisplaysChangedAfterPrimaryChange
) {
707 if (!SupportsMultipleDisplays())
710 const int64 internal_display_id
=
711 test::DisplayManagerTestApi(display_manager()).
712 SetFirstDisplayAsInternalDisplay();
713 const DisplayInfo native_display_info
=
714 CreateDisplayInfo(internal_display_id
, gfx::Rect(0, 0, 500, 500));
715 const DisplayInfo secondary_display_info
=
716 CreateDisplayInfo(10, gfx::Rect(1, 1, 100, 100));
718 std::vector
<DisplayInfo
> display_info_list
;
719 display_info_list
.push_back(native_display_info
);
720 display_info_list
.push_back(secondary_display_info
);
721 display_manager()->OnNativeDisplaysChanged(display_info_list
);
722 EXPECT_EQ(2U, display_manager()->GetNumDisplays());
723 EXPECT_EQ("0,0 500x500",
724 GetDisplayForId(internal_display_id
).bounds().ToString());
725 EXPECT_EQ("500,0 100x100", GetDisplayForId(10).bounds().ToString());
727 ash::Shell::GetInstance()->display_controller()->SetPrimaryDisplay(
728 GetDisplayForId(secondary_display_info
.id()));
729 EXPECT_EQ("-500,0 500x500",
730 GetDisplayForId(internal_display_id
).bounds().ToString());
731 EXPECT_EQ("0,0 100x100", GetDisplayForId(10).bounds().ToString());
733 // OnNativeDisplaysChanged may change the display bounds. Here makes sure
734 // nothing changed if the exactly same displays are specified.
735 display_manager()->OnNativeDisplaysChanged(display_info_list
);
736 EXPECT_EQ("-500,0 500x500",
737 GetDisplayForId(internal_display_id
).bounds().ToString());
738 EXPECT_EQ("0,0 100x100", GetDisplayForId(10).bounds().ToString());
741 TEST_F(DisplayManagerTest
, DontRememberBestResolution
) {
742 int display_id
= 1000;
743 DisplayInfo native_display_info
=
744 CreateDisplayInfo(display_id
, gfx::Rect(0, 0, 1000, 500));
745 std::vector
<DisplayMode
> display_modes
;
746 display_modes
.push_back(
747 DisplayMode(gfx::Size(1000, 500), 58.0f
, false, true));
748 display_modes
.push_back(
749 DisplayMode(gfx::Size(800, 300), 59.0f
, false, false));
750 display_modes
.push_back(
751 DisplayMode(gfx::Size(400, 500), 60.0f
, false, false));
753 native_display_info
.SetDisplayModes(display_modes
);
755 std::vector
<DisplayInfo
> display_info_list
;
756 display_info_list
.push_back(native_display_info
);
757 display_manager()->OnNativeDisplaysChanged(display_info_list
);
760 DisplayMode expected_mode
;
761 expected_mode
.size
= gfx::Size(1000, 500);
763 display_manager()->GetSelectedModeForDisplayId(display_id
, &mode
));
764 EXPECT_TRUE(expected_mode
.IsEquivalent(
765 display_manager()->GetActiveModeForDisplayId(display_id
)));
767 // Unsupported resolution.
768 display_manager()->SetDisplayResolution(display_id
, gfx::Size(800, 4000));
770 display_manager()->GetSelectedModeForDisplayId(display_id
, &mode
));
771 EXPECT_TRUE(expected_mode
.IsEquivalent(
772 display_manager()->GetActiveModeForDisplayId(display_id
)));
774 // Supported resolution.
775 display_manager()->SetDisplayResolution(display_id
, gfx::Size(800, 300));
777 display_manager()->GetSelectedModeForDisplayId(display_id
, &mode
));
778 EXPECT_EQ("800x300", mode
.size
.ToString());
779 EXPECT_EQ(59.0f
, mode
.refresh_rate
);
780 EXPECT_FALSE(mode
.native
);
781 expected_mode
.size
= gfx::Size(800, 300);
782 EXPECT_TRUE(expected_mode
.IsEquivalent(
783 display_manager()->GetActiveModeForDisplayId(display_id
)));
786 display_manager()->SetDisplayResolution(display_id
, gfx::Size(1000, 500));
788 display_manager()->GetSelectedModeForDisplayId(display_id
, &mode
));
789 EXPECT_EQ("1000x500", mode
.size
.ToString());
790 EXPECT_EQ(58.0f
, mode
.refresh_rate
);
791 EXPECT_TRUE(mode
.native
);
792 expected_mode
.size
= gfx::Size(1000, 500);
793 EXPECT_TRUE(expected_mode
.IsEquivalent(
794 display_manager()->GetActiveModeForDisplayId(display_id
)));
797 TEST_F(DisplayManagerTest
, ResolutionFallback
) {
798 int display_id
= 1000;
799 DisplayInfo native_display_info
=
800 CreateDisplayInfo(display_id
, gfx::Rect(0, 0, 1000, 500));
801 std::vector
<DisplayMode
> display_modes
;
802 display_modes
.push_back(
803 DisplayMode(gfx::Size(1000, 500), 58.0f
, false, true));
804 display_modes
.push_back(
805 DisplayMode(gfx::Size(800, 300), 59.0f
, false, false));
806 display_modes
.push_back(
807 DisplayMode(gfx::Size(400, 500), 60.0f
, false, false));
809 std::vector
<DisplayMode
> copy
= display_modes
;
810 native_display_info
.SetDisplayModes(copy
);
812 std::vector
<DisplayInfo
> display_info_list
;
813 display_info_list
.push_back(native_display_info
);
814 display_manager()->OnNativeDisplaysChanged(display_info_list
);
816 display_manager()->SetDisplayResolution(display_id
, gfx::Size(800, 300));
817 DisplayInfo new_native_display_info
=
818 CreateDisplayInfo(display_id
, gfx::Rect(0, 0, 400, 500));
819 copy
= display_modes
;
820 new_native_display_info
.SetDisplayModes(copy
);
821 std::vector
<DisplayInfo
> new_display_info_list
;
822 new_display_info_list
.push_back(new_native_display_info
);
823 display_manager()->OnNativeDisplaysChanged(new_display_info_list
);
827 display_manager()->GetSelectedModeForDisplayId(display_id
, &mode
));
828 EXPECT_EQ("400x500", mode
.size
.ToString());
829 EXPECT_EQ(60.0f
, mode
.refresh_rate
);
830 EXPECT_FALSE(mode
.native
);
833 // Best resolution should find itself on the resolutions list.
834 display_manager()->SetDisplayResolution(display_id
, gfx::Size(800, 300));
835 DisplayInfo new_native_display_info
=
836 CreateDisplayInfo(display_id
, gfx::Rect(0, 0, 1000, 500));
837 std::vector
<DisplayMode
> copy
= display_modes
;
838 new_native_display_info
.SetDisplayModes(copy
);
839 std::vector
<DisplayInfo
> new_display_info_list
;
840 new_display_info_list
.push_back(new_native_display_info
);
841 display_manager()->OnNativeDisplaysChanged(new_display_info_list
);
845 display_manager()->GetSelectedModeForDisplayId(display_id
, &mode
));
846 EXPECT_EQ("1000x500", mode
.size
.ToString());
847 EXPECT_EQ(58.0f
, mode
.refresh_rate
);
848 EXPECT_TRUE(mode
.native
);
852 TEST_F(DisplayManagerTest
, Rotate
) {
853 if (!SupportsMultipleDisplays())
856 UpdateDisplay("100x200/r,300x400/l");
857 EXPECT_EQ("1,1 100x200",
858 GetDisplayInfoAt(0).bounds_in_native().ToString());
860 GetDisplayInfoAt(0).size_in_pixel().ToString());
862 EXPECT_EQ("1,201 300x400",
863 GetDisplayInfoAt(1).bounds_in_native().ToString());
865 GetDisplayInfoAt(1).size_in_pixel().ToString());
867 UpdateDisplay("100x200/b,300x400");
868 EXPECT_EQ("2 0 0", GetCountSummary());
871 EXPECT_EQ("1,1 100x200",
872 GetDisplayInfoAt(0).bounds_in_native().ToString());
874 GetDisplayInfoAt(0).size_in_pixel().ToString());
876 EXPECT_EQ("1,201 300x400",
877 GetDisplayInfoAt(1).bounds_in_native().ToString());
879 GetDisplayInfoAt(1).size_in_pixel().ToString());
881 // Just Rotating display will change the bounds on both display.
882 UpdateDisplay("100x200/l,300x400");
883 EXPECT_EQ("2 0 0", GetCountSummary());
886 // Updating to the same configuration should report no changes.
887 UpdateDisplay("100x200/l,300x400");
888 EXPECT_EQ("0 0 0", GetCountSummary());
891 // Rotating 180 degrees should report one change.
892 UpdateDisplay("100x200/r,300x400");
893 EXPECT_EQ("1 0 0", GetCountSummary());
896 UpdateDisplay("200x200");
897 EXPECT_EQ("1 0 1", GetCountSummary());
900 // Rotating 180 degrees should report one change.
901 UpdateDisplay("200x200/u");
902 EXPECT_EQ("1 0 0", GetCountSummary());
905 UpdateDisplay("200x200/l");
906 EXPECT_EQ("1 0 0", GetCountSummary());
908 // Having the internal display deactivated should restore user rotation. Newly
909 // set rotations should be applied.
910 UpdateDisplay("200x200, 200x200");
911 const int64 internal_display_id
=
912 test::DisplayManagerTestApi(display_manager())
913 .SetFirstDisplayAsInternalDisplay();
915 display_manager()->SetDisplayRotation(internal_display_id
,
916 gfx::Display::ROTATE_90
,
917 gfx::Display::ROTATION_SOURCE_USER
);
918 display_manager()->SetDisplayRotation(internal_display_id
,
919 gfx::Display::ROTATE_0
,
920 gfx::Display::ROTATION_SOURCE_ACTIVE
);
922 const DisplayInfo info
= GetDisplayInfoForId(internal_display_id
);
923 EXPECT_EQ(gfx::Display::ROTATE_0
, info
.GetActiveRotation());
925 // Deactivate internal display to simulate Docked Mode.
926 vector
<DisplayInfo
> secondary_only
;
927 secondary_only
.push_back(GetDisplayInfoAt(1));
928 display_manager()->OnNativeDisplaysChanged(secondary_only
);
930 const DisplayInfo post_removal_info
=
931 display_manager()->display_info_
[internal_display_id
];
932 EXPECT_NE(info
.GetActiveRotation(), post_removal_info
.GetActiveRotation());
933 EXPECT_EQ(gfx::Display::ROTATE_90
, post_removal_info
.GetActiveRotation());
935 display_manager()->SetDisplayRotation(internal_display_id
,
936 gfx::Display::ROTATE_180
,
937 gfx::Display::ROTATION_SOURCE_ACTIVE
);
938 const DisplayInfo post_rotation_info
=
939 display_manager()->display_info_
[internal_display_id
];
940 EXPECT_NE(info
.GetActiveRotation(), post_rotation_info
.GetActiveRotation());
941 EXPECT_EQ(gfx::Display::ROTATE_180
, post_rotation_info
.GetActiveRotation());
944 TEST_F(DisplayManagerTest
, UIScale
) {
945 test::ScopedDisable125DSFForUIScaling disable
;
947 UpdateDisplay("1280x800");
948 int64 display_id
= Shell::GetScreen()->GetPrimaryDisplay().id();
949 display_manager()->SetDisplayUIScale(display_id
, 1.125f
);
950 EXPECT_EQ(1.0, GetDisplayInfoAt(0).configured_ui_scale());
951 display_manager()->SetDisplayUIScale(display_id
, 0.8f
);
952 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
953 display_manager()->SetDisplayUIScale(display_id
, 0.75f
);
954 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
955 display_manager()->SetDisplayUIScale(display_id
, 0.625f
);
956 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
958 test::DisplayManagerTestApi(display_manager())
959 .SetInternalDisplayId(display_id
);
961 display_manager()->SetDisplayUIScale(display_id
, 1.5f
);
962 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
963 display_manager()->SetDisplayUIScale(display_id
, 1.25f
);
964 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
965 display_manager()->SetDisplayUIScale(display_id
, 1.125f
);
966 EXPECT_EQ(1.125f
, GetDisplayInfoAt(0).configured_ui_scale());
967 display_manager()->SetDisplayUIScale(display_id
, 0.8f
);
968 EXPECT_EQ(0.8f
, GetDisplayInfoAt(0).configured_ui_scale());
969 display_manager()->SetDisplayUIScale(display_id
, 0.75f
);
970 EXPECT_EQ(0.8f
, GetDisplayInfoAt(0).configured_ui_scale());
971 display_manager()->SetDisplayUIScale(display_id
, 0.625f
);
972 EXPECT_EQ(0.625f
, GetDisplayInfoAt(0).configured_ui_scale());
973 display_manager()->SetDisplayUIScale(display_id
, 0.6f
);
974 EXPECT_EQ(0.625f
, GetDisplayInfoAt(0).configured_ui_scale());
975 display_manager()->SetDisplayUIScale(display_id
, 0.5f
);
976 EXPECT_EQ(0.5f
, GetDisplayInfoAt(0).configured_ui_scale());
978 UpdateDisplay("1366x768");
979 display_manager()->SetDisplayUIScale(display_id
, 1.5f
);
980 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
981 display_manager()->SetDisplayUIScale(display_id
, 1.25f
);
982 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
983 display_manager()->SetDisplayUIScale(display_id
, 1.125f
);
984 EXPECT_EQ(1.125f
, GetDisplayInfoAt(0).configured_ui_scale());
985 display_manager()->SetDisplayUIScale(display_id
, 0.8f
);
986 EXPECT_EQ(1.125f
, GetDisplayInfoAt(0).configured_ui_scale());
987 display_manager()->SetDisplayUIScale(display_id
, 0.75f
);
988 EXPECT_EQ(0.75f
, GetDisplayInfoAt(0).configured_ui_scale());
989 display_manager()->SetDisplayUIScale(display_id
, 0.6f
);
990 EXPECT_EQ(0.6f
, GetDisplayInfoAt(0).configured_ui_scale());
991 display_manager()->SetDisplayUIScale(display_id
, 0.625f
);
992 EXPECT_EQ(0.6f
, GetDisplayInfoAt(0).configured_ui_scale());
993 display_manager()->SetDisplayUIScale(display_id
, 0.5f
);
994 EXPECT_EQ(0.5f
, GetDisplayInfoAt(0).configured_ui_scale());
996 UpdateDisplay("1280x850*2");
997 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
998 display_manager()->SetDisplayUIScale(display_id
, 1.5f
);
999 EXPECT_EQ(1.5f
, GetDisplayInfoAt(0).configured_ui_scale());
1000 display_manager()->SetDisplayUIScale(display_id
, 1.25f
);
1001 EXPECT_EQ(1.25f
, GetDisplayInfoAt(0).configured_ui_scale());
1002 display_manager()->SetDisplayUIScale(display_id
, 1.125f
);
1003 EXPECT_EQ(1.125f
, GetDisplayInfoAt(0).configured_ui_scale());
1004 display_manager()->SetDisplayUIScale(display_id
, 1.0f
);
1005 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
1006 gfx::Display display
= Shell::GetScreen()->GetPrimaryDisplay();
1007 EXPECT_EQ(2.0f
, display
.device_scale_factor());
1008 EXPECT_EQ("640x425", display
.bounds().size().ToString());
1010 display_manager()->SetDisplayUIScale(display_id
, 0.8f
);
1011 EXPECT_EQ(0.8f
, GetDisplayInfoAt(0).configured_ui_scale());
1012 display_manager()->SetDisplayUIScale(display_id
, 0.75f
);
1013 EXPECT_EQ(0.8f
, GetDisplayInfoAt(0).configured_ui_scale());
1014 display_manager()->SetDisplayUIScale(display_id
, 0.625f
);
1015 EXPECT_EQ(0.625f
, GetDisplayInfoAt(0).configured_ui_scale());
1016 display_manager()->SetDisplayUIScale(display_id
, 0.6f
);
1017 EXPECT_EQ(0.625f
, GetDisplayInfoAt(0).configured_ui_scale());
1018 display_manager()->SetDisplayUIScale(display_id
, 0.5f
);
1019 EXPECT_EQ(0.5f
, GetDisplayInfoAt(0).configured_ui_scale());
1021 display_manager()->SetDisplayUIScale(display_id
, 2.0f
);
1022 EXPECT_EQ(2.0f
, GetDisplayInfoAt(0).configured_ui_scale());
1023 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).GetEffectiveUIScale());
1024 display
= Shell::GetScreen()->GetPrimaryDisplay();
1025 EXPECT_EQ(1.0f
, display
.device_scale_factor());
1026 EXPECT_EQ("1280x850", display
.bounds().size().ToString());
1028 // 1.25 ui scaling on 1.25 DSF device should use 1.0 DSF
1030 UpdateDisplay("1280x850*1.25");
1031 display_manager()->SetDisplayUIScale(display_id
, 1.25f
);
1032 EXPECT_EQ(1.25f
, GetDisplayInfoAt(0).configured_ui_scale());
1033 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).GetEffectiveUIScale());
1034 display
= Shell::GetScreen()->GetPrimaryDisplay();
1035 EXPECT_EQ(1.0f
, display
.device_scale_factor());
1036 EXPECT_EQ("1280x850", display
.bounds().size().ToString());
1039 TEST_F(DisplayManagerTest
, UIScaleWithDisplayMode
) {
1040 int display_id
= 1000;
1042 // Setup the display modes with UI-scale.
1043 DisplayInfo native_display_info
=
1044 CreateDisplayInfo(display_id
, gfx::Rect(0, 0, 1280, 800));
1045 std::vector
<DisplayMode
> display_modes
;
1046 const DisplayMode
base_mode(gfx::Size(1280, 800), 60.0f
, false, false);
1047 std::vector
<DisplayMode
> mode_list
= CreateInternalDisplayModeList(base_mode
);
1048 native_display_info
.SetDisplayModes(mode_list
);
1050 std::vector
<DisplayInfo
> display_info_list
;
1051 display_info_list
.push_back(native_display_info
);
1052 display_manager()->OnNativeDisplaysChanged(display_info_list
);
1054 DisplayMode expected_mode
= base_mode
;
1055 EXPECT_TRUE(expected_mode
.IsEquivalent(
1056 display_manager()->GetActiveModeForDisplayId(display_id
)));
1058 display_manager()->SetDisplayUIScale(display_id
, 1.125f
);
1059 EXPECT_EQ(1.0, GetDisplayInfoAt(0).configured_ui_scale());
1060 EXPECT_TRUE(expected_mode
.IsEquivalent(
1061 display_manager()->GetActiveModeForDisplayId(display_id
)));
1062 display_manager()->SetDisplayUIScale(display_id
, 0.8f
);
1063 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
1064 EXPECT_TRUE(expected_mode
.IsEquivalent(
1065 display_manager()->GetActiveModeForDisplayId(display_id
)));
1066 display_manager()->SetDisplayUIScale(display_id
, 0.75f
);
1067 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
1068 EXPECT_TRUE(expected_mode
.IsEquivalent(
1069 display_manager()->GetActiveModeForDisplayId(display_id
)));
1070 display_manager()->SetDisplayUIScale(display_id
, 0.625f
);
1071 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
1072 EXPECT_TRUE(expected_mode
.IsEquivalent(
1073 display_manager()->GetActiveModeForDisplayId(display_id
)));
1075 test::DisplayManagerTestApi(display_manager())
1076 .SetInternalDisplayId(display_id
);
1078 display_manager()->SetDisplayUIScale(display_id
, 1.5f
);
1079 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
1080 EXPECT_TRUE(expected_mode
.IsEquivalent(
1081 display_manager()->GetActiveModeForDisplayId(display_id
)));
1082 display_manager()->SetDisplayUIScale(display_id
, 1.25f
);
1083 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).configured_ui_scale());
1084 EXPECT_TRUE(expected_mode
.IsEquivalent(
1085 display_manager()->GetActiveModeForDisplayId(display_id
)));
1086 display_manager()->SetDisplayUIScale(display_id
, 1.125f
);
1087 EXPECT_EQ(1.125f
, GetDisplayInfoAt(0).configured_ui_scale());
1088 expected_mode
.ui_scale
= 1.125f
;
1089 EXPECT_TRUE(expected_mode
.IsEquivalent(
1090 display_manager()->GetActiveModeForDisplayId(display_id
)));
1091 display_manager()->SetDisplayUIScale(display_id
, 0.8f
);
1092 EXPECT_EQ(0.8f
, GetDisplayInfoAt(0).configured_ui_scale());
1093 expected_mode
.ui_scale
= 0.8f
;
1094 EXPECT_TRUE(expected_mode
.IsEquivalent(
1095 display_manager()->GetActiveModeForDisplayId(display_id
)));
1096 display_manager()->SetDisplayUIScale(display_id
, 0.75f
);
1097 EXPECT_EQ(0.8f
, GetDisplayInfoAt(0).configured_ui_scale());
1098 EXPECT_TRUE(expected_mode
.IsEquivalent(
1099 display_manager()->GetActiveModeForDisplayId(display_id
)));
1100 display_manager()->SetDisplayUIScale(display_id
, 0.625f
);
1101 EXPECT_EQ(0.625f
, GetDisplayInfoAt(0).configured_ui_scale());
1102 expected_mode
.ui_scale
= 0.625f
;
1103 EXPECT_TRUE(expected_mode
.IsEquivalent(
1104 display_manager()->GetActiveModeForDisplayId(display_id
)));
1105 display_manager()->SetDisplayUIScale(display_id
, 0.6f
);
1106 EXPECT_EQ(0.625f
, GetDisplayInfoAt(0).configured_ui_scale());
1107 EXPECT_TRUE(expected_mode
.IsEquivalent(
1108 display_manager()->GetActiveModeForDisplayId(display_id
)));
1109 display_manager()->SetDisplayUIScale(display_id
, 0.5f
);
1110 EXPECT_EQ(0.5f
, GetDisplayInfoAt(0).configured_ui_scale());
1111 expected_mode
.ui_scale
= 0.5f
;
1112 EXPECT_TRUE(expected_mode
.IsEquivalent(
1113 display_manager()->GetActiveModeForDisplayId(display_id
)));
1116 TEST_F(DisplayManagerTest
, Use125DSFForUIScaling
) {
1117 int64 display_id
= Shell::GetScreen()->GetPrimaryDisplay().id();
1118 test::DisplayManagerTestApi(display_manager())
1119 .SetInternalDisplayId(display_id
);
1121 UpdateDisplay("1920x1080*1.25");
1122 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).GetEffectiveDeviceScaleFactor());
1123 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).GetEffectiveUIScale());
1125 display_manager()->SetDisplayUIScale(display_id
, 0.8f
);
1126 EXPECT_EQ(1.25f
, GetDisplayInfoAt(0).GetEffectiveDeviceScaleFactor());
1127 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).GetEffectiveUIScale());
1128 EXPECT_EQ("1536x864", GetDisplayForId(display_id
).size().ToString());
1130 display_manager()->SetDisplayUIScale(display_id
, 0.5f
);
1131 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).GetEffectiveDeviceScaleFactor());
1132 EXPECT_EQ(0.5f
, GetDisplayInfoAt(0).GetEffectiveUIScale());
1133 EXPECT_EQ("960x540", GetDisplayForId(display_id
).size().ToString());
1135 display_manager()->SetDisplayUIScale(display_id
, 1.25f
);
1136 EXPECT_EQ(1.0f
, GetDisplayInfoAt(0).GetEffectiveDeviceScaleFactor());
1137 EXPECT_EQ(1.25f
, GetDisplayInfoAt(0).GetEffectiveUIScale());
1138 EXPECT_EQ("2400x1350", GetDisplayForId(display_id
).size().ToString());
1141 TEST_F(DisplayManagerTest
, UIScaleInUnifiedMode
) {
1142 if (!SupportsMultipleDisplays())
1145 test::DisplayManagerTestApi::EnableUnifiedDesktopForTest();
1147 // Don't check root window destruction in unified mode.
1148 Shell::GetPrimaryRootWindow()->RemoveObserver(this);
1150 DisplayManager
* display_manager
= Shell::GetInstance()->display_manager();
1152 UpdateDisplay("200x200, 400x400");
1154 int64 unified_id
= Shell::GetScreen()->GetPrimaryDisplay().id();
1155 EXPECT_EQ("800x400",
1156 Shell::GetScreen()->GetPrimaryDisplay().size().ToString());
1157 DisplayMode active_mode
=
1158 display_manager
->GetActiveModeForDisplayId(unified_id
);
1159 EXPECT_EQ(1.0f
, active_mode
.ui_scale
);
1160 EXPECT_EQ("800x400", active_mode
.size
.ToString());
1162 EXPECT_TRUE(display_manager
->SetDisplayUIScale(unified_id
, 0.5f
));
1163 EXPECT_EQ("400x200",
1164 Shell::GetScreen()->GetPrimaryDisplay().size().ToString());
1165 active_mode
= display_manager
->GetActiveModeForDisplayId(unified_id
);
1166 EXPECT_EQ(0.5f
, active_mode
.ui_scale
);
1167 EXPECT_EQ("800x400", active_mode
.size
.ToString());
1169 // UI scale will not persist in unified desktop mode.
1170 UpdateDisplay("200x200, 600x600");
1171 EXPECT_EQ("1200x600",
1172 Shell::GetScreen()->GetPrimaryDisplay().size().ToString());
1173 active_mode
= display_manager
->GetActiveModeForDisplayId(unified_id
);
1174 EXPECT_EQ(1.0f
, active_mode
.ui_scale
);
1175 EXPECT_EQ("1200x600", active_mode
.size
.ToString());
1179 // TODO(scottmg): RootWindow doesn't get resized on Windows
1180 // Ash. http://crbug.com/247916.
1181 #define MAYBE_UpdateMouseCursorAfterRotateZoom DISABLED_UpdateMouseCursorAfterRotateZoom
1183 #define MAYBE_UpdateMouseCursorAfterRotateZoom UpdateMouseCursorAfterRotateZoom
1186 TEST_F(DisplayManagerTest
, MAYBE_UpdateMouseCursorAfterRotateZoom
) {
1187 // Make sure just rotating will not change native location.
1188 UpdateDisplay("300x200,200x150");
1189 aura::Window::Windows root_windows
= Shell::GetAllRootWindows();
1190 aura::Env
* env
= aura::Env::GetInstance();
1192 ui::test::EventGenerator
generator1(root_windows
[0]);
1193 ui::test::EventGenerator
generator2(root_windows
[1]);
1195 // Test on 1st display.
1196 generator1
.MoveMouseToInHost(150, 50);
1197 EXPECT_EQ("150,50", env
->last_mouse_location().ToString());
1198 UpdateDisplay("300x200/r,200x150");
1199 EXPECT_EQ("50,149", env
->last_mouse_location().ToString());
1201 // Test on 2nd display.
1202 generator2
.MoveMouseToInHost(50, 100);
1203 EXPECT_EQ("250,100", env
->last_mouse_location().ToString());
1204 UpdateDisplay("300x200/r,200x150/l");
1205 EXPECT_EQ("249,50", env
->last_mouse_location().ToString());
1207 // The native location is now outside, so move to the center
1208 // of closest display.
1209 UpdateDisplay("300x200/r,100x50/l");
1210 EXPECT_EQ("225,50", env
->last_mouse_location().ToString());
1212 // Make sure just zooming will not change native location.
1213 UpdateDisplay("600x400*2,400x300");
1215 // Test on 1st display.
1216 generator1
.MoveMouseToInHost(200, 300);
1217 EXPECT_EQ("100,150", env
->last_mouse_location().ToString());
1218 UpdateDisplay("600x400*2@1.5,400x300");
1219 EXPECT_EQ("150,225", env
->last_mouse_location().ToString());
1221 // Test on 2nd display.
1222 UpdateDisplay("600x400,400x300*2");
1223 generator2
.MoveMouseToInHost(200, 250);
1224 EXPECT_EQ("700,125", env
->last_mouse_location().ToString());
1225 UpdateDisplay("600x400,400x300*2@1.5");
1226 EXPECT_EQ("750,187", env
->last_mouse_location().ToString());
1228 // The native location is now outside, so move to the
1229 // center of closest display.
1230 UpdateDisplay("600x400,400x200*2@1.5");
1231 EXPECT_EQ("750,75", env
->last_mouse_location().ToString());
1234 class TestDisplayObserver
: public gfx::DisplayObserver
{
1236 TestDisplayObserver() : changed_(false) {}
1237 ~TestDisplayObserver() override
{}
1239 // gfx::DisplayObserver overrides:
1240 void OnDisplayMetricsChanged(const gfx::Display
&, uint32_t) override
{}
1241 void OnDisplayAdded(const gfx::Display
& new_display
) override
{
1242 // Mirror window should already be delete before restoring
1243 // the external display.
1244 EXPECT_FALSE(test_api
.GetHost());
1247 void OnDisplayRemoved(const gfx::Display
& old_display
) override
{
1248 // Mirror window should not be created until the external display
1250 EXPECT_FALSE(test_api
.GetHost());
1254 bool changed_and_reset() {
1255 bool changed
= changed_
;
1261 test::MirrorWindowTestApi test_api
;
1264 DISALLOW_COPY_AND_ASSIGN(TestDisplayObserver
);
1267 TEST_F(DisplayManagerTest
, SoftwareMirroring
) {
1268 if (!SupportsMultipleDisplays())
1271 UpdateDisplay("300x400,400x500");
1273 test::MirrorWindowTestApi test_api
;
1274 EXPECT_EQ(NULL
, test_api
.GetHost());
1276 TestDisplayObserver display_observer
;
1277 Shell::GetScreen()->AddObserver(&display_observer
);
1279 DisplayManager
* display_manager
= Shell::GetInstance()->display_manager();
1280 display_manager
->SetMultiDisplayMode(DisplayManager::MIRRORING
);
1281 display_manager
->UpdateDisplays();
1282 RunAllPendingInMessageLoop();
1283 EXPECT_TRUE(display_observer
.changed_and_reset());
1284 EXPECT_EQ(1U, display_manager
->GetNumDisplays());
1285 EXPECT_EQ("0,0 300x400",
1286 Shell::GetScreen()->GetPrimaryDisplay().bounds().ToString());
1287 EXPECT_EQ("400x500", test_api
.GetHost()->GetBounds().size().ToString());
1288 EXPECT_EQ("300x400",
1289 test_api
.GetHost()->window()->bounds().size().ToString());
1290 EXPECT_TRUE(display_manager
->IsInMirrorMode());
1292 display_manager
->SetMirrorMode(false);
1293 EXPECT_TRUE(display_observer
.changed_and_reset());
1294 EXPECT_EQ(NULL
, test_api
.GetHost());
1295 EXPECT_EQ(2U, display_manager
->GetNumDisplays());
1296 EXPECT_FALSE(display_manager
->IsInMirrorMode());
1298 // Make sure the mirror window has the pixel size of the
1300 display_manager
->SetMirrorMode(true);
1301 EXPECT_TRUE(display_observer
.changed_and_reset());
1303 UpdateDisplay("300x400@0.5,400x500");
1304 EXPECT_FALSE(display_observer
.changed_and_reset());
1305 EXPECT_EQ("300x400",
1306 test_api
.GetHost()->window()->bounds().size().ToString());
1308 UpdateDisplay("310x410*2,400x500");
1309 EXPECT_FALSE(display_observer
.changed_and_reset());
1310 EXPECT_EQ("310x410",
1311 test_api
.GetHost()->window()->bounds().size().ToString());
1313 UpdateDisplay("320x420/r,400x500");
1314 EXPECT_FALSE(display_observer
.changed_and_reset());
1315 EXPECT_EQ("320x420",
1316 test_api
.GetHost()->window()->bounds().size().ToString());
1318 UpdateDisplay("330x440/r,400x500");
1319 EXPECT_FALSE(display_observer
.changed_and_reset());
1320 EXPECT_EQ("330x440",
1321 test_api
.GetHost()->window()->bounds().size().ToString());
1323 // Overscan insets are ignored.
1324 UpdateDisplay("400x600/o,600x800/o");
1325 EXPECT_FALSE(display_observer
.changed_and_reset());
1326 EXPECT_EQ("400x600",
1327 test_api
.GetHost()->window()->bounds().size().ToString());
1329 Shell::GetScreen()->RemoveObserver(&display_observer
);
1332 TEST_F(DisplayManagerTest
, SingleDisplayToSoftwareMirroring
) {
1333 if (!SupportsMultipleDisplays())
1335 UpdateDisplay("600x400");
1337 DisplayManager
* display_manager
= Shell::GetInstance()->display_manager();
1338 display_manager
->SetMultiDisplayMode(DisplayManager::MIRRORING
);
1339 UpdateDisplay("600x400,600x400");
1341 EXPECT_TRUE(display_manager
->IsInMirrorMode());
1342 EXPECT_EQ(1U, display_manager
->GetNumDisplays());
1343 DisplayController
* display_controller
=
1344 ash::Shell::GetInstance()->display_controller();
1345 EXPECT_TRUE(display_controller
->mirror_window_controller()->GetWindow());
1347 UpdateDisplay("600x400");
1348 EXPECT_FALSE(display_manager
->IsInMirrorMode());
1349 EXPECT_EQ(1U, display_manager
->GetNumDisplays());
1350 EXPECT_FALSE(display_controller
->mirror_window_controller()->GetWindow());
1353 #if defined(OS_CHROMEOS)
1354 // Make sure this does not cause any crashes. See http://crbug.com/412910
1355 // This test is limited to OS_CHROMEOS because CursorCompositingEnabled is only
1357 TEST_F(DisplayManagerTest
, SoftwareMirroringWithCompositingCursor
) {
1358 if (!SupportsMultipleDisplays())
1361 UpdateDisplay("300x400,400x500");
1363 test::MirrorWindowTestApi test_api
;
1364 EXPECT_EQ(NULL
, test_api
.GetHost());
1366 DisplayManager
* display_manager
= Shell::GetInstance()->display_manager();
1367 DisplayInfo secondary_info
= display_manager
->GetDisplayInfo(
1368 ScreenUtil::GetSecondaryDisplay().id());
1370 display_manager
->SetSoftwareMirroring(true);
1371 display_manager
->UpdateDisplays();
1373 aura::Window::Windows root_windows
= Shell::GetAllRootWindows();
1374 EXPECT_FALSE(root_windows
[0]->Contains(test_api
.GetCursorWindow()));
1376 Shell::GetInstance()->SetCursorCompositingEnabled(true);
1378 EXPECT_TRUE(root_windows
[0]->Contains(test_api
.GetCursorWindow()));
1380 // Removes the first display and keeps the second one.
1381 display_manager
->SetSoftwareMirroring(false);
1382 std::vector
<DisplayInfo
> new_info_list
;
1383 new_info_list
.push_back(secondary_info
);
1384 display_manager
->OnNativeDisplaysChanged(new_info_list
);
1386 root_windows
= Shell::GetAllRootWindows();
1387 EXPECT_TRUE(root_windows
[0]->Contains(test_api
.GetCursorWindow()));
1389 Shell::GetInstance()->SetCursorCompositingEnabled(false);
1391 #endif // OS_CHROMEOS
1393 TEST_F(DisplayManagerTest
, MirroredLayout
) {
1394 if (!SupportsMultipleDisplays())
1397 DisplayManager
* display_manager
= Shell::GetInstance()->display_manager();
1398 UpdateDisplay("500x500,400x400");
1399 EXPECT_FALSE(display_manager
->GetCurrentDisplayLayout().mirrored
);
1400 EXPECT_EQ(2, Shell::GetScreen()->GetNumDisplays());
1401 EXPECT_EQ(2U, display_manager
->num_connected_displays());
1403 UpdateDisplay("1+0-500x500,1+0-500x500");
1404 EXPECT_TRUE(display_manager
->GetCurrentDisplayLayout().mirrored
);
1405 EXPECT_EQ(1, Shell::GetScreen()->GetNumDisplays());
1406 EXPECT_EQ(2U, display_manager
->num_connected_displays());
1408 UpdateDisplay("500x500,500x500");
1409 EXPECT_FALSE(display_manager
->GetCurrentDisplayLayout().mirrored
);
1410 EXPECT_EQ(2, Shell::GetScreen()->GetNumDisplays());
1411 EXPECT_EQ(2U, display_manager
->num_connected_displays());
1414 TEST_F(DisplayManagerTest
, InvertLayout
) {
1415 EXPECT_EQ("left, 0",
1416 DisplayLayout(DisplayLayout::RIGHT
, 0).Invert().ToString());
1417 EXPECT_EQ("left, -100",
1418 DisplayLayout(DisplayLayout::RIGHT
, 100).Invert().ToString());
1419 EXPECT_EQ("left, 50",
1420 DisplayLayout(DisplayLayout::RIGHT
, -50).Invert().ToString());
1422 EXPECT_EQ("right, 0",
1423 DisplayLayout(DisplayLayout::LEFT
, 0).Invert().ToString());
1424 EXPECT_EQ("right, -90",
1425 DisplayLayout(DisplayLayout::LEFT
, 90).Invert().ToString());
1426 EXPECT_EQ("right, 60",
1427 DisplayLayout(DisplayLayout::LEFT
, -60).Invert().ToString());
1429 EXPECT_EQ("bottom, 0",
1430 DisplayLayout(DisplayLayout::TOP
, 0).Invert().ToString());
1431 EXPECT_EQ("bottom, -80",
1432 DisplayLayout(DisplayLayout::TOP
, 80).Invert().ToString());
1433 EXPECT_EQ("bottom, 70",
1434 DisplayLayout(DisplayLayout::TOP
, -70).Invert().ToString());
1437 DisplayLayout(DisplayLayout::BOTTOM
, 0).Invert().ToString());
1438 EXPECT_EQ("top, -70",
1439 DisplayLayout(DisplayLayout::BOTTOM
, 70).Invert().ToString());
1440 EXPECT_EQ("top, 80",
1441 DisplayLayout(DisplayLayout::BOTTOM
, -80).Invert().ToString());
1444 TEST_F(DisplayManagerTest
, NotifyPrimaryChange
) {
1445 if (!SupportsMultipleDisplays())
1447 UpdateDisplay("500x500,500x500");
1448 ash::Shell::GetInstance()->display_controller()->SwapPrimaryDisplay();
1450 UpdateDisplay("500x500");
1451 EXPECT_FALSE(changed_metrics() & gfx::DisplayObserver::DISPLAY_METRIC_BOUNDS
);
1452 EXPECT_FALSE(changed_metrics() &
1453 gfx::DisplayObserver::DISPLAY_METRIC_WORK_AREA
);
1454 EXPECT_TRUE(changed_metrics() &
1455 gfx::DisplayObserver::DISPLAY_METRIC_PRIMARY
);
1457 UpdateDisplay("500x500,500x500");
1458 ash::Shell::GetInstance()->display_controller()->SwapPrimaryDisplay();
1460 UpdateDisplay("500x400");
1461 EXPECT_TRUE(changed_metrics() & gfx::DisplayObserver::DISPLAY_METRIC_BOUNDS
);
1462 EXPECT_TRUE(changed_metrics() &
1463 gfx::DisplayObserver::DISPLAY_METRIC_WORK_AREA
);
1464 EXPECT_TRUE(changed_metrics() &
1465 gfx::DisplayObserver::DISPLAY_METRIC_PRIMARY
);
1468 TEST_F(DisplayManagerTest
, NotifyPrimaryChangeUndock
) {
1469 if (!SupportsMultipleDisplays())
1471 // Assume the default display is an external display, and
1472 // emulates undocking by switching to another display.
1473 DisplayInfo another_display_info
=
1474 CreateDisplayInfo(1, gfx::Rect(0, 0, 1280, 800));
1475 std::vector
<DisplayInfo
> info_list
;
1476 info_list
.push_back(another_display_info
);
1478 display_manager()->OnNativeDisplaysChanged(info_list
);
1479 EXPECT_TRUE(changed_metrics() & gfx::DisplayObserver::DISPLAY_METRIC_BOUNDS
);
1480 EXPECT_TRUE(changed_metrics() &
1481 gfx::DisplayObserver::DISPLAY_METRIC_WORK_AREA
);
1482 EXPECT_TRUE(changed_metrics() &
1483 gfx::DisplayObserver::DISPLAY_METRIC_PRIMARY
);
1487 // TODO(scottmg): RootWindow doesn't get resized on Windows
1488 // Ash. http://crbug.com/247916.
1489 #define MAYBE_UpdateDisplayWithHostOrigin DISABLED_UpdateDisplayWithHostOrigin
1491 #define MAYBE_UpdateDisplayWithHostOrigin UpdateDisplayWithHostOrigin
1494 TEST_F(DisplayManagerTest
, MAYBE_UpdateDisplayWithHostOrigin
) {
1495 UpdateDisplay("100x200,300x400");
1496 ASSERT_EQ(2, Shell::GetScreen()->GetNumDisplays());
1497 aura::Window::Windows root_windows
=
1498 Shell::GetInstance()->GetAllRootWindows();
1499 ASSERT_EQ(2U, root_windows
.size());
1500 aura::WindowTreeHost
* host0
= root_windows
[0]->GetHost();
1501 aura::WindowTreeHost
* host1
= root_windows
[1]->GetHost();
1503 EXPECT_EQ("1,1", host0
->GetBounds().origin().ToString());
1504 EXPECT_EQ("100x200", host0
->GetBounds().size().ToString());
1505 // UpdateDisplay set the origin if it's not set.
1506 EXPECT_NE("1,1", host1
->GetBounds().origin().ToString());
1507 EXPECT_EQ("300x400", host1
->GetBounds().size().ToString());
1509 UpdateDisplay("100x200,200+300-300x400");
1510 ASSERT_EQ(2, Shell::GetScreen()->GetNumDisplays());
1511 EXPECT_EQ("0,0", host0
->GetBounds().origin().ToString());
1512 EXPECT_EQ("100x200", host0
->GetBounds().size().ToString());
1513 EXPECT_EQ("200,300", host1
->GetBounds().origin().ToString());
1514 EXPECT_EQ("300x400", host1
->GetBounds().size().ToString());
1516 UpdateDisplay("400+500-200x300,300x400");
1517 ASSERT_EQ(2, Shell::GetScreen()->GetNumDisplays());
1518 EXPECT_EQ("400,500", host0
->GetBounds().origin().ToString());
1519 EXPECT_EQ("200x300", host0
->GetBounds().size().ToString());
1520 EXPECT_EQ("0,0", host1
->GetBounds().origin().ToString());
1521 EXPECT_EQ("300x400", host1
->GetBounds().size().ToString());
1523 UpdateDisplay("100+200-100x200,300+500-200x300");
1524 ASSERT_EQ(2, Shell::GetScreen()->GetNumDisplays());
1525 EXPECT_EQ("100,200", host0
->GetBounds().origin().ToString());
1526 EXPECT_EQ("100x200", host0
->GetBounds().size().ToString());
1527 EXPECT_EQ("300,500", host1
->GetBounds().origin().ToString());
1528 EXPECT_EQ("200x300", host1
->GetBounds().size().ToString());
1531 TEST_F(DisplayManagerTest
, UnifiedDesktopBasic
) {
1532 if (!SupportsMultipleDisplays())
1534 test::DisplayManagerTestApi::EnableUnifiedDesktopForTest();
1536 // Don't check root window destruction in unified mode.
1537 Shell::GetPrimaryRootWindow()->RemoveObserver(this);
1539 UpdateDisplay("300x200,400x500");
1541 // Defaults to the unified desktop.
1542 gfx::Screen
* screen
=
1543 gfx::Screen::GetScreenByType(gfx::SCREEN_TYPE_ALTERNATE
);
1544 // The 1st display is scaled so that it has the same height as 2nd display.
1545 // 300 * 500 / 200 + 400 = 1150.
1546 EXPECT_EQ("1150x500", screen
->GetPrimaryDisplay().size().ToString());
1548 display_manager()->SetMirrorMode(true);
1549 EXPECT_EQ("300x200", screen
->GetPrimaryDisplay().size().ToString());
1551 display_manager()->SetMirrorMode(false);
1552 EXPECT_EQ("1150x500", screen
->GetPrimaryDisplay().size().ToString());
1554 // Switch to single desktop.
1555 UpdateDisplay("500x300");
1556 EXPECT_EQ("500x300", screen
->GetPrimaryDisplay().size().ToString());
1558 // Switch to unified desktop.
1559 UpdateDisplay("500x300,400x500");
1560 // 500 * 500 / 300 + 400 ~= 1233.
1561 EXPECT_EQ("1233x500", screen
->GetPrimaryDisplay().size().ToString());
1563 // Switch back to extended desktop.
1564 display_manager()->SetDefaultMultiDisplayMode(DisplayManager::EXTENDED
);
1565 display_manager()->ReconfigureDisplays();
1566 EXPECT_EQ("500x300", screen
->GetPrimaryDisplay().size().ToString());
1567 EXPECT_EQ("400x500", ScreenUtil::GetSecondaryDisplay().size().ToString());
1570 // Updating displays again in unified desktop mode should not crash.
1571 // crbug.com/491094.
1572 TEST_F(DisplayManagerTest
, ConfigureUnifiedTwice
) {
1573 if (!SupportsMultipleDisplays())
1575 // Don't check root window destruction in unified mode.
1576 Shell::GetPrimaryRootWindow()->RemoveObserver(this);
1578 UpdateDisplay("300x200,400x500");
1579 // Mirror windows are created in a posted task.
1580 RunAllPendingInMessageLoop();
1582 UpdateDisplay("300x250,400x550");
1583 RunAllPendingInMessageLoop();
1586 TEST_F(DisplayManagerTest
, NoRotateUnifiedDesktop
) {
1587 if (!SupportsMultipleDisplays())
1589 test::DisplayManagerTestApi::EnableUnifiedDesktopForTest();
1591 // Don't check root window destruction in unified mode.
1592 Shell::GetPrimaryRootWindow()->RemoveObserver(this);
1594 UpdateDisplay("300x200,400x500");
1596 gfx::Screen
* screen
=
1597 gfx::Screen::GetScreenByType(gfx::SCREEN_TYPE_ALTERNATE
);
1598 const gfx::Display
& display
= screen
->GetPrimaryDisplay();
1599 EXPECT_EQ("1150x500", display
.size().ToString());
1600 display_manager()->SetDisplayRotation(display
.id(), gfx::Display::ROTATE_90
,
1601 gfx::Display::ROTATION_SOURCE_ACTIVE
);
1602 EXPECT_EQ("1150x500", screen
->GetPrimaryDisplay().size().ToString());
1603 display_manager()->SetDisplayRotation(display
.id(), gfx::Display::ROTATE_0
,
1604 gfx::Display::ROTATION_SOURCE_ACTIVE
);
1605 EXPECT_EQ("1150x500", screen
->GetPrimaryDisplay().size().ToString());
1607 UpdateDisplay("300x200");
1608 EXPECT_EQ("300x200", screen
->GetPrimaryDisplay().size().ToString());
1611 // Makes sure the transition from unified to single won't crash
1612 // with docked windows.
1613 TEST_F(DisplayManagerTest
, UnifiedWithDockWindows
) {
1614 if (!SupportsMultipleDisplays())
1616 test::DisplayManagerTestApi::EnableUnifiedDesktopForTest();
1618 // Don't check root window destruction in unified mode.
1619 Shell::GetPrimaryRootWindow()->RemoveObserver(this);
1621 UpdateDisplay("300x200,400x500");
1623 scoped_ptr
<aura::Window
> docked(
1624 CreateTestWindowInShellWithBounds(gfx::Rect(10, 10, 50, 50)));
1625 docked
->SetProperty(aura::client::kShowStateKey
, ui::SHOW_STATE_DOCKED
);
1626 ASSERT_TRUE(wm::GetWindowState(docked
.get())->IsDocked());
1627 // 47 pixels reserved for launcher shelf height.
1628 EXPECT_EQ("0,0 250x453", docked
->bounds().ToString());
1629 UpdateDisplay("300x300");
1630 // Make sure the window is still docked.
1631 EXPECT_TRUE(wm::GetWindowState(docked
.get())->IsDocked());
1632 EXPECT_EQ("0,0 250x253", docked
->bounds().ToString());
1635 class ScreenShutdownTest
: public test::AshTestBase
{
1637 ScreenShutdownTest() {
1639 ~ScreenShutdownTest() override
{}
1641 void TearDown() override
{
1642 gfx::Screen
* orig_screen
=
1643 gfx::Screen::GetScreenByType(gfx::SCREEN_TYPE_ALTERNATE
);
1644 AshTestBase::TearDown();
1645 if (!SupportsMultipleDisplays())
1647 gfx::Screen
* screen
=
1648 gfx::Screen::GetScreenByType(gfx::SCREEN_TYPE_ALTERNATE
);
1649 EXPECT_NE(orig_screen
, screen
);
1650 EXPECT_EQ(2, screen
->GetNumDisplays());
1651 EXPECT_EQ("500x300", screen
->GetPrimaryDisplay().size().ToString());
1652 std::vector
<gfx::Display
> all
= screen
->GetAllDisplays();
1653 EXPECT_EQ("500x300", all
[0].size().ToString());
1654 EXPECT_EQ("800x400", all
[1].size().ToString());
1658 DISALLOW_COPY_AND_ASSIGN(ScreenShutdownTest
);
1661 TEST_F(ScreenShutdownTest
, ScreenAfterShutdown
) {
1662 if (!SupportsMultipleDisplays())
1664 UpdateDisplay("500x300,800x400");
1668 #if defined(OS_CHROMEOS)
1671 // A helper class that sets the display configuration and starts ash.
1672 // This is to make sure the font configuration happens during ash
1673 // initialization process.
1674 class FontTestHelper
: public test::AshTestBase
{
1681 FontTestHelper(float scale
, DisplayType display_type
) {
1682 gfx::ClearFontRenderParamsCacheForTest();
1683 base::CommandLine
* command_line
= base::CommandLine::ForCurrentProcess();
1684 if (display_type
== INTERNAL
)
1685 command_line
->AppendSwitch(switches::kAshUseFirstDisplayAsInternal
);
1686 command_line
->AppendSwitchASCII(switches::kAshHostWindowBounds
,
1687 StringPrintf("1000x800*%f", scale
));
1691 ~FontTestHelper() override
{ TearDown(); }
1693 // test::AshTestBase:
1694 void TestBody() override
{ NOTREACHED(); }
1697 DISALLOW_COPY_AND_ASSIGN(FontTestHelper
);
1701 bool IsTextSubpixelPositioningEnabled() {
1702 gfx::FontRenderParams params
=
1703 gfx::GetFontRenderParams(gfx::FontRenderParamsQuery(), NULL
);
1704 return params
.subpixel_positioning
;
1707 gfx::FontRenderParams::Hinting
GetFontHintingParams() {
1708 gfx::FontRenderParams params
=
1709 gfx::GetFontRenderParams(gfx::FontRenderParamsQuery(), NULL
);
1710 return params
.hinting
;
1715 typedef testing::Test DisplayManagerFontTest
;
1717 TEST_F(DisplayManagerFontTest
, TextSubpixelPositioningWithDsf100Internal
) {
1718 FontTestHelper
helper(1.0f
, FontTestHelper::INTERNAL
);
1720 1.0f
, Shell::GetScreen()->GetPrimaryDisplay().device_scale_factor());
1721 EXPECT_FALSE(IsTextSubpixelPositioningEnabled());
1722 EXPECT_NE(gfx::FontRenderParams::HINTING_NONE
, GetFontHintingParams());
1725 TEST_F(DisplayManagerFontTest
, TextSubpixelPositioningWithDsf125Internal
) {
1726 test::ScopedDisable125DSFForUIScaling disable
;
1727 FontTestHelper
helper(1.25f
, FontTestHelper::INTERNAL
);
1729 1.25f
, Shell::GetScreen()->GetPrimaryDisplay().device_scale_factor());
1730 EXPECT_TRUE(IsTextSubpixelPositioningEnabled());
1731 EXPECT_EQ(gfx::FontRenderParams::HINTING_NONE
, GetFontHintingParams());
1734 TEST_F(DisplayManagerFontTest
, TextSubpixelPositioningWithDsf200Internal
) {
1735 FontTestHelper
helper(2.0f
, FontTestHelper::INTERNAL
);
1737 2.0f
, Shell::GetScreen()->GetPrimaryDisplay().device_scale_factor());
1738 EXPECT_TRUE(IsTextSubpixelPositioningEnabled());
1739 EXPECT_EQ(gfx::FontRenderParams::HINTING_NONE
, GetFontHintingParams());
1741 Shell::GetInstance()->display_manager()->SetDisplayUIScale(
1742 Shell::GetScreen()->GetPrimaryDisplay().id(), 2.0f
);
1745 1.0f
, Shell::GetScreen()->GetPrimaryDisplay().device_scale_factor());
1746 EXPECT_FALSE(IsTextSubpixelPositioningEnabled());
1747 EXPECT_NE(gfx::FontRenderParams::HINTING_NONE
, GetFontHintingParams());
1750 TEST_F(DisplayManagerFontTest
, TextSubpixelPositioningWithDsf100External
) {
1751 FontTestHelper
helper(1.0f
, FontTestHelper::EXTERNAL
);
1753 1.0f
, Shell::GetScreen()->GetPrimaryDisplay().device_scale_factor());
1754 EXPECT_FALSE(IsTextSubpixelPositioningEnabled());
1755 EXPECT_NE(gfx::FontRenderParams::HINTING_NONE
, GetFontHintingParams());
1758 TEST_F(DisplayManagerFontTest
, TextSubpixelPositioningWithDsf125External
) {
1759 FontTestHelper
helper(1.25f
, FontTestHelper::EXTERNAL
);
1761 1.25f
, Shell::GetScreen()->GetPrimaryDisplay().device_scale_factor());
1762 EXPECT_TRUE(IsTextSubpixelPositioningEnabled());
1763 EXPECT_EQ(gfx::FontRenderParams::HINTING_NONE
, GetFontHintingParams());
1766 TEST_F(DisplayManagerFontTest
, TextSubpixelPositioningWithDsf200External
) {
1767 FontTestHelper
helper(2.0f
, FontTestHelper::EXTERNAL
);
1769 2.0f
, Shell::GetScreen()->GetPrimaryDisplay().device_scale_factor());
1770 EXPECT_TRUE(IsTextSubpixelPositioningEnabled());
1771 EXPECT_EQ(gfx::FontRenderParams::HINTING_NONE
, GetFontHintingParams());
1774 TEST_F(DisplayManagerFontTest
,
1775 TextSubpixelPositioningWithDsf125InternalWithScaling
) {
1776 FontTestHelper
helper(1.25f
, FontTestHelper::INTERNAL
);
1778 1.0f
, Shell::GetScreen()->GetPrimaryDisplay().device_scale_factor());
1779 EXPECT_FALSE(IsTextSubpixelPositioningEnabled());
1780 EXPECT_NE(gfx::FontRenderParams::HINTING_NONE
, GetFontHintingParams());
1782 Shell::GetInstance()->display_manager()->SetDisplayUIScale(
1783 Shell::GetScreen()->GetPrimaryDisplay().id(), 0.8f
);
1786 1.25f
, Shell::GetScreen()->GetPrimaryDisplay().device_scale_factor());
1787 EXPECT_TRUE(IsTextSubpixelPositioningEnabled());
1788 EXPECT_EQ(gfx::FontRenderParams::HINTING_NONE
, GetFontHintingParams());
1791 TEST_F(DisplayManagerTest
, CheckInitializationOfRotationProperty
) {
1792 int64_t id
= display_manager()->GetDisplayAt(0).id();
1793 display_manager()->RegisterDisplayProperty(id
, gfx::Display::ROTATE_90
, 1.0f
,
1794 nullptr, gfx::Size(), 1.0f
,
1795 ui::COLOR_PROFILE_STANDARD
);
1797 const DisplayInfo
& info
= display_manager()->GetDisplayInfo(id
);
1799 EXPECT_EQ(gfx::Display::ROTATE_90
,
1800 info
.GetRotation(gfx::Display::ROTATION_SOURCE_USER
));
1801 EXPECT_EQ(gfx::Display::ROTATE_90
,
1802 info
.GetRotation(gfx::Display::ROTATION_SOURCE_ACTIVE
));
1805 #endif // OS_CHROMEOS