summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--chrome/browser/printing/print_preview_message_handler.cc52
-rw-r--r--chrome/browser/printing/print_preview_message_handler.h4
-rw-r--r--chrome/browser/resources/print_preview/print_preview.js76
-rw-r--r--chrome/browser/ui/webui/print_preview_handler.cc13
-rw-r--r--chrome/browser/ui/webui/print_preview_ui.cc44
-rw-r--r--chrome/browser/ui/webui/print_preview_ui.h25
-rw-r--r--chrome/common/print_messages.h15
-rw-r--r--chrome/renderer/mock_render_thread.cc13
-rw-r--r--chrome/renderer/mock_render_thread.h7
-rw-r--r--chrome/renderer/print_web_view_helper.cc19
-rw-r--r--chrome/renderer/print_web_view_helper.h8
-rw-r--r--chrome/renderer/print_web_view_helper_browsertest.cc27
-rw-r--r--chrome/renderer/print_web_view_helper_linux.cc40
-rw-r--r--chrome/renderer/print_web_view_helper_mac.mm15
-rw-r--r--chrome/renderer/print_web_view_helper_win.cc18
15 files changed, 314 insertions, 62 deletions
diff --git a/chrome/browser/printing/print_preview_message_handler.cc b/chrome/browser/printing/print_preview_message_handler.cc
index 99714cf..c91a143 100644
--- a/chrome/browser/printing/print_preview_message_handler.cc
+++ b/chrome/browser/printing/print_preview_message_handler.cc
@@ -4,6 +4,8 @@
#include "chrome/browser/printing/print_preview_message_handler.h"
+#include <vector>
+
#include "base/memory/ref_counted.h"
#include "chrome/browser/browser_process.h"
#include "chrome/browser/printing/background_printing_manager.h"
@@ -61,6 +63,35 @@ void PrintPreviewMessageHandler::OnRequestPrintPreview() {
PrintPreviewTabController::PrintPreview(tab_contents());
}
+void PrintPreviewMessageHandler::OnDidGetPreviewPageCount(int page_count) {
+ if (page_count <= 0)
+ return;
+ TabContents* print_preview_tab = GetPrintPreviewTab();
+ if (!print_preview_tab)
+ return;
+
+ PrintPreviewUI* print_preview_ui =
+ static_cast<PrintPreviewUI*>(print_preview_tab->web_ui());
+ print_preview_ui->OnDidGetPreviewPageCount(page_count);
+}
+
+void PrintPreviewMessageHandler::OnDidPreviewPage(int page_number,
+ bool* cancel) {
+ TabContents* print_preview_tab = GetPrintPreviewTab();
+ if (!print_preview_tab) {
+ // Can't find print preview tab means we should cancel.
+ *cancel = true;
+ return;
+ }
+
+ PrintPreviewUI* print_preview_ui =
+ static_cast<PrintPreviewUI*>(print_preview_tab->web_ui());
+ bool has_pending = print_preview_ui->HasPendingRequests();
+ if (!has_pending && page_number >= 0)
+ print_preview_ui->OnDidPreviewPage(page_number);
+ *cancel = has_pending;
+}
+
void PrintPreviewMessageHandler::OnPagesReadyForPreview(
const PrintHostMsg_DidPreviewDocument_Params& params) {
// Always need to stop the worker and send PrintMsg_PrintingDone.
@@ -135,20 +166,39 @@ void PrintPreviewMessageHandler::OnPrintPreviewFailed(int document_cookie) {
} else {
PrintPreviewUI* print_preview_ui =
static_cast<PrintPreviewUI*>(print_preview_tab->web_ui());
- print_preview_ui->CallJavascriptFunction("printPreviewFailed");
+ print_preview_ui->OnPrintPreviewFailed();
}
}
+void PrintPreviewMessageHandler::OnPrintPreviewCancelled(int document_cookie) {
+ // Always need to stop the worker.
+ StopWorker(document_cookie);
+
+ TabContents* print_preview_tab = GetPrintPreviewTab();
+ if (!print_preview_tab)
+ return;
+
+ PrintPreviewUI* print_preview_ui =
+ static_cast<PrintPreviewUI*>(print_preview_tab->web_ui());
+ print_preview_ui->OnPrintPreviewCancelled();
+}
+
bool PrintPreviewMessageHandler::OnMessageReceived(
const IPC::Message& message) {
bool handled = true;
IPC_BEGIN_MESSAGE_MAP(PrintPreviewMessageHandler, message)
IPC_MESSAGE_HANDLER(PrintHostMsg_RequestPrintPreview,
OnRequestPrintPreview)
+ IPC_MESSAGE_HANDLER(PrintHostMsg_DidGetPreviewPageCount,
+ OnDidGetPreviewPageCount)
+ IPC_MESSAGE_HANDLER(PrintHostMsg_DidPreviewPage,
+ OnDidPreviewPage)
IPC_MESSAGE_HANDLER(PrintHostMsg_PagesReadyForPreview,
OnPagesReadyForPreview)
IPC_MESSAGE_HANDLER(PrintHostMsg_PrintPreviewFailed,
OnPrintPreviewFailed)
+ IPC_MESSAGE_HANDLER(PrintHostMsg_PrintPreviewCancelled,
+ OnPrintPreviewCancelled)
IPC_MESSAGE_UNHANDLED(handled = false)
IPC_END_MESSAGE_MAP()
return handled;
diff --git a/chrome/browser/printing/print_preview_message_handler.h b/chrome/browser/printing/print_preview_message_handler.h
index 6591bc7..1421de9 100644
--- a/chrome/browser/printing/print_preview_message_handler.h
+++ b/chrome/browser/printing/print_preview_message_handler.h
@@ -30,9 +30,13 @@ class PrintPreviewMessageHandler : public TabContentsObserver {
// Message handlers.
void OnRequestPrintPreview();
+ void OnDidGetPreviewPageCount(int page_count);
+ // |page_number| is 0-based.
+ void OnDidPreviewPage(int page_number, bool* cancel);
void OnPagesReadyForPreview(
const PrintHostMsg_DidPreviewDocument_Params& params);
void OnPrintPreviewFailed(int document_cookie);
+ void OnPrintPreviewCancelled(int document_cookie);
DISALLOW_COPY_AND_ASSIGN(PrintPreviewMessageHandler);
};
diff --git a/chrome/browser/resources/print_preview/print_preview.js b/chrome/browser/resources/print_preview/print_preview.js
index 66bdcb3..1e57797 100644
--- a/chrome/browser/resources/print_preview/print_preview.js
+++ b/chrome/browser/resources/print_preview/print_preview.js
@@ -599,57 +599,87 @@ function onPDFLoad() {
}
/**
+ * Update the page count and check the page range.
+ * Called from PrintPreviewUI::OnDidGetPreviewPageCount().
+ * @param {number} pageCount The number of pages.
+ */
+function onDidGetPreviewPageCount(pageCount) {
+ totalPageCount = pageCount;
+
+ if (!isSelectedPagesValid())
+ pageRangesFieldChanged();
+}
+
+/**
+ * Notification that a print preview page has been rendered.
+ * Check if the settings have changed and request a regeneration if needed.
+ * Called from PrintPreviewUI::OnDidPreviewPage().
+ * @param {number} pageNumber The page number, 0-based.
+ */
+function onDidPreviewPage(pageNumber) {
+ if (checkIfSettingsChangedAndRegeneratePreview())
+ return;
+ // TODO(thestig) Make use of |pageNumber| for pipelined preview generation.
+}
+
+/**
* Update the print preview when new preview data is available.
* Create the PDF plugin as needed.
* Called from PrintPreviewUI::PreviewDataIsAvailable().
- * @param {number} pageCount The expected total pages count.
* @param {string} jobTitle The print job title.
* @param {boolean} modifiable If the preview is modifiable.
* @param {string} previewUid Preview unique identifier.
*/
-function updatePrintPreview(pageCount, jobTitle, modifiable, previewUid) {
- var tempPrintSettings = new PrintSettings();
- tempPrintSettings.save();
+function updatePrintPreview(jobTitle, modifiable, previewUid) {
+ hasPendingPreviewRequest = false;
+
+ if (checkIfSettingsChangedAndRegeneratePreview())
+ return;
previewModifiable = modifiable;
+ document.title = localStrings.getStringF('printPreviewTitleFormat', jobTitle);
- hasPendingPreviewRequest = false;
+ createPDFPlugin(previewUid);
+ updatePrintSummary();
+ updatePrintButtonState();
+ addEventListeners();
- if (!totalPageCount)
- totalPageCount = pageCount;
+ if (hasPendingPrintFileRequest)
+ printPendingFile();
+}
+
+/**
+ * Check if any print settings changed and regenerate the preview if needed.
+ * @return {boolean} true if a new preview is required.
+ */
+function checkIfSettingsChangedAndRegeneratePreview() {
+ var tempPrintSettings = new PrintSettings();
+ tempPrintSettings.save();
- if (previouslySelectedPages.length == 0)
- for (var i = 0; i < totalPageCount; i++)
+ if (previouslySelectedPages.length == 0) {
+ for (var i = 0; i < totalPageCount; i++) {
previouslySelectedPages.push(i+1);
+ }
+ }
if (printSettings.deviceName != tempPrintSettings.deviceName) {
updateControlsWithSelectedPrinterCapabilities();
- return;
+ return true;
} else if (printSettings.isLandscape != tempPrintSettings.isLandscape) {
setDefaultValuesAndRegeneratePreview();
- return;
+ return true;
} else if (isSelectedPagesValid()) {
var currentlySelectedPages = getSelectedPagesSet();
if (!areArraysEqual(previouslySelectedPages, currentlySelectedPages)) {
previouslySelectedPages = currentlySelectedPages;
requestPrintPreview();
- return;
+ return true;
}
}
if (!isSelectedPagesValid())
pageRangesFieldChanged();
-
- // Update the current tab title.
- document.title = localStrings.getStringF('printPreviewTitleFormat', jobTitle);
-
- createPDFPlugin(previewUid);
- updatePrintSummary();
- updatePrintButtonState();
- addEventListeners();
-
- if (hasPendingPrintFileRequest)
- printPendingFile();
+ return false;
}
/**
diff --git a/chrome/browser/ui/webui/print_preview_handler.cc b/chrome/browser/ui/webui/print_preview_handler.cc
index 8a141e6..55ffe15 100644
--- a/chrome/browser/ui/webui/print_preview_handler.cc
+++ b/chrome/browser/ui/webui/print_preview_handler.cc
@@ -430,22 +430,25 @@ void PrintPreviewHandler::HandleGetPrinters(const ListValue*) {
}
void PrintPreviewHandler::HandleGetPreview(const ListValue* args) {
+ scoped_ptr<DictionaryValue> settings(GetSettingsDictionary(args));
+ if (!settings.get())
+ return;
+
// Increment request count.
++regenerate_preview_request_count_;
+ PrintPreviewUI* print_preview_ui = static_cast<PrintPreviewUI*>(web_ui_);
+ print_preview_ui->OnPrintPreviewRequest();
+
TabContents* initiator_tab = GetInitiatorTab();
if (!initiator_tab) {
if (!reported_failed_preview_) {
ReportUserActionHistogram(PREVIEW_FAILED);
reported_failed_preview_ = true;
}
- web_ui_->CallJavascriptFunction("printPreviewFailed");
+ print_preview_ui->OnPrintPreviewFailed();
return;
}
- scoped_ptr<DictionaryValue> settings(GetSettingsDictionary(args));
- if (!settings.get())
- return;
-
VLOG(1) << "Print preview request start";
RenderViewHost* rvh = initiator_tab->render_view_host();
rvh->Send(new PrintMsg_PrintPreview(rvh->routing_id(), *settings));
diff --git a/chrome/browser/ui/webui/print_preview_ui.cc b/chrome/browser/ui/webui/print_preview_ui.cc
index 339a506..e5efdfa 100644
--- a/chrome/browser/ui/webui/print_preview_ui.cc
+++ b/chrome/browser/ui/webui/print_preview_ui.cc
@@ -15,7 +15,8 @@
PrintPreviewUI::PrintPreviewUI(TabContents* contents)
: ChromeWebUI(contents),
- initial_preview_start_time_(base::TimeTicks::Now()) {
+ initial_preview_start_time_(base::TimeTicks::Now()),
+ request_count_(0U) {
// WebUI owns |handler_|.
handler_ = new PrintPreviewHandler();
AddMessageHandler(handler_->Attach(this));
@@ -49,11 +50,29 @@ void PrintPreviewUI::OnInitiatorTabClosed(
CallJavascriptFunction("onInitiatorTabClosed", initiator_tab_url);
}
+void PrintPreviewUI::OnPrintPreviewRequest() {
+ request_count_++;
+}
+
+void PrintPreviewUI::OnDidGetPreviewPageCount(int page_count) {
+ DCHECK_GT(page_count, 0);
+ FundamentalValue count(page_count);
+ CallJavascriptFunction("onDidGetPreviewPageCount", count);
+}
+
+void PrintPreviewUI::OnDidPreviewPage(int page_number) {
+ DCHECK_GE(page_number, 0);
+ FundamentalValue number(page_number);
+ CallJavascriptFunction("onDidPreviewPage", number);
+}
+
void PrintPreviewUI::OnPreviewDataIsAvailable(int expected_pages_count,
const string16& job_title,
bool modifiable) {
VLOG(1) << "Print preview request finished with "
<< expected_pages_count << " pages";
+ DecrementRequestCount();
+
if (!initial_preview_start_time_.is_null()) {
UMA_HISTOGRAM_TIMES("PrintPreview.InitalDisplayTime",
base::TimeTicks::Now() - initial_preview_start_time_);
@@ -65,8 +84,8 @@ void PrintPreviewUI::OnPreviewDataIsAvailable(int expected_pages_count,
StringValue title(job_title);
FundamentalValue is_preview_modifiable(modifiable);
StringValue ui_identifier(preview_ui_addr_str_);
- CallJavascriptFunction("updatePrintPreview", pages_count, title,
- is_preview_modifiable, ui_identifier);
+ CallJavascriptFunction("updatePrintPreview", title, is_preview_modifiable,
+ ui_identifier);
}
void PrintPreviewUI::OnNavigation() {
@@ -77,6 +96,25 @@ void PrintPreviewUI::OnFileSelectionCancelled() {
CallJavascriptFunction("fileSelectionCancelled");
}
+void PrintPreviewUI::OnPrintPreviewFailed() {
+ DecrementRequestCount();
+ CallJavascriptFunction("printPreviewFailed");
+}
+
+void PrintPreviewUI::OnPrintPreviewCancelled() {
+ DecrementRequestCount();
+}
+
+bool PrintPreviewUI::HasPendingRequests() {
+ return request_count_ > 1;
+}
+
PrintPreviewDataService* PrintPreviewUI::print_preview_data_service() {
return PrintPreviewDataService::GetInstance();
}
+
+void PrintPreviewUI::DecrementRequestCount() {
+ DCHECK_GT(request_count_, 0U);
+ if (request_count_ > 0)
+ request_count_--;
+}
diff --git a/chrome/browser/ui/webui/print_preview_ui.h b/chrome/browser/ui/webui/print_preview_ui.h
index 7637801..f2d44ce 100644
--- a/chrome/browser/ui/webui/print_preview_ui.h
+++ b/chrome/browser/ui/webui/print_preview_ui.h
@@ -30,6 +30,17 @@ class PrintPreviewUI : public ChromeWebUI {
// Sets the print preview |data|.
void SetPrintPreviewData(const RefCountedBytes* data);
+ // Notify the Web UI that there is a print preview request.
+ // There should be a matching call to OnPreviewDataIsAvailable() or
+ // OnPrintPreviewFailed().
+ void OnPrintPreviewRequest();
+
+ // Notify the Web UI that the print preview will have |page_count| pages.
+ void OnDidGetPreviewPageCount(int page_count);
+
+ // Notify the Web UI that the 0-based page |page_number| has been rendered.
+ void OnDidPreviewPage(int page_number);
+
// Notify the Web UI renderer that preview data is available.
// |expected_pages_count| specifies the total number of pages.
// |job_title| is the title of the page being previewed.
@@ -44,6 +55,12 @@ class PrintPreviewUI : public ChromeWebUI {
// erased.
void OnNavigation();
+ // Notify the Web UI that the print preview failed to render.
+ void OnPrintPreviewFailed();
+
+ // Notify the Web UI that the print preview request has been cancelled.
+ void OnPrintPreviewCancelled();
+
// Notify the Web UI that initiator tab is closed, so we can disable all
// the controls that need the initiator tab for generating the preview data.
// |initiator_tab_url| is passed in order to display a more accurate error
@@ -53,10 +70,15 @@ class PrintPreviewUI : public ChromeWebUI {
// Notify the Web UI renderer that file selection has been cancelled.
void OnFileSelectionCancelled();
+ // Return true if there are pending requests.
+ bool HasPendingRequests();
+
private:
// Helper function
PrintPreviewDataService* print_preview_data_service();
+ void DecrementRequestCount();
+
base::TimeTicks initial_preview_start_time_;
// Store the PrintPreviewUI address string.
@@ -65,6 +87,9 @@ class PrintPreviewUI : public ChromeWebUI {
// Weak pointer to the WebUI handler.
PrintPreviewHandler* handler_;
+ // The number of print preview requests in flight.
+ uint32 request_count_;
+
DISALLOW_COPY_AND_ASSIGN(PrintPreviewUI);
};
diff --git a/chrome/common/print_messages.h b/chrome/common/print_messages.h
index ec825a5..0c8c48a 100644
--- a/chrome/common/print_messages.h
+++ b/chrome/common/print_messages.h
@@ -228,6 +228,17 @@ IPC_MESSAGE_CONTROL1(PrintHostMsg_TempFileForPrintingWritten,
// Asks the browser to do print preview.
IPC_MESSAGE_ROUTED0(PrintHostMsg_RequestPrintPreview)
+// Notify the browser the number of pages in the print preview document.
+IPC_MESSAGE_ROUTED1(PrintHostMsg_DidGetPreviewPageCount,
+ int /* page count */)
+
+// Notify the browser a print preview page has been rendered. Give the browser
+// a chance to cancel the print preview as needed. Page number is zero-based,
+// and can be -1 if it is just a check.
+IPC_SYNC_MESSAGE_ROUTED1_1(PrintHostMsg_DidPreviewPage,
+ int /* page number */,
+ bool /* print preview cancelled */)
+
// Sends back to the browser the rendered "printed document" for preview that
// was requested by a PrintMsg_PrintPreview message. The memory handle in this
// message is already valid in the browser process.
@@ -241,3 +252,7 @@ IPC_MESSAGE_ROUTED1(PrintHostMsg_PrintingFailed,
// Tell the browser print preview failed.
IPC_MESSAGE_ROUTED1(PrintHostMsg_PrintPreviewFailed,
int /* document cookie */)
+
+// Tell the browser print preview was cancelled.
+IPC_MESSAGE_ROUTED1(PrintHostMsg_PrintPreviewCancelled,
+ int /* document cookie */)
diff --git a/chrome/renderer/mock_render_thread.cc b/chrome/renderer/mock_render_thread.cc
index de3daef..2535ff3 100644
--- a/chrome/renderer/mock_render_thread.cc
+++ b/chrome/renderer/mock_render_thread.cc
@@ -24,7 +24,8 @@ MockRenderThread::MockRenderThread()
widget_(NULL),
reply_deserializer_(NULL),
printer_(new MockPrinter),
- print_dialog_user_response_(true) {
+ print_dialog_user_response_(true),
+ cancel_print_preview_(false) {
}
MockRenderThread::~MockRenderThread() {
@@ -109,6 +110,8 @@ bool MockRenderThread::OnMessageReceived(const IPC::Message& msg) {
IPC_MESSAGE_HANDLER(PrintHostMsg_DidGetPrintedPagesCount,
OnDidGetPrintedPagesCount)
IPC_MESSAGE_HANDLER(PrintHostMsg_DidPrintPage, OnDidPrintPage)
+ IPC_MESSAGE_HANDLER(PrintHostMsg_DidPreviewPage,
+ OnDidPreviewPage)
#if defined(OS_WIN)
IPC_MESSAGE_HANDLER(PrintHostMsg_DuplicateSection, OnDuplicateSection)
#endif
@@ -209,6 +212,10 @@ void MockRenderThread::OnDidPrintPage(
printer_->PrintPage(params);
}
+void MockRenderThread::OnDidPreviewPage(int page_number, bool* cancel) {
+ *cancel = cancel_print_preview_;
+}
+
void MockRenderThread::OnUpdatePrintSettings(
int document_cookie,
const DictionaryValue& job_settings,
@@ -234,3 +241,7 @@ void MockRenderThread::OnUpdatePrintSettings(
void MockRenderThread::set_print_dialog_user_response(bool response) {
print_dialog_user_response_ = response;
}
+
+void MockRenderThread::set_cancel_print_preview(bool cancel) {
+ cancel_print_preview_ = cancel;
+}
diff --git a/chrome/renderer/mock_render_thread.h b/chrome/renderer/mock_render_thread.h
index 3be3134..3b359cf 100644
--- a/chrome/renderer/mock_render_thread.h
+++ b/chrome/renderer/mock_render_thread.h
@@ -83,6 +83,9 @@ class MockRenderThread : public RenderThreadBase {
// False if the user decides to cancel.
void set_print_dialog_user_response(bool response);
+ // Set to true to simulate canceling of a print preview.
+ void set_cancel_print_preview(bool cancel);
+
private:
// This function operates as a regular IPC listener.
bool OnMessageReceived(const IPC::Message& msg);
@@ -121,6 +124,7 @@ class MockRenderThread : public RenderThreadBase {
void OnDidGetPrintedPagesCount(int cookie, int number_pages);
void OnDidPrintPage(const PrintHostMsg_DidPrintPage_Params& params);
+ void OnDidPreviewPage(int page_number, bool* cancel);
// For print preview, PrintWebViewHelper will update settings.
void OnUpdatePrintSettings(int document_cookie,
@@ -147,6 +151,9 @@ class MockRenderThread : public RenderThreadBase {
// True to simulate user clicking print. False to cancel.
bool print_dialog_user_response_;
+
+ // True to simulate cancelling a print preview.
+ bool cancel_print_preview_;
};
#endif // CHROME_RENDERER_MOCK_RENDER_THREAD_H_
diff --git a/chrome/renderer/print_web_view_helper.cc b/chrome/renderer/print_web_view_helper.cc
index 8fcfd08..a918de7 100644
--- a/chrome/renderer/print_web_view_helper.cc
+++ b/chrome/renderer/print_web_view_helper.cc
@@ -398,7 +398,11 @@ void PrintWebViewHelper::DidFinishPrinting(PrintingResult result) {
}
} else if (result == FAIL_PREVIEW) {
int cookie = print_pages_params_->params.document_cookie;
- Send(new PrintHostMsg_PrintPreviewFailed(routing_id(), cookie));
+ if (notify_browser_of_print_failure_) {
+ Send(new PrintHostMsg_PrintPreviewFailed(routing_id(), cookie));
+ } else {
+ Send(new PrintHostMsg_PrintPreviewCancelled(routing_id(), cookie));
+ }
}
if (print_web_view_) {
@@ -449,12 +453,11 @@ bool PrintWebViewHelper::PrintPages(const PrintMsg_PrintPages_Params& params,
node,
frame->view());
int page_count = prep_frame_view.GetExpectedPageCount();
-
+ if (!page_count)
+ return false;
Send(new PrintHostMsg_DidGetPrintedPagesCount(routing_id(),
printParams.document_cookie,
page_count));
- if (!page_count)
- return false;
const gfx::Size& canvas_size = prep_frame_view.GetPrintCanvasSize();
PrintMsg_PrintPage_Params page_params;
@@ -804,3 +807,11 @@ void PrintWebViewHelper::RequestPrintPreview() {
old_print_pages_params_.reset();
Send(new PrintHostMsg_RequestPrintPreview(routing_id()));
}
+
+bool PrintWebViewHelper::PreviewPageRendered(int page_number) {
+ bool cancel = false;
+ Send(new PrintHostMsg_DidPreviewPage(routing_id(), page_number, &cancel));
+ if (cancel)
+ notify_browser_of_print_failure_ = false;
+ return !cancel;
+}
diff --git a/chrome/renderer/print_web_view_helper.h b/chrome/renderer/print_web_view_helper.h
index d477cc0..ba0d9e5 100644
--- a/chrome/renderer/print_web_view_helper.h
+++ b/chrome/renderer/print_web_view_helper.h
@@ -82,6 +82,7 @@ class PrintWebViewHelper : public RenderViewObserver,
BlockScriptInitiatedPrinting);
FRIEND_TEST_ALL_PREFIXES(PrintWebViewHelperTest, OnPrintPages);
FRIEND_TEST_ALL_PREFIXES(PrintWebViewHelperPreviewTest, OnPrintPreview);
+ FRIEND_TEST_ALL_PREFIXES(PrintWebViewHelperPreviewTest, OnPrintPreviewCancel);
FRIEND_TEST_ALL_PREFIXES(PrintWebViewHelperPreviewTest, OnPrintPreviewFail);
FRIEND_TEST_ALL_PREFIXES(PrintWebViewHelperPreviewTest,
OnPrintForPrintPreview);
@@ -197,7 +198,6 @@ class PrintWebViewHelper : public RenderViewObserver,
bool RenderPages(const PrintMsg_PrintPages_Params& params,
WebKit::WebFrame* frame,
WebKit::WebNode* node,
- bool send_expected_page_count,
int* page_count,
printing::Metafile* metafile,
bool is_preview);
@@ -255,6 +255,12 @@ class PrintWebViewHelper : public RenderViewObserver,
void RequestPrintPreview();
+ // Called every time print preview renders a page. Notify the browser of the
+ // event and check if print preview should be cancelled. Returns false if
+ // print preview has been cancelled. |page_number| is 0-based, or negative to
+ // indicate its a cancel check only.
+ bool PreviewPageRendered(int page_number);
+
WebKit::WebView* print_web_view_;
// The frame to print for script initiated print preview.
diff --git a/chrome/renderer/print_web_view_helper_browsertest.cc b/chrome/renderer/print_web_view_helper_browsertest.cc
index 4ca40a4..1dd8e51 100644
--- a/chrome/renderer/print_web_view_helper_browsertest.cc
+++ b/chrome/renderer/print_web_view_helper_browsertest.cc
@@ -310,6 +310,13 @@ class PrintWebViewHelperPreviewTest : public PrintWebViewHelperTestBase {
}
protected:
+ void VerifyPrintPreviewCancelled(bool did_cancel) {
+ bool print_preview_cancelled =
+ (render_thread_.sink().GetUniqueMessageMatching(
+ PrintHostMsg_PrintPreviewCancelled::ID) != NULL);
+ EXPECT_EQ(did_cancel, print_preview_cancelled);
+ }
+
void VerifyPrintPreviewFailed(bool did_fail) {
bool print_preview_failed = (render_thread_.sink().GetUniqueMessageMatching(
PrintHostMsg_PrintPreviewFailed::ID) != NULL);
@@ -350,11 +357,30 @@ TEST_F(PrintWebViewHelperPreviewTest, OnPrintPreview) {
CreatePrintSettingsDictionary(&dict);
PrintWebViewHelper::Get(view_)->OnPrintPreview(dict);
+ VerifyPrintPreviewCancelled(false);
VerifyPrintPreviewFailed(false);
VerifyPrintPreviewGenerated(true);
VerifyPagesPrinted(false);
}
+// Tests that cancelling a print preview works correctly.
+TEST_F(PrintWebViewHelperPreviewTest, OnPrintPreviewCancel) {
+ LoadHTML(kPrintPreviewHTML);
+
+ // Cancel the print preview.
+ render_thread_.set_cancel_print_preview(true);
+
+ // Fill in some dummy values.
+ DictionaryValue dict;
+ CreatePrintSettingsDictionary(&dict);
+ PrintWebViewHelper::Get(view_)->OnPrintPreview(dict);
+
+ VerifyPrintPreviewCancelled(true);
+ VerifyPrintPreviewFailed(false);
+ VerifyPrintPreviewGenerated(false);
+ VerifyPagesPrinted(false);
+}
+
// Tests that print preview fails and receiving error messages through
// that channel all works.
TEST_F(PrintWebViewHelperPreviewTest, OnPrintPreviewFail) {
@@ -364,6 +390,7 @@ TEST_F(PrintWebViewHelperPreviewTest, OnPrintPreviewFail) {
DictionaryValue empty_dict;
PrintWebViewHelper::Get(view_)->OnPrintPreview(empty_dict);
+ VerifyPrintPreviewCancelled(false);
VerifyPrintPreviewFailed(true);
VerifyPrintPreviewGenerated(false);
VerifyPagesPrinted(false);
diff --git a/chrome/renderer/print_web_view_helper_linux.cc b/chrome/renderer/print_web_view_helper_linux.cc
index ebbea61..9255a00 100644
--- a/chrome/renderer/print_web_view_helper_linux.cc
+++ b/chrome/renderer/print_web_view_helper_linux.cc
@@ -28,15 +28,16 @@ using WebKit::WebNode;
bool PrintWebViewHelper::CreatePreviewDocument(
const PrintMsg_PrintPages_Params& params, WebKit::WebFrame* frame,
WebKit::WebNode* node) {
- preview_page_count_ = 0;
+ if (!PreviewPageRendered(-1))
+ return false;
+
printing::PreviewMetafile metafile;
if (!metafile.Init())
return false;
- if (!RenderPages(params, frame, node, false, &preview_page_count_,
- &metafile, true)) {
+ preview_page_count_ = 0;
+ if (!RenderPages(params, frame, node, &preview_page_count_, &metafile, true))
return false;
- }
// Get the size of the resulting metafile.
uint32 buf_size = metafile.GetDataSize();
@@ -60,22 +61,13 @@ bool PrintWebViewHelper::CreatePreviewDocument(
bool PrintWebViewHelper::PrintPages(const PrintMsg_PrintPages_Params& params,
WebFrame* frame,
WebNode* node) {
- int page_count = 0;
- bool send_expected_page_count =
-#if defined(OS_CHROMEOS)
- false;
-#else
- true;
-#endif // defined(OS_CHROMEOS)
-
printing::NativeMetafile metafile;
if (!metafile.Init())
return false;
- if (!RenderPages(params, frame, node, send_expected_page_count, &page_count,
- &metafile, false)) {
+ int page_count = 0;
+ if (!RenderPages(params, frame, node, &page_count, &metafile, false))
return false;
- }
// Get the size of the resulting metafile.
uint32 buf_size = metafile.GetDataSize();
@@ -148,7 +140,6 @@ bool PrintWebViewHelper::PrintPages(const PrintMsg_PrintPages_Params& params,
bool PrintWebViewHelper::RenderPages(const PrintMsg_PrintPages_Params& params,
WebKit::WebFrame* frame,
WebKit::WebNode* node,
- bool send_expected_page_count,
int* page_count,
printing::Metafile* metafile,
bool is_preview) {
@@ -158,14 +149,21 @@ bool PrintWebViewHelper::RenderPages(const PrintMsg_PrintPages_Params& params,
PrepareFrameAndViewForPrint prep_frame_view(printParams, frame, node,
frame->view());
+ if (is_preview && !PreviewPageRendered(-1))
+ return false;
+
*page_count = prep_frame_view.GetExpectedPageCount();
- if (send_expected_page_count) {
+ if (!*page_count)
+ return false;
+ if (is_preview) {
+ Send(new PrintHostMsg_DidGetPreviewPageCount(routing_id(), *page_count));
+ } else {
+#if !defined(OS_CHROMEOS)
Send(new PrintHostMsg_DidGetPrintedPagesCount(routing_id(),
printParams.document_cookie,
*page_count));
+#endif
}
- if (!*page_count)
- return false;
base::TimeTicks begin_time = base::TimeTicks::Now();
base::TimeTicks page_begin_time = begin_time;
@@ -179,6 +177,8 @@ bool PrintWebViewHelper::RenderPages(const PrintMsg_PrintPages_Params& params,
PrintPageInternal(page_params, canvas_size, frame, metafile);
if (is_preview) {
page_begin_time = ReportPreviewPageRenderTime(page_begin_time);
+ if (!PreviewPageRendered(i))
+ return false;
}
}
} else {
@@ -187,6 +187,8 @@ bool PrintWebViewHelper::RenderPages(const PrintMsg_PrintPages_Params& params,
PrintPageInternal(page_params, canvas_size, frame, metafile);
if (is_preview) {
page_begin_time = ReportPreviewPageRenderTime(page_begin_time);
+ if (!PreviewPageRendered(params.pages[i]))
+ return false;
}
}
}
diff --git a/chrome/renderer/print_web_view_helper_mac.mm b/chrome/renderer/print_web_view_helper_mac.mm
index aab653d..54521ff 100644
--- a/chrome/renderer/print_web_view_helper_mac.mm
+++ b/chrome/renderer/print_web_view_helper_mac.mm
@@ -62,15 +62,22 @@ void PrintWebViewHelper::PrintPageInternal(
bool PrintWebViewHelper::CreatePreviewDocument(
const PrintMsg_PrintPages_Params& params, WebKit::WebFrame* frame,
WebKit::WebNode* node) {
+ if (!PreviewPageRendered(-1))
+ return false;
+
PrintMsg_Print_Params printParams = params.params;
UpdatePrintableSizeInPrintParameters(frame, node, &printParams);
PrepareFrameAndViewForPrint prep_frame_view(printParams,
frame, node, frame->view());
- preview_page_count_ = prep_frame_view.GetExpectedPageCount();
+ if (!PreviewPageRendered(-1))
+ return false;
+ preview_page_count_ = prep_frame_view.GetExpectedPageCount();
if (!preview_page_count_)
return false;
+ Send(new PrintHostMsg_DidGetPreviewPageCount(routing_id(),
+ preview_page_count_));
printing::PreviewMetafile metafile;
if (!metafile.Init())
@@ -89,14 +96,18 @@ bool PrintWebViewHelper::CreatePreviewDocument(
RenderPage(printParams.page_size, content_area, scale_factor, i, frame,
&metafile);
page_begin_time = ReportPreviewPageRenderTime(page_begin_time);
+ if (!PreviewPageRendered(i))
+ return false;
}
} else {
for (size_t i = 0; i < params.pages.size(); ++i) {
if (params.pages[i] >= preview_page_count_)
break;
RenderPage(printParams.page_size, content_area, scale_factor,
- static_cast<int>(params.pages[i]), frame, &metafile);
+ params.pages[i], frame, &metafile);
page_begin_time = ReportPreviewPageRenderTime(page_begin_time);
+ if (!PreviewPageRendered(params.pages[i]))
+ return false;
}
}
diff --git a/chrome/renderer/print_web_view_helper_win.cc b/chrome/renderer/print_web_view_helper_win.cc
index 5514780..9528797 100644
--- a/chrome/renderer/print_web_view_helper_win.cc
+++ b/chrome/renderer/print_web_view_helper_win.cc
@@ -5,9 +5,9 @@
#include "chrome/renderer/print_web_view_helper.h"
#include "base/logging.h"
+#include "base/memory/scoped_ptr.h"
#include "base/metrics/histogram.h"
#include "base/process_util.h"
-#include "base/scoped_ptr.h"
#include "chrome/common/print_messages.h"
#include "printing/metafile.h"
#include "printing/metafile_impl.h"
@@ -126,13 +126,21 @@ void PrintWebViewHelper::PrintPageInternal(
bool PrintWebViewHelper::CreatePreviewDocument(
const PrintMsg_PrintPages_Params& params, WebKit::WebFrame* frame,
WebKit::WebNode* node) {
+ if (!PreviewPageRendered(-1))
+ return false;
+
PrintMsg_Print_Params print_params = params.params;
UpdatePrintableSizeInPrintParameters(frame, node, &print_params);
PrepareFrameAndViewForPrint prep_frame_view(print_params, frame, node,
frame->view());
+ if (!PreviewPageRendered(-1))
+ return false;
+
preview_page_count_ = prep_frame_view.GetExpectedPageCount();
if (!preview_page_count_)
return false;
+ Send(new PrintHostMsg_DidGetPreviewPageCount(routing_id(),
+ preview_page_count_));
scoped_ptr<Metafile> metafile(new printing::PreviewMetafile);
metafile->Init();
@@ -149,15 +157,19 @@ bool PrintWebViewHelper::CreatePreviewDocument(
float scale_factor = shrink;
RenderPage(print_params, &scale_factor, i, true, frame, &metafile);
page_begin_time = ReportPreviewPageRenderTime(page_begin_time);
+ if (!PreviewPageRendered(i))
+ return false;
}
} else {
for (size_t i = 0; i < params.pages.size(); ++i) {
if (params.pages[i] >= preview_page_count_)
break;
float scale_factor = shrink;
- RenderPage(print_params, &scale_factor,
- static_cast<int>(params.pages[i]), true, frame, &metafile);
+ RenderPage(print_params, &scale_factor, params.pages[i], true, frame,
+ &metafile);
page_begin_time = ReportPreviewPageRenderTime(page_begin_time);
+ if (!PreviewPageRendered(params.pages[i]))
+ return false;
}
}