Home | History | Annotate | Download | only in ui
      1 // Copyright (c) 2006-2008 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.
      4 
      5 #include <vector>
      6 
      7 #include "chrome/browser/ui/window_sizer.h"
      8 #include "base/logging.h"
      9 #include "testing/gtest/include/gtest/gtest.h"
     10 
     11 // Some standard monitor sizes (no task bar).
     12 static const gfx::Rect tentwentyfour(0, 0, 1024, 768);
     13 static const gfx::Rect twelveeighty(0, 0, 1280, 1024);
     14 static const gfx::Rect sixteenhundred(0, 0, 1600, 1200);
     15 static const gfx::Rect sixteeneighty(0, 0, 1680, 1050);
     16 static const gfx::Rect nineteentwenty(0, 0, 1920, 1200);
     17 
     18 // Represents a 1024x768 monitor that is not the primary monitor, arranged to
     19 // the immediate left of the primary 1024x768 monitor.
     20 static const gfx::Rect left_nonprimary(-1024, 0, 1024, 768);
     21 
     22 // Represents a 1024x768 monitor that is not the primary monitor, arranged to
     23 // the immediate right of the primary 1024x768 monitor.
     24 static const gfx::Rect right_nonprimary(1024, 0, 1024, 768);
     25 
     26 // Represents a 1024x768 monitor that is not the primary monitor, arranged to
     27 // the immediate top of the primary 1024x768 monitor.
     28 static const gfx::Rect top_nonprimary(0, -768, 1024, 768);
     29 
     30 // Represents a 1024x768 monitor that is not the primary monitor, arranged to
     31 // the immediate bottom of the primary 1024x768 monitor.
     32 static const gfx::Rect bottom_nonprimary(0, 768, 1024, 768);
     33 
     34 // The work area for 1024x768 monitors with different taskbar orientations.
     35 static const gfx::Rect taskbar_bottom_work_area(0, 0, 1024, 734);
     36 static const gfx::Rect taskbar_top_work_area(0, 34, 1024, 734);
     37 static const gfx::Rect taskbar_left_work_area(107, 0, 917, 768);
     38 static const gfx::Rect taskbar_right_work_area(0, 0, 917, 768);
     39 
     40 static int kWindowTilePixels = WindowSizer::kWindowTilePixels;
     41 
     42 // Testing implementation of WindowSizer::MonitorInfoProvider that we can use
     43 // to fake various monitor layouts and sizes.
     44 class TestMonitorInfoProvider : public WindowSizer::MonitorInfoProvider {
     45  public:
     46   TestMonitorInfoProvider() {}
     47   virtual ~TestMonitorInfoProvider() {}
     48 
     49   void AddMonitor(const gfx::Rect& bounds, const gfx::Rect& work_area) {
     50     DCHECK(bounds.Contains(work_area));
     51     monitor_bounds_.push_back(bounds);
     52     work_areas_.push_back(work_area);
     53   }
     54 
     55   // Overridden from WindowSizer::MonitorInfoProvider:
     56   virtual gfx::Rect GetPrimaryMonitorWorkArea() const {
     57     return work_areas_[0];
     58   }
     59 
     60   virtual gfx::Rect GetPrimaryMonitorBounds() const {
     61     return monitor_bounds_[0];
     62   }
     63 
     64   virtual gfx::Rect GetMonitorWorkAreaMatching(
     65       const gfx::Rect& match_rect) const {
     66     return work_areas_[GetMonitorIndexMatchingBounds(match_rect)];
     67   }
     68 
     69   virtual gfx::Point GetBoundsOffsetMatching(
     70       const gfx::Rect& match_rect) const {
     71     int monitor_index = GetMonitorIndexMatchingBounds(match_rect);
     72     gfx::Rect bounds = monitor_bounds_[monitor_index];
     73     const gfx::Rect& work_area = work_areas_[monitor_index];
     74     return gfx::Point(work_area.x() - bounds.x(), work_area.y() - bounds.y());
     75   }
     76 
     77   virtual void UpdateWorkAreas() { }
     78 
     79  private:
     80   size_t GetMonitorIndexMatchingBounds(const gfx::Rect& match_rect) const {
     81     int max_area = 0;
     82     size_t max_area_index = 0;
     83     // Loop through all the monitors, finding the one that intersects the
     84     // largest area of the supplied match rect.
     85     for (size_t i = 0; i < work_areas_.size(); ++i) {
     86       gfx::Rect overlap(match_rect.Intersect(work_areas_[i]));
     87       int area = overlap.width() * overlap.height();
     88       if (area > max_area) {
     89         max_area = area;
     90         max_area_index = i;
     91       }
     92     }
     93     return max_area_index;
     94   }
     95 
     96   std::vector<gfx::Rect> monitor_bounds_;
     97 
     98   DISALLOW_COPY_AND_ASSIGN(TestMonitorInfoProvider);
     99 };
    100 
    101 // Testing implementation of WindowSizer::StateProvider that we use to fake
    102 // persistent storage and existing windows.
    103 class TestStateProvider : public WindowSizer::StateProvider {
    104  public:
    105   TestStateProvider()
    106     : persistent_maximized_(false),
    107       has_persistent_data_(false),
    108       has_last_active_data_(false) {
    109   }
    110   virtual ~TestStateProvider() {}
    111 
    112   void SetPersistentState(const gfx::Rect& bounds,
    113                           bool maximized,
    114                           const gfx::Rect& work_area,
    115                           bool has_persistent_data) {
    116     persistent_bounds_ = bounds;
    117     persistent_maximized_ = maximized;
    118     persistent_work_area_ = work_area;
    119     has_persistent_data_ = has_persistent_data;
    120   }
    121 
    122   void SetLastActiveState(const gfx::Rect& bounds, bool has_last_active_data) {
    123     last_active_bounds_ = bounds;
    124     has_last_active_data_ = has_last_active_data;
    125   }
    126 
    127   // Overridden from WindowSizer::StateProvider:
    128   virtual bool GetPersistentState(gfx::Rect* bounds,
    129                                   bool* maximized,
    130                                   gfx::Rect* saved_work_area) const {
    131     *bounds = persistent_bounds_;
    132     *maximized = persistent_maximized_;
    133     *saved_work_area = persistent_work_area_;
    134     return has_persistent_data_;
    135   }
    136 
    137   virtual bool GetLastActiveWindowState(gfx::Rect* bounds) const {
    138     *bounds = last_active_bounds_;
    139     return has_last_active_data_;
    140   }
    141 
    142  private:
    143   gfx::Rect persistent_bounds_;
    144   bool persistent_maximized_;
    145   gfx::Rect persistent_work_area_;
    146   bool has_persistent_data_;
    147 
    148   gfx::Rect last_active_bounds_;
    149   bool has_last_active_data_;
    150 
    151   DISALLOW_COPY_AND_ASSIGN(TestStateProvider);
    152 };
    153 
    154 // A convenience function to read the window bounds from the window sizer
    155 // according to the specified configuration.
    156 enum Source { DEFAULT, LAST_ACTIVE, PERSISTED };
    157 static void GetWindowBounds(const gfx::Rect& monitor1_bounds,
    158                             const gfx::Rect& monitor1_work_area,
    159                             const gfx::Rect& monitor2_bounds,
    160                             const gfx::Rect& state,
    161                             bool maximized,
    162                             const gfx::Rect& work_area,
    163                             Source source,
    164                             gfx::Rect* out_bounds,
    165                             bool* out_maximized) {
    166   TestMonitorInfoProvider* mip = new TestMonitorInfoProvider;
    167   mip->AddMonitor(monitor1_bounds, monitor1_work_area);
    168   if (!monitor2_bounds.IsEmpty())
    169     mip->AddMonitor(monitor2_bounds, monitor2_bounds);
    170   TestStateProvider* sp = new TestStateProvider;
    171   if (source == PERSISTED)
    172     sp->SetPersistentState(state, maximized, work_area, true);
    173   else if (source == LAST_ACTIVE)
    174     sp->SetLastActiveState(state, true);
    175   WindowSizer sizer(sp, mip);
    176   sizer.DetermineWindowBounds(gfx::Rect(), out_bounds, out_maximized);
    177 }
    178 
    179 // Test that the window is sized appropriately for the first run experience
    180 // where the default window bounds calculation is invoked.
    181 TEST(WindowSizerTest, DefaultSizeCase) {
    182   { // 4:3 monitor case, 1024x768, no taskbar
    183     gfx::Rect window_bounds;
    184     bool maximized;
    185     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(), gfx::Rect(),
    186                     false, gfx::Rect(), DEFAULT, &window_bounds, &maximized);
    187     EXPECT_FALSE(maximized);
    188     EXPECT_EQ(gfx::Rect(kWindowTilePixels, kWindowTilePixels,
    189                         1024 - kWindowTilePixels * 2,
    190                         768 - kWindowTilePixels * 2),
    191               window_bounds);
    192   }
    193 
    194   { // 4:3 monitor case, 1024x768, taskbar on bottom
    195     gfx::Rect window_bounds;
    196     bool maximized;
    197     GetWindowBounds(tentwentyfour, taskbar_bottom_work_area, gfx::Rect(),
    198                     gfx::Rect(), false, gfx::Rect(), DEFAULT, &window_bounds,
    199                     &maximized);
    200     EXPECT_FALSE(maximized);
    201     EXPECT_EQ(gfx::Rect(kWindowTilePixels, kWindowTilePixels,
    202                         1024 - kWindowTilePixels * 2,
    203                         (taskbar_bottom_work_area.height() -
    204                          kWindowTilePixels * 2)),
    205               window_bounds);
    206   }
    207 
    208   { // 4:3 monitor case, 1024x768, taskbar on right
    209     gfx::Rect window_bounds;
    210     bool maximized;
    211     GetWindowBounds(tentwentyfour, taskbar_right_work_area, gfx::Rect(),
    212                     gfx::Rect(), false, gfx::Rect(), DEFAULT, &window_bounds,
    213                     &maximized);
    214     EXPECT_FALSE(maximized);
    215     EXPECT_EQ(gfx::Rect(kWindowTilePixels, kWindowTilePixels,
    216                         taskbar_right_work_area.width() - kWindowTilePixels*2,
    217                         768 - kWindowTilePixels * 2),
    218               window_bounds);
    219   }
    220 
    221   { // 4:3 monitor case, 1024x768, taskbar on left
    222     gfx::Rect window_bounds;
    223     bool maximized;
    224     GetWindowBounds(tentwentyfour, taskbar_left_work_area, gfx::Rect(),
    225                     gfx::Rect(), false, gfx::Rect(), DEFAULT, &window_bounds,
    226                     &maximized);
    227     EXPECT_FALSE(maximized);
    228     EXPECT_EQ(gfx::Rect(taskbar_left_work_area.x() + kWindowTilePixels,
    229                         kWindowTilePixels,
    230                         taskbar_left_work_area.width() - kWindowTilePixels * 2,
    231                         (taskbar_left_work_area.height() -
    232                          kWindowTilePixels * 2)),
    233               window_bounds);
    234   }
    235 
    236   { // 4:3 monitor case, 1024x768, taskbar on top
    237     gfx::Rect window_bounds;
    238     bool maximized;
    239     GetWindowBounds(tentwentyfour, taskbar_top_work_area, gfx::Rect(),
    240                     gfx::Rect(), false, gfx::Rect(), DEFAULT, &window_bounds,
    241                     &maximized);
    242     EXPECT_FALSE(maximized);
    243     EXPECT_EQ(gfx::Rect(kWindowTilePixels,
    244                         taskbar_top_work_area.y() + kWindowTilePixels,
    245                         1024 - kWindowTilePixels * 2,
    246                         taskbar_top_work_area.height() - kWindowTilePixels * 2),
    247               window_bounds);
    248   }
    249 
    250   { // 4:3 monitor case, 1280x1024
    251     gfx::Rect window_bounds;
    252     bool maximized;
    253     GetWindowBounds(twelveeighty, twelveeighty, gfx::Rect(), gfx::Rect(),
    254                     false, gfx::Rect(), DEFAULT, &window_bounds, &maximized);
    255     EXPECT_FALSE(maximized);
    256     EXPECT_EQ(gfx::Rect(kWindowTilePixels, kWindowTilePixels,
    257                         1050,
    258                         1024 - kWindowTilePixels * 2),
    259               window_bounds);
    260   }
    261 
    262   { // 4:3 monitor case, 1600x1200
    263     gfx::Rect window_bounds;
    264     bool maximized;
    265     GetWindowBounds(sixteenhundred, sixteenhundred, gfx::Rect(), gfx::Rect(),
    266                     false, gfx::Rect(), DEFAULT, &window_bounds, &maximized);
    267     EXPECT_FALSE(maximized);
    268     EXPECT_EQ(gfx::Rect(kWindowTilePixels, kWindowTilePixels,
    269                         1050,
    270                         1200 - kWindowTilePixels * 2),
    271               window_bounds);
    272   }
    273 
    274   { // 16:10 monitor case, 1680x1050
    275     gfx::Rect window_bounds;
    276     bool maximized;
    277     GetWindowBounds(sixteeneighty, sixteeneighty, gfx::Rect(), gfx::Rect(),
    278                     false, gfx::Rect(), DEFAULT, &window_bounds, &maximized);
    279     EXPECT_FALSE(maximized);
    280     EXPECT_EQ(gfx::Rect(kWindowTilePixels, kWindowTilePixels,
    281                         840 - static_cast<int>(kWindowTilePixels * 1.5),
    282                         1050 - kWindowTilePixels * 2),
    283               window_bounds);
    284   }
    285 
    286   { // 16:10 monitor case, 1920x1200
    287     gfx::Rect window_bounds;
    288     bool maximized;
    289     GetWindowBounds(nineteentwenty, nineteentwenty, gfx::Rect(), gfx::Rect(),
    290                     false, gfx::Rect(), DEFAULT, &window_bounds, &maximized);
    291     EXPECT_FALSE(maximized);
    292     EXPECT_EQ(gfx::Rect(kWindowTilePixels, kWindowTilePixels,
    293                         960 - static_cast<int>(kWindowTilePixels * 1.5),
    294                         1200 - kWindowTilePixels * 2),
    295               window_bounds);
    296   }
    297 }
    298 
    299 // Test that the next opened window is positioned appropriately given the
    300 // bounds of an existing window of the same type.
    301 TEST(WindowSizerTest, LastWindowBoundsCase) {
    302   { // normal, in the middle of the screen somewhere.
    303     gfx::Rect window_bounds;
    304     bool maximized = false;
    305     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    306                     gfx::Rect(kWindowTilePixels, kWindowTilePixels, 500, 400),
    307                     false, gfx::Rect(), LAST_ACTIVE,
    308                     &window_bounds, &maximized);
    309     EXPECT_FALSE(maximized);
    310     EXPECT_EQ(gfx::Rect(kWindowTilePixels * 2,
    311                         kWindowTilePixels * 2, 500, 400), window_bounds);
    312   }
    313 
    314   { // taskbar on top.
    315     gfx::Rect window_bounds;
    316     bool maximized = false;
    317     GetWindowBounds(tentwentyfour, taskbar_top_work_area, gfx::Rect(),
    318                     gfx::Rect(kWindowTilePixels, kWindowTilePixels, 500, 400),
    319                     false, gfx::Rect(), LAST_ACTIVE,
    320                     &window_bounds, &maximized);
    321     EXPECT_FALSE(maximized);
    322     EXPECT_EQ(gfx::Rect(kWindowTilePixels * 2,
    323                         std::max(kWindowTilePixels * 2,
    324                                  34 /* toolbar height */),
    325                         500, 400), window_bounds);
    326   }
    327 
    328   { // too small to satisify the minimum visibility condition.
    329     gfx::Rect window_bounds;
    330     bool maximized = false;
    331     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    332                     gfx::Rect(kWindowTilePixels, kWindowTilePixels, 29, 29),
    333                     false, gfx::Rect(), LAST_ACTIVE,
    334                     &window_bounds, &maximized);
    335     EXPECT_FALSE(maximized);
    336     EXPECT_EQ(gfx::Rect(kWindowTilePixels * 2,
    337                         kWindowTilePixels * 2,
    338                         30 /* not 29 */,
    339                         30 /* not 29 */),
    340               window_bounds);
    341   }
    342 
    343 
    344   { // normal, but maximized
    345     gfx::Rect window_bounds;
    346     bool maximized = false;
    347     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    348                     gfx::Rect(kWindowTilePixels, kWindowTilePixels, 500, 400),
    349                     true, gfx::Rect(), LAST_ACTIVE,
    350                     &window_bounds, &maximized);
    351     EXPECT_FALSE(maximized);
    352     EXPECT_EQ(gfx::Rect(kWindowTilePixels * 2,
    353                         kWindowTilePixels * 2, 500, 400), window_bounds);
    354   }
    355 }
    356 
    357 // Test that the window opened is sized appropriately given persisted sizes.
    358 TEST(WindowSizerTest, PersistedBoundsCase) {
    359   { // normal, in the middle of the screen somewhere.
    360     gfx::Rect initial_bounds(kWindowTilePixels, kWindowTilePixels, 500, 400);
    361 
    362     gfx::Rect window_bounds;
    363     bool maximized;
    364     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(), initial_bounds,
    365                     false, gfx::Rect(), PERSISTED, &window_bounds, &maximized);
    366     EXPECT_FALSE(maximized);
    367     EXPECT_EQ(initial_bounds, window_bounds);
    368   }
    369 
    370   { // normal, maximized.
    371     gfx::Rect initial_bounds(0, 0, 1024, 768);
    372 
    373     gfx::Rect window_bounds;
    374     bool maximized;
    375     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(), initial_bounds,
    376                     true, gfx::Rect(), PERSISTED, &window_bounds, &maximized);
    377     EXPECT_TRUE(maximized);
    378     EXPECT_EQ(initial_bounds, window_bounds);
    379   }
    380 
    381   { // normal, on non-primary monitor in negative coords.
    382     gfx::Rect initial_bounds(-600, 10, 500, 400);
    383 
    384     gfx::Rect window_bounds;
    385     bool maximized;
    386     GetWindowBounds(tentwentyfour, tentwentyfour, left_nonprimary,
    387                     initial_bounds, false, gfx::Rect(), PERSISTED,
    388                     &window_bounds, &maximized);
    389     EXPECT_FALSE(maximized);
    390     EXPECT_EQ(initial_bounds, window_bounds);
    391   }
    392 
    393   { // normal, on non-primary monitor in negative coords, maximized.
    394     gfx::Rect initial_bounds(-1024, 0, 1024, 768);
    395 
    396     gfx::Rect window_bounds;
    397     bool maximized;
    398     GetWindowBounds(tentwentyfour, tentwentyfour, left_nonprimary,
    399                     initial_bounds, true, gfx::Rect(), PERSISTED,
    400                     &window_bounds, &maximized);
    401     EXPECT_TRUE(maximized);
    402     EXPECT_EQ(initial_bounds, window_bounds);
    403   }
    404 
    405   { // Non-primary monitor resoultion has changed, but the monitor still
    406     // completely contains the window.
    407 
    408     gfx::Rect initial_bounds(1074, 50, 600, 500);
    409 
    410     gfx::Rect window_bounds;
    411     bool maximized;
    412     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(1024, 0, 800, 600),
    413                     initial_bounds, false, right_nonprimary,
    414                     PERSISTED, &window_bounds, &maximized);
    415     EXPECT_FALSE(maximized);
    416     EXPECT_EQ(initial_bounds, window_bounds);
    417   }
    418 
    419   { // Non-primary monitor resoultion has changed, and the window is partially
    420     // off-screen.
    421 
    422     gfx::Rect initial_bounds(1274, 50, 600, 500);
    423 
    424     gfx::Rect window_bounds;
    425     bool maximized;
    426     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(1024, 0, 800, 600),
    427                     initial_bounds, false, right_nonprimary,
    428                     PERSISTED, &window_bounds, &maximized);
    429     EXPECT_FALSE(maximized);
    430     EXPECT_EQ(gfx::Rect(1224, 50, 600, 500), window_bounds);
    431   }
    432 
    433   { // Non-primary monitor resoultion has changed, and the window is now too
    434     // large for the monitor.
    435 
    436     gfx::Rect initial_bounds(1274, 50, 900, 700);
    437 
    438     gfx::Rect window_bounds;
    439     bool maximized;
    440     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(1024, 0, 800, 600),
    441                     initial_bounds, false, right_nonprimary,
    442                     PERSISTED, &window_bounds, &maximized);
    443     EXPECT_FALSE(maximized);
    444     EXPECT_EQ(gfx::Rect(1024, 0, 800, 600), window_bounds);
    445   }
    446 
    447   { // width and height too small
    448     gfx::Rect window_bounds;
    449     bool maximized;
    450     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    451                     gfx::Rect(kWindowTilePixels, kWindowTilePixels, 29, 29),
    452                     false, gfx::Rect(), PERSISTED,
    453                     &window_bounds, &maximized);
    454     EXPECT_FALSE(maximized);
    455     EXPECT_EQ(gfx::Rect(kWindowTilePixels, kWindowTilePixels,
    456                         30 /* not 29 */, 30 /* not 29 */),
    457               window_bounds);
    458   }
    459 
    460 #if defined(OS_MACOSX)
    461   { // Saved state is too tall to possibly be resized.  Mac resizers
    462     // are at the bottom of the window, and no piece of a window can
    463     // be moved higher than the menubar.  (Perhaps the user changed
    464     // resolution to something smaller before relaunching Chrome?)
    465     gfx::Rect window_bounds;
    466     bool maximized;
    467     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    468                     gfx::Rect(kWindowTilePixels, kWindowTilePixels, 30, 5000),
    469                     false, gfx::Rect(), PERSISTED,
    470                     &window_bounds, &maximized);
    471     EXPECT_FALSE(maximized);
    472     EXPECT_EQ(tentwentyfour.height(), window_bounds.height());
    473   }
    474 #endif  // defined(OS_MACOSX)
    475 }
    476 
    477 //////////////////////////////////////////////////////////////////////////////
    478 // The following unittests have different results on Mac/non-Mac because we
    479 // reposition windows aggressively on Mac.  The *WithAggressiveReposition tests
    480 // are run on Mac, and the *WithNonAggressiveRepositioning tests are run on
    481 // other platforms.
    482 
    483 #if defined(OS_MACOSX)
    484 TEST(WindowSizerTest, LastWindowOffscreenWithAggressiveRepositioning) {
    485   { // taskbar on left.  The new window overlaps slightly with the taskbar, so
    486     // it is moved to be flush with the left edge of the work area.
    487     gfx::Rect window_bounds;
    488     bool maximized = false;
    489     GetWindowBounds(tentwentyfour, taskbar_left_work_area, gfx::Rect(),
    490                     gfx::Rect(kWindowTilePixels, kWindowTilePixels, 500, 400),
    491                     false, gfx::Rect(), LAST_ACTIVE,
    492                     &window_bounds, &maximized);
    493     EXPECT_FALSE(maximized);
    494     EXPECT_EQ(gfx::Rect(taskbar_left_work_area.x(),
    495                         kWindowTilePixels * 2, 500, 400), window_bounds);
    496   }
    497 
    498   { // offset would put the new window offscreen at the bottom
    499     gfx::Rect window_bounds;
    500     bool maximized = false;
    501     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    502                     gfx::Rect(10, 729, 500, 400), false, gfx::Rect(),
    503                     LAST_ACTIVE, &window_bounds, &maximized);
    504     EXPECT_FALSE(maximized);
    505     EXPECT_EQ(gfx::Rect(10 + kWindowTilePixels,
    506                         0 /* not 729 + kWindowTilePixels */,
    507                         500, 400),
    508               window_bounds);
    509   }
    510 
    511   { // offset would put the new window offscreen at the right
    512     gfx::Rect window_bounds;
    513     bool maximized = false;
    514     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    515                     gfx::Rect(985, 10, 500, 400), false, gfx::Rect(),
    516                     LAST_ACTIVE, &window_bounds, &maximized);
    517     EXPECT_FALSE(maximized);
    518     EXPECT_EQ(gfx::Rect(0 /* not 985 + kWindowTilePixels*/,
    519                         10 + kWindowTilePixels,
    520                         500, 400),
    521               window_bounds);
    522   }
    523 
    524   { // offset would put the new window offscreen at the bottom right
    525     gfx::Rect window_bounds;
    526     bool maximized = false;
    527     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    528                     gfx::Rect(985, 729, 500, 400), false, gfx::Rect(),
    529                     LAST_ACTIVE, &window_bounds, &maximized);
    530     EXPECT_FALSE(maximized);
    531     EXPECT_EQ(gfx::Rect(0 /* not 985 + kWindowTilePixels*/,
    532                         0 /* not 729 + kWindowTilePixels*/,
    533                         500, 400),
    534               window_bounds);
    535   }
    536 }
    537 
    538 TEST(WindowSizerTest, PersistedWindowOffscreenWithAggressiveRepositioning) {
    539   { // off the left
    540     gfx::Rect window_bounds;
    541     bool maximized;
    542     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    543                     gfx::Rect(-471, 50, 500, 400), false, gfx::Rect(),
    544                     PERSISTED, &window_bounds, &maximized);
    545     EXPECT_FALSE(maximized);
    546     EXPECT_EQ(gfx::Rect(0 /* not -471 */, 50, 500, 400), window_bounds);
    547   }
    548 
    549   { // off the top
    550     gfx::Rect window_bounds;
    551     bool maximized;
    552     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    553                     gfx::Rect(50, -370, 500, 400), false, gfx::Rect(),
    554                     PERSISTED, &window_bounds, &maximized);
    555     EXPECT_FALSE(maximized);
    556     EXPECT_EQ(gfx::Rect(50, 0, 500, 400), window_bounds);
    557   }
    558 
    559   { // off the right
    560     gfx::Rect window_bounds;
    561     bool maximized;
    562     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    563                     gfx::Rect(995, 50, 500, 400), false, gfx::Rect(),
    564                     PERSISTED, &window_bounds, &maximized);
    565     EXPECT_FALSE(maximized);
    566     EXPECT_EQ(gfx::Rect(0 /* not 995 */, 50, 500, 400), window_bounds);
    567   }
    568 
    569   { // off the bottom
    570     gfx::Rect window_bounds;
    571     bool maximized;
    572     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    573                     gfx::Rect(50, 739, 500, 400), false, gfx::Rect(), PERSISTED,
    574                     &window_bounds, &maximized);
    575     EXPECT_FALSE(maximized);
    576     EXPECT_EQ(gfx::Rect(50, 0 /* not 739 */, 500, 400), window_bounds);
    577   }
    578 
    579   { // off the topleft
    580     gfx::Rect window_bounds;
    581     bool maximized;
    582     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    583                     gfx::Rect(-471, -371, 500, 400), false, gfx::Rect(),
    584                     PERSISTED, &window_bounds, &maximized);
    585     EXPECT_FALSE(maximized);
    586     EXPECT_EQ(gfx::Rect(0 /* not -471 */, 0 /* not -371 */, 500, 400),
    587               window_bounds);
    588   }
    589 
    590   { // off the topright
    591     gfx::Rect window_bounds;
    592     bool maximized;
    593     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    594                     gfx::Rect(995, -371, 500, 400), false, gfx::Rect(),
    595                     PERSISTED, &window_bounds, &maximized);
    596     EXPECT_FALSE(maximized);
    597     EXPECT_EQ(gfx::Rect(0 /* not 995 */, 0 /* not -371 */, 500, 400),
    598                         window_bounds);
    599   }
    600 
    601   { // off the bottomleft
    602     gfx::Rect window_bounds;
    603     bool maximized;
    604     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    605                     gfx::Rect(-471, 739, 500, 400), false, gfx::Rect(),
    606                     PERSISTED, &window_bounds, &maximized);
    607     EXPECT_FALSE(maximized);
    608     EXPECT_EQ(gfx::Rect(0 /* not -471 */, 0 /* not 739 */, 500, 400),
    609                         window_bounds);
    610   }
    611 
    612   { // off the bottomright
    613     gfx::Rect window_bounds;
    614     bool maximized;
    615     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    616                     gfx::Rect(995, 739, 500, 400), false, gfx::Rect(),
    617                     PERSISTED, &window_bounds, &maximized);
    618     EXPECT_FALSE(maximized);
    619     EXPECT_EQ(gfx::Rect(0 /* not 995 */, 0 /* not 739 */, 500, 400),
    620                         window_bounds);
    621   }
    622 
    623   { // entirely off left
    624     gfx::Rect window_bounds;
    625     bool maximized;
    626     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    627                     gfx::Rect(-700, 50, 500, 400), false, gfx::Rect(),
    628                     PERSISTED, &window_bounds, &maximized);
    629     EXPECT_FALSE(maximized);
    630     EXPECT_EQ(gfx::Rect(0 /* not -700 */, 50, 500, 400), window_bounds);
    631   }
    632 
    633   { // entirely off left (monitor was detached since last run)
    634     gfx::Rect window_bounds;
    635     bool maximized;
    636     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    637                     gfx::Rect(-700, 50, 500, 400), false, left_nonprimary,
    638                     PERSISTED, &window_bounds, &maximized);
    639     EXPECT_FALSE(maximized);
    640     EXPECT_EQ(gfx::Rect(0, 50, 500, 400), window_bounds);
    641   }
    642 
    643   { // entirely off top
    644     gfx::Rect window_bounds;
    645     bool maximized;
    646     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    647                     gfx::Rect(50, -500, 500, 400), false, gfx::Rect(),
    648                     PERSISTED, &window_bounds, &maximized);
    649     EXPECT_FALSE(maximized);
    650     EXPECT_EQ(gfx::Rect(50, 0, 500, 400), window_bounds);
    651   }
    652 
    653   { // entirely off top (monitor was detached since last run)
    654     gfx::Rect window_bounds;
    655     bool maximized;
    656     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    657                     gfx::Rect(50, -500, 500, 400), false, top_nonprimary,
    658                     PERSISTED, &window_bounds, &maximized);
    659     EXPECT_FALSE(maximized);
    660     EXPECT_EQ(gfx::Rect(50, 0, 500, 400), window_bounds);
    661   }
    662 
    663   { // entirely off right
    664     gfx::Rect window_bounds;
    665     bool maximized;
    666     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    667                     gfx::Rect(1200, 50, 500, 400), false, gfx::Rect(),
    668                     PERSISTED, &window_bounds, &maximized);
    669     EXPECT_FALSE(maximized);
    670     EXPECT_EQ(gfx::Rect(0 /* not 1200 */, 50, 500, 400), window_bounds);
    671   }
    672 
    673   { // entirely off right (monitor was detached since last run)
    674     gfx::Rect window_bounds;
    675     bool maximized;
    676     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    677                     gfx::Rect(1200, 50, 500, 400), false, right_nonprimary,
    678                     PERSISTED, &window_bounds, &maximized);
    679     EXPECT_FALSE(maximized);
    680     EXPECT_EQ(gfx::Rect(524 /* not 1200 */, 50, 500, 400), window_bounds);
    681   }
    682 
    683   { // entirely off bottom
    684     gfx::Rect window_bounds;
    685     bool maximized;
    686     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    687                     gfx::Rect(50, 800, 500, 400), false, gfx::Rect(), PERSISTED,
    688                     &window_bounds, &maximized);
    689     EXPECT_FALSE(maximized);
    690     EXPECT_EQ(gfx::Rect(50, 0 /* not 800 */, 500, 400), window_bounds);
    691   }
    692 
    693   { // entirely off bottom (monitor was detached since last run)
    694     gfx::Rect window_bounds;
    695     bool maximized;
    696     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    697                     gfx::Rect(50, 800, 500, 400), false, bottom_nonprimary,
    698                     PERSISTED, &window_bounds, &maximized);
    699     EXPECT_FALSE(maximized);
    700     EXPECT_EQ(gfx::Rect(50, 368 /* not 800 */, 500, 400), window_bounds);
    701   }
    702 
    703   { // wider than the screen. off both the left and right
    704     gfx::Rect window_bounds;
    705     bool maximized;
    706     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    707                     gfx::Rect(-100, 50, 2000, 400), false, gfx::Rect(),
    708                     PERSISTED, &window_bounds, &maximized);
    709     EXPECT_FALSE(maximized);
    710     EXPECT_EQ(gfx::Rect(0 /* not -100 */, 50, 2000, 400), window_bounds);
    711   }
    712 }
    713 #else
    714 TEST(WindowSizerTest, LastWindowOffscreenWithNonAggressiveRepositioning) {
    715   { // taskbar on left.
    716     gfx::Rect window_bounds;
    717     bool maximized = false;
    718     GetWindowBounds(tentwentyfour, taskbar_left_work_area, gfx::Rect(),
    719                     gfx::Rect(kWindowTilePixels, kWindowTilePixels, 500, 400),
    720                     false, gfx::Rect(), LAST_ACTIVE,
    721                     &window_bounds, &maximized);
    722     EXPECT_FALSE(maximized);
    723     EXPECT_EQ(gfx::Rect(kWindowTilePixels * 2,
    724                         kWindowTilePixels * 2, 500, 400), window_bounds);
    725   }
    726 
    727   // Linux does not tile windows, so tile adjustment tests don't make sense.
    728 #if !defined(OS_LINUX)
    729   { // offset would put the new window offscreen at the bottom but the minimum
    730     // visibility condition is barely satisfied without relocation.
    731     gfx::Rect window_bounds;
    732     bool maximized = false;
    733     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    734                     gfx::Rect(10, 728, 500, 400), false, gfx::Rect(),
    735                     LAST_ACTIVE, &window_bounds, &maximized);
    736     EXPECT_FALSE(maximized);
    737     EXPECT_EQ(gfx::Rect(10 + kWindowTilePixels, 738,
    738                         500, 400), window_bounds);
    739   }
    740 
    741   { // offset would put the new window offscreen at the bottom and the minimum
    742     // visibility condition is satisified by relocation.
    743     gfx::Rect window_bounds;
    744     bool maximized = false;
    745     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    746                     gfx::Rect(10, 729, 500, 400), false, gfx::Rect(),
    747                     LAST_ACTIVE, &window_bounds, &maximized);
    748     EXPECT_FALSE(maximized);
    749     EXPECT_EQ(gfx::Rect(10 + kWindowTilePixels, 738 /* not 739 */, 500, 400),
    750               window_bounds);
    751   }
    752 
    753   { // offset would put the new window offscreen at the right but the minimum
    754     // visibility condition is barely satisfied without relocation.
    755     gfx::Rect window_bounds;
    756     bool maximized = false;
    757     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    758                     gfx::Rect(984, 10, 500, 400), false, gfx::Rect(),
    759                     LAST_ACTIVE, &window_bounds, &maximized);
    760     EXPECT_FALSE(maximized);
    761     EXPECT_EQ(gfx::Rect(994, 10 + kWindowTilePixels, 500, 400), window_bounds);
    762   }
    763 
    764   { // offset would put the new window offscreen at the right and the minimum
    765     // visibility condition is satisified by relocation.
    766     gfx::Rect window_bounds;
    767     bool maximized = false;
    768     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    769                     gfx::Rect(985, 10, 500, 400), false, gfx::Rect(),
    770                     LAST_ACTIVE, &window_bounds, &maximized);
    771     EXPECT_FALSE(maximized);
    772     EXPECT_EQ(gfx::Rect(994 /* not 995 */, 10 + kWindowTilePixels,
    773                         500, 400), window_bounds);
    774   }
    775 
    776   { // offset would put the new window offscreen at the bottom right and the
    777     // minimum visibility condition is satisified by relocation.
    778     gfx::Rect window_bounds;
    779     bool maximized = false;
    780     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    781                     gfx::Rect(985, 729, 500, 400), false, gfx::Rect(),
    782                     LAST_ACTIVE, &window_bounds, &maximized);
    783     EXPECT_FALSE(maximized);
    784     EXPECT_EQ(gfx::Rect(994 /* not 995 */, 738 /* not 739 */, 500, 400),
    785               window_bounds);
    786   }
    787 #endif  // !defined(OS_LINUX)
    788 }
    789 
    790 TEST(WindowSizerTest, PersistedWindowOffscreenWithNonAggressiveRepositioning) {
    791   { // off the left but the minimum visibility condition is barely satisfied
    792     // without relocaiton.
    793     gfx::Rect initial_bounds(-470, 50, 500, 400);
    794 
    795     gfx::Rect window_bounds;
    796     bool maximized;
    797     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    798                     initial_bounds, false, gfx::Rect(), PERSISTED,
    799                     &window_bounds, &maximized);
    800     EXPECT_FALSE(maximized);
    801     EXPECT_EQ(initial_bounds, window_bounds);
    802   }
    803 
    804   { // off the left and the minimum visibility condition is satisfied by
    805     // relocation.
    806     gfx::Rect window_bounds;
    807     bool maximized;
    808     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    809                     gfx::Rect(-471, 50, 500, 400), false, gfx::Rect(),
    810                     PERSISTED, &window_bounds, &maximized);
    811     EXPECT_FALSE(maximized);
    812     EXPECT_EQ(gfx::Rect(-470 /* not -471 */, 50, 500, 400), window_bounds);
    813   }
    814 
    815   { // off the top
    816     gfx::Rect initial_bounds(50, -370, 500, 400);
    817 
    818     gfx::Rect window_bounds;
    819     bool maximized;
    820     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    821                     gfx::Rect(50, -370, 500, 400), false, gfx::Rect(),
    822                     PERSISTED, &window_bounds, &maximized);
    823     EXPECT_FALSE(maximized);
    824     EXPECT_EQ(gfx::Rect(50, 0, 500, 400), window_bounds);
    825   }
    826 
    827   { // off the right but the minimum visibility condition is barely satisified
    828     // without relocation.
    829     gfx::Rect initial_bounds(994, 50, 500, 400);
    830 
    831     gfx::Rect window_bounds;
    832     bool maximized;
    833     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    834                     initial_bounds, false, gfx::Rect(), PERSISTED,
    835                     &window_bounds, &maximized);
    836     EXPECT_FALSE(maximized);
    837     EXPECT_EQ(initial_bounds, window_bounds);
    838   }
    839 
    840   { // off the right and the minimum visibility condition is satisified by
    841     // relocation.
    842     gfx::Rect window_bounds;
    843     bool maximized;
    844     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    845                     gfx::Rect(995, 50, 500, 400), false, gfx::Rect(),
    846                     PERSISTED, &window_bounds, &maximized);
    847     EXPECT_FALSE(maximized);
    848     EXPECT_EQ(gfx::Rect(994 /* not 995 */, 50, 500, 400), window_bounds);
    849   }
    850 
    851   { // off the bottom but the minimum visibility condition is barely satisified
    852     // without relocation.
    853     gfx::Rect initial_bounds(50, 738, 500, 400);
    854 
    855     gfx::Rect window_bounds;
    856     bool maximized;
    857     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    858                     initial_bounds, false, gfx::Rect(), PERSISTED,
    859                     &window_bounds, &maximized);
    860     EXPECT_FALSE(maximized);
    861     EXPECT_EQ(initial_bounds, window_bounds);
    862   }
    863 
    864   { // off the bottom and the minimum visibility condition is satisified by
    865     // relocation.
    866     gfx::Rect window_bounds;
    867     bool maximized;
    868     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    869                     gfx::Rect(50, 739, 500, 400), false, gfx::Rect(), PERSISTED,
    870                     &window_bounds, &maximized);
    871     EXPECT_FALSE(maximized);
    872     EXPECT_EQ(gfx::Rect(50, 738 /* not 739 */, 500, 400), window_bounds);
    873   }
    874 
    875   { // off the topleft
    876     gfx::Rect window_bounds;
    877     bool maximized;
    878     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    879                     gfx::Rect(-471, -371, 500, 400), false, gfx::Rect(),
    880                     PERSISTED, &window_bounds, &maximized);
    881     EXPECT_FALSE(maximized);
    882     EXPECT_EQ(gfx::Rect(-470 /* not -471 */, 0, 500, 400),
    883               window_bounds);
    884   }
    885 
    886   { // off the topright and the minimum visibility condition is satisified by
    887     // relocation.
    888     gfx::Rect window_bounds;
    889     bool maximized;
    890     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    891                     gfx::Rect(995, -371, 500, 400), false, gfx::Rect(),
    892                     PERSISTED, &window_bounds, &maximized);
    893     EXPECT_FALSE(maximized);
    894     EXPECT_EQ(gfx::Rect(994 /* not 995 */, 0, 500, 400),
    895                         window_bounds);
    896   }
    897 
    898   { // off the bottomleft and the minimum visibility condition is satisified by
    899     // relocation.
    900     gfx::Rect window_bounds;
    901     bool maximized;
    902     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    903                     gfx::Rect(-471, 739, 500, 400), false, gfx::Rect(),
    904                     PERSISTED, &window_bounds, &maximized);
    905     EXPECT_FALSE(maximized);
    906     EXPECT_EQ(gfx::Rect(-470 /* not -471 */, 738 /* not 739 */, 500, 400),
    907                         window_bounds);
    908   }
    909 
    910   { // off the bottomright and the minimum visibility condition is satisified by
    911     // relocation.
    912     gfx::Rect window_bounds;
    913     bool maximized;
    914     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    915                     gfx::Rect(995, 739, 500, 400), false, gfx::Rect(),
    916                     PERSISTED, &window_bounds, &maximized);
    917     EXPECT_FALSE(maximized);
    918     EXPECT_EQ(gfx::Rect(994 /* not 995 */, 738 /* not 739 */, 500, 400),
    919                         window_bounds);
    920   }
    921 
    922   { // entirely off left
    923     gfx::Rect window_bounds;
    924     bool maximized;
    925     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    926                     gfx::Rect(-700, 50, 500, 400), false, gfx::Rect(),
    927                     PERSISTED, &window_bounds, &maximized);
    928     EXPECT_FALSE(maximized);
    929     EXPECT_EQ(gfx::Rect(-470 /* not -700 */, 50, 500, 400), window_bounds);
    930   }
    931 
    932   { // entirely off left (monitor was detached since last run)
    933     gfx::Rect window_bounds;
    934     bool maximized;
    935     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    936                     gfx::Rect(-700, 50, 500, 400), false, left_nonprimary,
    937                     PERSISTED, &window_bounds, &maximized);
    938     EXPECT_FALSE(maximized);
    939     EXPECT_EQ(gfx::Rect(0, 50, 500, 400), window_bounds);
    940   }
    941 
    942   { // entirely off top
    943     gfx::Rect window_bounds;
    944     bool maximized;
    945     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    946                     gfx::Rect(50, -500, 500, 400), false, gfx::Rect(),
    947                     PERSISTED, &window_bounds, &maximized);
    948     EXPECT_FALSE(maximized);
    949     EXPECT_EQ(gfx::Rect(50, 0, 500, 400), window_bounds);
    950   }
    951 
    952   { // entirely off top (monitor was detached since last run)
    953     gfx::Rect window_bounds;
    954     bool maximized;
    955     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    956                     gfx::Rect(50, -500, 500, 400), false, top_nonprimary,
    957                     PERSISTED, &window_bounds, &maximized);
    958     EXPECT_FALSE(maximized);
    959     EXPECT_EQ(gfx::Rect(50, 0, 500, 400), window_bounds);
    960   }
    961 
    962   { // entirely off right
    963     gfx::Rect window_bounds;
    964     bool maximized;
    965     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    966                     gfx::Rect(1200, 50, 500, 400), false, gfx::Rect(),
    967                     PERSISTED, &window_bounds, &maximized);
    968     EXPECT_FALSE(maximized);
    969     EXPECT_EQ(gfx::Rect(994 /* not 1200 */, 50, 500, 400), window_bounds);
    970   }
    971 
    972   { // entirely off right (monitor was detached since last run)
    973     gfx::Rect window_bounds;
    974     bool maximized;
    975     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    976                     gfx::Rect(1200, 50, 500, 400), false, right_nonprimary,
    977                     PERSISTED, &window_bounds, &maximized);
    978     EXPECT_FALSE(maximized);
    979     EXPECT_EQ(gfx::Rect(524, 50, 500, 400), window_bounds);
    980   }
    981 
    982   { // entirely off bottom
    983     gfx::Rect window_bounds;
    984     bool maximized;
    985     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    986                     gfx::Rect(50, 800, 500, 400), false, gfx::Rect(), PERSISTED,
    987                     &window_bounds, &maximized);
    988     EXPECT_FALSE(maximized);
    989     EXPECT_EQ(gfx::Rect(50, 738 /* not 800 */, 500, 400), window_bounds);
    990   }
    991 
    992   { // entirely off bottom (monitor was detached since last run)
    993     gfx::Rect window_bounds;
    994     bool maximized;
    995     GetWindowBounds(tentwentyfour, tentwentyfour, gfx::Rect(),
    996                     gfx::Rect(50, 800, 500, 400), false, bottom_nonprimary,
    997                     PERSISTED, &window_bounds, &maximized);
    998     EXPECT_FALSE(maximized);
    999     EXPECT_EQ(gfx::Rect(50, 368, 500, 400), window_bounds);
   1000   }
   1001 }
   1002 #endif  //defined(OS_MACOSX)
   1003