browser_view_layout_unittest.cc revision f2477e01787aa58f445919b809d89e252beef54f
1// Copyright 2013 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 "chrome/browser/ui/views/frame/browser_view_layout.h" 6 7#include "chrome/browser/ui/views/frame/browser_view.h" 8#include "chrome/browser/ui/views/frame/browser_view_layout_delegate.h" 9#include "chrome/browser/ui/views/frame/contents_container.h" 10#include "chrome/browser/ui/views/frame/immersive_mode_controller.h" 11#include "chrome/browser/ui/views/infobars/infobar_container_view.h" 12#include "chrome/browser/ui/views/tabs/tab_strip.h" 13#include "chrome/test/base/browser_with_test_window_test.h" 14#include "testing/gtest/include/gtest/gtest.h" 15 16class MockBrowserViewLayoutDelegate : public BrowserViewLayoutDelegate { 17 public: 18 MockBrowserViewLayoutDelegate() 19 : tab_strip_visible_(true), 20 toolbar_visible_(true), 21 bookmark_bar_visible_(true), 22 download_shelf_needs_layout_(false) { 23 } 24 virtual ~MockBrowserViewLayoutDelegate() {} 25 26 void set_download_shelf_needs_layout(bool layout) { 27 download_shelf_needs_layout_ = layout; 28 } 29 void set_tab_strip_visible(bool visible) { 30 tab_strip_visible_ = visible; 31 } 32 void set_toolbar_visible(bool visible) { 33 toolbar_visible_ = visible; 34 } 35 void set_bookmark_bar_visible(bool visible) { 36 bookmark_bar_visible_ = visible; 37 } 38 39 // BrowserViewLayout::Delegate overrides: 40 virtual views::View* GetWindowSwitcherButton() const OVERRIDE { 41 // TODO(jamescook): Add a test for Windows that exercises the layout for 42 // this button. 43 return NULL; 44 } 45 virtual bool IsTabStripVisible() const OVERRIDE { 46 return tab_strip_visible_; 47 } 48 virtual gfx::Rect GetBoundsForTabStripInBrowserView() const OVERRIDE { 49 return gfx::Rect(); 50 } 51 virtual int GetTopInsetInBrowserView() const OVERRIDE { 52 return 0; 53 } 54 virtual int GetThemeBackgroundXInset() const OVERRIDE { 55 return 0; 56 } 57 virtual bool IsToolbarVisible() const OVERRIDE { 58 return toolbar_visible_; 59 } 60 virtual bool IsBookmarkBarVisible() const OVERRIDE { 61 return bookmark_bar_visible_; 62 } 63 virtual bool DownloadShelfNeedsLayout() const OVERRIDE { 64 return download_shelf_needs_layout_; 65 } 66 67 virtual FullscreenExitBubbleViews* GetFullscreenExitBubble() const OVERRIDE { 68 return NULL; 69 } 70 71 private: 72 bool tab_strip_visible_; 73 bool toolbar_visible_; 74 bool bookmark_bar_visible_; 75 bool download_shelf_needs_layout_; 76 77 DISALLOW_COPY_AND_ASSIGN(MockBrowserViewLayoutDelegate); 78}; 79 80/////////////////////////////////////////////////////////////////////////////// 81 82// A simple view that prefers an initial size. 83class MockView : public views::View { 84 public: 85 explicit MockView(gfx::Size initial_size) 86 : size_(initial_size) { 87 SetBoundsRect(gfx::Rect(gfx::Point(), size_)); 88 } 89 virtual ~MockView() {} 90 91 // views::View overrides: 92 virtual gfx::Size GetPreferredSize() OVERRIDE { 93 return size_; 94 } 95 96 private: 97 gfx::Size size_; 98 99 DISALLOW_COPY_AND_ASSIGN(MockView); 100}; 101 102/////////////////////////////////////////////////////////////////////////////// 103 104class MockImmersiveModeController : public ImmersiveModeController { 105 public: 106 MockImmersiveModeController() {} 107 virtual ~MockImmersiveModeController() {} 108 109 // ImmersiveModeController overrides: 110 virtual void Init(BrowserView* browser_view) OVERRIDE {} 111 virtual void SetEnabled(bool enabled) OVERRIDE {} 112 virtual bool IsEnabled() const OVERRIDE { return false; } 113 virtual bool ShouldHideTabIndicators() const OVERRIDE { return false; } 114 virtual bool ShouldHideTopViews() const OVERRIDE { return false; } 115 virtual bool IsRevealed() const OVERRIDE { return false; } 116 virtual int GetTopContainerVerticalOffset( 117 const gfx::Size& top_container_size) const OVERRIDE { return 0; } 118 virtual ImmersiveRevealedLock* GetRevealedLock( 119 AnimateReveal animate_reveal) OVERRIDE WARN_UNUSED_RESULT { return NULL; } 120 virtual void OnFindBarVisibleBoundsChanged( 121 const gfx::Rect& new_visible_bounds) OVERRIDE {} 122 virtual void SetupForTest() OVERRIDE {} 123 124 private: 125 DISALLOW_COPY_AND_ASSIGN(MockImmersiveModeController); 126}; 127 128/////////////////////////////////////////////////////////////////////////////// 129// Tests of BrowserViewLayout. Runs tests without constructing a BrowserView. 130class BrowserViewLayoutTest : public BrowserWithTestWindowTest { 131 public: 132 BrowserViewLayoutTest() 133 : delegate_(NULL), 134 top_container_(NULL), 135 tab_strip_(NULL), 136 toolbar_(NULL), 137 infobar_container_(NULL), 138 contents_split_(NULL), 139 contents_container_(NULL), 140 active_web_view_(NULL) {} 141 virtual ~BrowserViewLayoutTest() {} 142 143 BrowserViewLayout* layout() { return layout_.get(); } 144 MockBrowserViewLayoutDelegate* delegate() { return delegate_; } 145 MockView* root_view() { return root_view_.get(); } 146 MockView* top_container() { return top_container_; } 147 TabStrip* tab_strip() { return tab_strip_; } 148 MockView* toolbar() { return toolbar_; } 149 InfoBarContainerView* infobar_container() { return infobar_container_; } 150 MockView* contents_split() { return contents_split_; } 151 ContentsContainer* contents_container() { return contents_container_; } 152 153 // BrowserWithTestWindowTest overrides: 154 virtual void SetUp() OVERRIDE { 155 BrowserWithTestWindowTest::SetUp(); 156 157 root_view_.reset(new MockView(gfx::Size(800, 600))); 158 159 immersive_mode_controller_.reset(new MockImmersiveModeController); 160 161 top_container_ = new MockView(gfx::Size(800, 60)); 162 tab_strip_ = new TabStrip(NULL); 163 top_container_->AddChildView(tab_strip_); 164 toolbar_ = new MockView(gfx::Size(800, 30)); 165 top_container_->AddChildView(toolbar_); 166 root_view_->AddChildView(top_container_); 167 168 infobar_container_ = new InfoBarContainerView(NULL); 169 root_view_->AddChildView(infobar_container_); 170 171 contents_split_ = new MockView(gfx::Size(800, 600)); 172 active_web_view_ = new MockView(gfx::Size(800, 600)); 173 contents_container_ = new ContentsContainer(active_web_view_); 174 contents_split_->AddChildView(contents_container_); 175 root_view_->AddChildView(contents_split_); 176 177 // TODO(jamescook): Attach |layout_| to |root_view_|? 178 layout_.reset(new BrowserViewLayout); 179 delegate_ = new MockBrowserViewLayoutDelegate; 180 layout_->Init(delegate_, 181 browser(), 182 NULL, // BrowserView. 183 top_container_, 184 tab_strip_, 185 toolbar_, 186 infobar_container_, 187 contents_split_, 188 contents_container_, 189 immersive_mode_controller_.get()); 190 } 191 192 private: 193 scoped_ptr<BrowserViewLayout> layout_; 194 MockBrowserViewLayoutDelegate* delegate_; // Owned by |layout_|. 195 scoped_ptr<MockView> root_view_; 196 197 // Views owned by |root_view_|. 198 MockView* top_container_; 199 TabStrip* tab_strip_; 200 MockView* toolbar_; 201 InfoBarContainerView* infobar_container_; 202 MockView* contents_split_; 203 ContentsContainer* contents_container_; 204 MockView* active_web_view_; 205 206 scoped_ptr<MockImmersiveModeController> immersive_mode_controller_; 207 208 DISALLOW_COPY_AND_ASSIGN(BrowserViewLayoutTest); 209}; 210 211// Test basic construction and initialization. 212TEST_F(BrowserViewLayoutTest, BrowserViewLayout) { 213 EXPECT_TRUE(layout()->browser()); 214 EXPECT_TRUE(layout()->GetWebContentsModalDialogHost()); 215 EXPECT_FALSE(layout()->InfobarVisible()); 216} 217 218// Test the core layout functions. 219TEST_F(BrowserViewLayoutTest, Layout) { 220 // Simulate a window with no interesting UI. 221 delegate()->set_tab_strip_visible(false); 222 delegate()->set_toolbar_visible(false); 223 delegate()->set_bookmark_bar_visible(false); 224 layout()->Layout(root_view()); 225 226 // Top views are zero-height. 227 EXPECT_EQ("0,0 0x0", tab_strip()->bounds().ToString()); 228 EXPECT_EQ("0,0 800x0", toolbar()->bounds().ToString()); 229 EXPECT_EQ("0,0 800x0", infobar_container()->bounds().ToString()); 230 // Contents split fills the window. 231 EXPECT_EQ("0,0 800x600", contents_split()->bounds().ToString()); 232 233 // Turn on the toolbar, like in a pop-up window. 234 delegate()->set_toolbar_visible(true); 235 layout()->Layout(root_view()); 236 237 // Now the toolbar has bounds and other views shift down. 238 EXPECT_EQ("0,0 0x0", tab_strip()->bounds().ToString()); 239 EXPECT_EQ("0,0 800x30", toolbar()->bounds().ToString()); 240 EXPECT_EQ("0,30 800x0", infobar_container()->bounds().ToString()); 241 EXPECT_EQ("0,30 800x570", contents_split()->bounds().ToString()); 242 243 // TODO(jamescook): Tab strip and bookmark bar. 244} 245 246TEST_F(BrowserViewLayoutTest, LayoutDownloadShelf) { 247 scoped_ptr<MockView> download_shelf(new MockView(gfx::Size(800, 50))); 248 layout()->set_download_shelf(download_shelf.get()); 249 250 // If download shelf doesn't need layout, it doesn't move the bottom edge. 251 delegate()->set_download_shelf_needs_layout(false); 252 const int kBottom = 500; 253 EXPECT_EQ(kBottom, layout()->LayoutDownloadShelf(kBottom)); 254 255 // Download shelf layout moves up the bottom edge and sets visibility. 256 delegate()->set_download_shelf_needs_layout(true); 257 download_shelf->SetVisible(false); 258 EXPECT_EQ(450, layout()->LayoutDownloadShelf(kBottom)); 259 EXPECT_TRUE(download_shelf->visible()); 260 EXPECT_EQ("0,450 0x50", download_shelf->bounds().ToString()); 261} 262