11320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci// Copyright 2014 The Chromium Authors. All rights reserved. 21320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci// Use of this source code is governed by a BSD-style license that can be 31320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci// found in the LICENSE file. 41320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 51320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "ui/views/controls/webview/webview.h" 61320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 71320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "base/memory/scoped_ptr.h" 81320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "content/browser/web_contents/web_contents_impl.h" 91320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "content/public/browser/web_contents_observer.h" 101320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "content/public/test/test_browser_context.h" 111320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "content/public/test/test_browser_thread.h" 121320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "content/public/test/web_contents_tester.h" 131320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "content/test/test_content_browser_client.h" 141320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "ui/aura/window.h" 151320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "ui/views/test/test_views_delegate.h" 161320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "ui/views/test/widget_test.h" 171320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 181320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tuccinamespace { 191320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 201320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci// Provides functionality to create a test WebContents. 211320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucciclass WebViewTestViewsDelegate : public views::TestViewsDelegate { 221320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci public: 231320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci WebViewTestViewsDelegate() {} 241320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci virtual ~WebViewTestViewsDelegate() {} 251320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 261320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // Overriden from TestViewsDelegate. 271320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci virtual content::WebContents* CreateWebContents( 281320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::BrowserContext* browser_context, 291320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::SiteInstance* site_instance) OVERRIDE { 301320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci return content::WebContentsTester::CreateTestWebContents(browser_context, 311320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci site_instance); 321320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci } 331320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 341320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci private: 351320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci DISALLOW_COPY_AND_ASSIGN(WebViewTestViewsDelegate); 361320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci}; 371320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 381320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci// Provides functionality to test a WebView. 391320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucciclass WebViewUnitTest : public views::test::WidgetTest { 401320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci public: 411320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci WebViewUnitTest() 421320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci : ui_thread_(content::BrowserThread::UI, base::MessageLoop::current()), 431320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci file_blocking_thread_(content::BrowserThread::FILE_USER_BLOCKING, 441320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci base::MessageLoop::current()), 451320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci io_thread_(content::BrowserThread::IO, base::MessageLoop::current()) {} 461320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 471320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci virtual ~WebViewUnitTest() {} 481320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 491320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci virtual void SetUp() OVERRIDE { 501320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // The ViewsDelegate is deleted when the ViewsTestBase class is torn down. 511320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci WidgetTest::set_views_delegate(new WebViewTestViewsDelegate); 521320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci browser_context_.reset(new content::TestBrowserContext); 531320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci WidgetTest::SetUp(); 541320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // Set the test content browser client to avoid pulling in needless 551320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // dependencies from content. 561320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci SetBrowserClientForTesting(&test_browser_client_); 571320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci } 581320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 591320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci virtual void TearDown() OVERRIDE { 601320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci browser_context_.reset(NULL); 611320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // Flush the message loop to execute pending relase tasks as this would 621320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // upset ASAN and Valgrind. 631320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci RunPendingMessages(); 641320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci WidgetTest::TearDown(); 651320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci } 661320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 671320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci protected: 681320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::BrowserContext* browser_context() { return browser_context_.get(); } 691320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 701320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci private: 711320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::TestBrowserThread ui_thread_; 721320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::TestBrowserThread file_blocking_thread_; 731320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::TestBrowserThread io_thread_; 741320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci scoped_ptr<content::TestBrowserContext> browser_context_; 751320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci scoped_ptr<WebViewTestViewsDelegate> views_delegate_; 761320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::TestContentBrowserClient test_browser_client_; 771320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 781320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci DISALLOW_COPY_AND_ASSIGN(WebViewUnitTest); 791320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci}; 801320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 811320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci// Provides functionaity to observe events on a WebContents like WasShown/ 821320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci// WasHidden/WebContentsDestroyed. 831320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucciclass WebViewTestWebContentsObserver : public content::WebContentsObserver { 841320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci public: 851320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci WebViewTestWebContentsObserver(content::WebContents* web_contents) 861320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci : web_contents_(static_cast<content::WebContentsImpl*>(web_contents)), 871320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci was_shown_(false), 881320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci shown_count_(0), 891320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci hidden_count_(0) { 901320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::WebContentsObserver::Observe(web_contents); 911320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci } 921320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 931320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci virtual ~WebViewTestWebContentsObserver() { 941320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci if (web_contents_) 951320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::WebContentsObserver::Observe(NULL); 961320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci } 971320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 981320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci virtual void WebContentsDestroyed() OVERRIDE { 991320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci DCHECK(web_contents_); 1001320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::WebContentsObserver::Observe(NULL); 1011320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci web_contents_ = NULL; 1021320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci } 1031320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1041320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci virtual void WasShown() OVERRIDE { 1051320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci valid_root_while_shown_ = 1061320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci web_contents()->GetNativeView()->GetRootWindow() != NULL; 1071320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci was_shown_ = true; 1081320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci ++shown_count_; 1091320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci } 1101320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1111320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci virtual void WasHidden() OVERRIDE { 1121320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci was_shown_ = false; 1131320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci ++hidden_count_; 1141320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci } 1151320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1161320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci bool was_shown() const { return was_shown_; } 1171320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1181320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci int shown_count() const { return shown_count_; } 1191320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1201320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci int hidden_count() const { return hidden_count_; } 1211320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1221320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci bool valid_root_while_shown() const { return valid_root_while_shown_; } 1231320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1241320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci private: 1251320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::WebContentsImpl* web_contents_; 1261320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci bool was_shown_; 1271320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci int32 shown_count_; 1281320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci int32 hidden_count_; 1291320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // Set to true if the view containing the webcontents has a valid root window. 1301320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci bool valid_root_while_shown_; 1311320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1321320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci DISALLOW_COPY_AND_ASSIGN(WebViewTestWebContentsObserver); 1331320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci}; 1341320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1351320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci// Tests that attaching and detaching a WebContents to a WebView makes the 1361320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci// WebContents visible and hidden respectively. 1371320f92c476a1ad9d19dba2a48c72b75566198e9Primiano TucciTEST_F(WebViewUnitTest, TestWebViewAttachDetachWebContents) { 1381320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // Create a top level widget and a webview as its content. 1391320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci views::Widget* widget = CreateTopLevelFramelessPlatformWidget(); 1401320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci widget->SetBounds(gfx::Rect(0, 10, 100, 100)); 1411320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci views::WebView* webview = new views::WebView(browser_context()); 1421320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci widget->SetContentsView(webview); 1431320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci widget->Show(); 1441320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1451320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // Case 1: Create a new WebContents and set it in the webview via 1461320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // SetWebContents. This should make the WebContents visible. 1471320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::WebContents::CreateParams params(browser_context()); 1481320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci scoped_ptr<content::WebContents> web_contents1( 1491320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::WebContents::Create(params)); 1501320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci WebViewTestWebContentsObserver observer1(web_contents1.get()); 1511320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_FALSE(observer1.was_shown()); 1521320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1531320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci webview->SetWebContents(web_contents1.get()); 1541320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_TRUE(observer1.was_shown()); 1551320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_TRUE(web_contents1->GetNativeView()->IsVisible()); 1561320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_EQ(observer1.shown_count(), 1); 1571320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_EQ(observer1.hidden_count(), 0); 1581320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_TRUE(observer1.valid_root_while_shown()); 1591320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1601320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // Case 2: Create another WebContents and replace the current WebContents 1611320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // via SetWebContents(). This should hide the current WebContents and show 1621320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // the new one. 1631320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::WebContents::CreateParams params2(browser_context()); 1641320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci scoped_ptr<content::WebContents> web_contents2( 1651320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci content::WebContents::Create(params2)); 1661320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1671320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci WebViewTestWebContentsObserver observer2(web_contents2.get()); 1681320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_FALSE(observer2.was_shown()); 1691320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1701320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // Setting the new WebContents should hide the existing one. 1711320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci webview->SetWebContents(web_contents2.get()); 1721320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_FALSE(observer1.was_shown()); 1731320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_TRUE(observer2.was_shown()); 1741320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_TRUE(observer2.valid_root_while_shown()); 1751320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1761320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci // WebContents1 should not get stray show calls when WebContents2 is set. 1771320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_EQ(observer1.shown_count(), 1); 1781320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_EQ(observer1.hidden_count(), 1); 1791320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_EQ(observer2.shown_count(), 1); 1801320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci EXPECT_EQ(observer2.hidden_count(), 0); 1811320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1821320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci widget->Close(); 1831320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci RunPendingMessages(); 1841320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci} 1851320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 1861320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci} // namespace 187