diff options
author | jam@chromium.org <jam@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-10-28 23:37:58 +0000 |
---|---|---|
committer | jam@chromium.org <jam@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-10-28 23:37:58 +0000 |
commit | fab2b8f341094f1c24eefc61f8671c7ddc23ad38 (patch) | |
tree | a384f98e98dc1f4cb4b73253dfa07650a7f6cad9 /chrome | |
parent | 66cdc8083488db136c3e0a6ed8a8b5051541a2e7 (diff) | |
download | chromium_src-fab2b8f341094f1c24eefc61f8671c7ddc23ad38.zip chromium_src-fab2b8f341094f1c24eefc61f8671c7ddc23ad38.tar.gz chromium_src-fab2b8f341094f1c24eefc61f8671c7ddc23ad38.tar.bz2 |
Add automated tests for PDFs.
Review URL: http://codereview.chromium.org/2720002
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@64336 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome')
-rw-r--r-- | chrome/browser/plugin_updater.cc | 15 | ||||
-rw-r--r-- | chrome/chrome_tests.gypi | 1 | ||||
-rw-r--r-- | chrome/common/chrome_switches.cc | 4 | ||||
-rw-r--r-- | chrome/common/chrome_switches.h | 1 | ||||
-rw-r--r-- | chrome/test/data/pdf_browsertest.pdf | bin | 0 -> 26251 bytes | |||
-rw-r--r-- | chrome/test/data/pdf_browsertest.png | bin | 0 -> 92261 bytes | |||
-rw-r--r-- | chrome/test/data/pdf_browsertest_scroll.png | bin | 0 -> 101999 bytes | |||
-rw-r--r-- | chrome/test/plugin/pdf_browsertest.cc | 243 |
8 files changed, 260 insertions, 4 deletions
diff --git a/chrome/browser/plugin_updater.cc b/chrome/browser/plugin_updater.cc index d560b3e5..8e8227c0 100644 --- a/chrome/browser/plugin_updater.cc +++ b/chrome/browser/plugin_updater.cc @@ -136,6 +136,8 @@ void PluginUpdater::DisablePluginGroupsFromPrefs(Profile* profile) { bool found_internal_pdf = false; bool force_enable_internal_pdf = false; string16 pdf_group_name = ASCIIToUTF16(PepperPluginRegistry::kPDFPluginName); + bool force_internal_pdf_for_this_run = CommandLine::ForCurrentProcess()-> + HasSwitch(switches::kForceInternalPDFPlugin); FilePath pdf_path; PathService::Get(chrome::FILE_PDF_PLUGIN, &pdf_path); FilePath::StringType pdf_path_str = pdf_path.value(); @@ -181,9 +183,13 @@ void PluginUpdater::DisablePluginGroupsFromPrefs(Profile* profile) { if (FilePath::CompareIgnoreCase(path, pdf_path_str) == 0) { found_internal_pdf = true; - if (!enabled && force_enable_internal_pdf) { - enabled = true; - plugin->SetBoolean("enabled", true); + if (!enabled) { + if (force_enable_internal_pdf) { + enabled = true; + plugin->SetBoolean("enabled", true); + } else if (force_internal_pdf_for_this_run) { + enabled = true; + } } } if (!enabled) @@ -206,7 +212,8 @@ void PluginUpdater::DisablePluginGroupsFromPrefs(Profile* profile) { profile->GetPrefs()->GetList(prefs::kPluginsPluginsBlacklist); DisablePluginsFromPolicy(plugin_blacklist); - if (!enable_internal_pdf_ && !found_internal_pdf) { + if ((!enable_internal_pdf_ && !found_internal_pdf) && + !force_internal_pdf_for_this_run) { // The internal PDF plugin is disabled by default, and the user hasn't // overridden the default. NPAPI::PluginList::Singleton()->DisablePlugin(pdf_path); diff --git a/chrome/chrome_tests.gypi b/chrome/chrome_tests.gypi index bb2f0f1..a4d0e35 100644 --- a/chrome/chrome_tests.gypi +++ b/chrome/chrome_tests.gypi @@ -2032,6 +2032,7 @@ 'test/in_process_browser_test.cc', 'test/in_process_browser_test.h', 'test/out_of_proc_test_runner.cc', + 'test/plugin/pdf_browsertest.cc', 'test/render_view_test.cc', 'test/render_view_test.h', ], diff --git a/chrome/common/chrome_switches.cc b/chrome/common/chrome_switches.cc index 9f5c154..907f8f3 100644 --- a/chrome/common/chrome_switches.cc +++ b/chrome/common/chrome_switches.cc @@ -600,6 +600,10 @@ const char kForceAppsPromoVisible[] = "force-apps-promo-visible"; // current details. const char kForceFieldTestNameAndValue[] = "force-fieldtest"; +// Forces the internal PDF plugin to be used for this run, even if it's disabled +// by default. Used for testing. +const char kForceInternalPDFPlugin[] = "force-internal-pdf"; + // Force renderer accessibility to be on instead of enabling it on demand when // a screen reader is detected. The disable-renderer-accessibility switch // overrides this if present. diff --git a/chrome/common/chrome_switches.h b/chrome/common/chrome_switches.h index 91bf0cf..6235e50 100644 --- a/chrome/common/chrome_switches.h +++ b/chrome/common/chrome_switches.h @@ -180,6 +180,7 @@ extern const char kFileDescriptorLimit[]; extern const char kFirstRun[]; extern const char kForceAppsPromoVisible[]; extern const char kForceFieldTestNameAndValue[]; +extern const char kForceInternalPDFPlugin[]; extern const char kForceRendererAccessibility[]; extern const char kGpuLauncher[]; extern const char kGpuProcess[]; diff --git a/chrome/test/data/pdf_browsertest.pdf b/chrome/test/data/pdf_browsertest.pdf Binary files differnew file mode 100644 index 0000000..0b5bdb9 --- /dev/null +++ b/chrome/test/data/pdf_browsertest.pdf diff --git a/chrome/test/data/pdf_browsertest.png b/chrome/test/data/pdf_browsertest.png Binary files differnew file mode 100644 index 0000000..3f5bbff --- /dev/null +++ b/chrome/test/data/pdf_browsertest.png diff --git a/chrome/test/data/pdf_browsertest_scroll.png b/chrome/test/data/pdf_browsertest_scroll.png Binary files differnew file mode 100644 index 0000000..d80223f --- /dev/null +++ b/chrome/test/data/pdf_browsertest_scroll.png diff --git a/chrome/test/plugin/pdf_browsertest.cc b/chrome/test/plugin/pdf_browsertest.cc new file mode 100644 index 0000000..1feb500e --- /dev/null +++ b/chrome/test/plugin/pdf_browsertest.cc @@ -0,0 +1,243 @@ +// Copyright (c) 2010 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "app/clipboard/clipboard.h" +#include "base/command_line.h" +#include "base/file_util.h" +#include "base/path_service.h" +#include "base/string_number_conversions.h" +#include "base/utf_string_conversions.h" +#include "chrome/browser/browser.h" +#include "chrome/browser/browser_window.h" +#include "chrome/browser/renderer_host/render_view_host.h" +#include "chrome/browser/tab_contents/tab_contents.h" +#include "chrome/browser/window_sizer.h" +#include "chrome/common/chrome_paths.h" +#include "chrome/common/chrome_switches.h" +#include "chrome/common/notification_observer.h" +#include "chrome/test/in_process_browser_test.h" +#include "chrome/test/ui_test_utils.h" +#include "gfx/codec/png_codec.h" + +namespace { + +// Include things like browser frame and scrollbar and make sure we're bigger +// than the test pdf document. +static const int kBrowserWidth = 1000; +static const int kBrowserHeight = 600; + +class PDFBrowserTest : public InProcessBrowserTest, + public NotificationObserver { + public: + PDFBrowserTest() + : have_plugin_(false), + snapshot_different_(true), + next_dummy_search_value_(0) { + } + + protected: + bool have_plugin() const { return have_plugin_; } + + virtual void SetUp() { + FilePath pdf_path; + PathService::Get(chrome::FILE_PDF_PLUGIN, &pdf_path); + have_plugin_ = file_util::PathExists(pdf_path); + InProcessBrowserTest::SetUp(); + } + + void Load() { + GURL url(ui_test_utils::GetTestUrl( + FilePath(FilePath::kCurrentDirectory), + FilePath(FILE_PATH_LITERAL("pdf_browsertest.pdf")))); + ui_test_utils::NavigateToURL(browser(), url); + gfx::Rect bounds(gfx::Rect(0, 0, kBrowserWidth, kBrowserHeight)); + + scoped_ptr<WindowSizer::MonitorInfoProvider> monitor_info( + WindowSizer::CreateDefaultMonitorInfoProvider()); + gfx::Rect screen_bounds = monitor_info->GetPrimaryMonitorBounds(); + ASSERT_GT(screen_bounds.width(), kBrowserWidth); + ASSERT_GT(screen_bounds.height(), kBrowserHeight); + + browser()->window()->SetBounds(bounds); + } + + void VerifySnapshot(const std::string& expected_filename) { + snapshot_different_ = true; + expected_filename_ = expected_filename; + RenderViewHost* host = + browser()->GetSelectedTabContents()->render_view_host(); + + host->CaptureSnapshot(); + ui_test_utils::RegisterAndWait(this, + NotificationType::TAB_SNAPSHOT_TAKEN, + Source<RenderViewHost>(host)); + ASSERT_FALSE(snapshot_different_) << "Rendering didn't match, see result " + "at " << snapshot_filename_.value().c_str(); + } + + void WaitForResponse() { + // Even if the plugin has loaded the data or scrolled, because of how + // pepper painting works, we might not have the data. One way to force this + // to be flushed is to do a find operation, since on this two-page test + // document, it'll wait for us to flush the renderer message loop twice and + // also the browser's once, at which point we're guaranteed to have updated + // the backingstore. Hacky, but it works. + // Note that we need to change the text each time, because if we don't the + // renderer code will think the second message is to go to next result, but + // there are none so the plugin will assert. + + string16 query = UTF8ToUTF16( + std::string("xyzxyz" + base::IntToString(next_dummy_search_value_++))); + ASSERT_EQ(0, ui_test_utils::FindInPage( + browser()->GetSelectedTabContents(), query, true, false, NULL)); + } + + private: + virtual void SetUpCommandLine(CommandLine* command_line) { + command_line->AppendSwitch(switches::kForceInternalPDFPlugin); + } + + // NotificationObserver + virtual void Observe(NotificationType type, + const NotificationSource& source, + const NotificationDetails& details) { + if (type == NotificationType::TAB_SNAPSHOT_TAKEN) { + MessageLoopForUI::current()->Quit(); + FilePath reference = ui_test_utils::GetTestFilePath( + FilePath(FilePath::kCurrentDirectory), + FilePath().AppendASCII(expected_filename_)); + base::PlatformFileInfo info; + ASSERT_TRUE(file_util::GetFileInfo(reference, &info)); + int size = static_cast<size_t>(info.size); + scoped_array<char> data(new char[size]); + ASSERT_EQ(size, file_util::ReadFile(reference, data.get(), size)); + + int w, h; + std::vector<unsigned char> decoded; + ASSERT_TRUE(gfx::PNGCodec::Decode( + reinterpret_cast<unsigned char*>(data.get()), size, + gfx::PNGCodec::FORMAT_BGRA, &decoded, &w, &h)); + int32* ref_pixels = reinterpret_cast<int32*>(&decoded[0]); + + const SkBitmap* bitmap = Details<const SkBitmap>(details).ptr(); + int32* pixels = static_cast<int32*>(bitmap->getPixels()); + + // Get the background color, and use it to figure out the x-offsets in + // each image. The reason is that depending on the theme in the OS, the + // same browser width can lead to slightly different plugin sizes, so the + // pdf content will start at different x offsets. + // Also note that the images we saved are cut off before the scrollbar, as + // that'll change depending on the theme, and also cut off vertically so + // that the ui controls don't show up, as those fade-in and so the timing + // will affect their transparency. + int32 bg_color = ref_pixels[0]; + int ref_x_offset, snapshot_x_offset; + for (ref_x_offset = 0; ref_x_offset < w; ++ref_x_offset) { + if (ref_pixels[ref_x_offset] != bg_color) + break; + } + + for (snapshot_x_offset = 0; snapshot_x_offset < bitmap->width(); + ++snapshot_x_offset) { + if (pixels[snapshot_x_offset] != bg_color) + break; + } + + int x_max = std::min( + w - ref_x_offset, bitmap->width() - snapshot_x_offset); + int y_max = std::min(h, bitmap->height()); + int stride = bitmap->rowBytes(); + snapshot_different_ = false; + for (int y = 0; y < y_max && !snapshot_different_; ++y) { + for (int x = 0; x < x_max && !snapshot_different_; ++x) { + if (pixels[y * stride / sizeof(int32) + x + snapshot_x_offset] != + ref_pixels[y * w + x + ref_x_offset]) + snapshot_different_ = true; + } + } + + if (snapshot_different_) { + std::vector<unsigned char> png_data; + gfx::PNGCodec::EncodeBGRASkBitmap(*bitmap, false, &png_data); + if (file_util::CreateTemporaryFile(&snapshot_filename_)) { + file_util::WriteFile(snapshot_filename_, + reinterpret_cast<char*>(&png_data[0]), png_data.size()); + } + } + } + } + + // True if we found the pdf plugin. Needed since only official builders have + // the pdf plugin, so for the rest, and for other devs, we don't want the test + // to fail. + bool have_plugin_; + // True if the snapshot differed from the expected value. + bool snapshot_different_; + // Internal variable used to synchronize to the renderer. + int next_dummy_search_value_; + // The filename of the bitmap to compare the snapshot to. + std::string expected_filename_; + // If the snapshot is different, holds the location where it's saved. + FilePath snapshot_filename_; +}; + +// Tests basic PDF rendering. This can be broken depending on bad merges with +// the vendor, so it's important that we have basic sanity checking. +IN_PROC_BROWSER_TEST_F(PDFBrowserTest, Basic) { + if (!have_plugin()) + return; + + ASSERT_NO_FATAL_FAILURE(Load()); + ASSERT_NO_FATAL_FAILURE(WaitForResponse()); + ASSERT_NO_FATAL_FAILURE(VerifySnapshot("pdf_browsertest.png")); +} + +// Tests that scrolling works. +IN_PROC_BROWSER_TEST_F(PDFBrowserTest, Scroll) { + if (!have_plugin()) + return; + + ASSERT_NO_FATAL_FAILURE(Load()); + + // We use wheel mouse event since that's the only one we can easily push to + // the renderer. There's no way to push a cross-platform keyboard event at + // the moment. + WebKit::WebMouseWheelEvent wheel_event; + wheel_event.type = WebKit::WebInputEvent::MouseWheel; + wheel_event.deltaY = -200; + wheel_event.wheelTicksY = -2; + TabContents* tab_contents = browser()->GetSelectedTabContents(); + tab_contents->render_view_host()->ForwardWheelEvent(wheel_event); + ASSERT_NO_FATAL_FAILURE(WaitForResponse()); + ASSERT_NO_FATAL_FAILURE(VerifySnapshot("pdf_browsertest_scroll.png")); +} + +IN_PROC_BROWSER_TEST_F(PDFBrowserTest, FindAndCopy) { + if (!have_plugin()) + return; + + ASSERT_NO_FATAL_FAILURE(Load()); + // Verifies that find in page works. + ASSERT_EQ(3, ui_test_utils::FindInPage( + browser()->GetSelectedTabContents(), UTF8ToUTF16("adipiscing"), true, + false, NULL)); + + // Verify that copying selected text works. + Clipboard clipboard; + // Reset the clipboard first. + Clipboard::ObjectMap objects; + Clipboard::ObjectMapParams params; + params.push_back(std::vector<char>()); + objects[Clipboard::CBF_TEXT] = params; + clipboard.WriteObjects(objects); + + browser()->GetSelectedTabContents()->render_view_host()->Copy(); + ASSERT_NO_FATAL_FAILURE(WaitForResponse()); + + std::string text; + clipboard.ReadAsciiText(Clipboard::BUFFER_STANDARD, &text); + ASSERT_EQ("adipiscing", text); +} + +} // namespace |