| Index: headless/lib/browser/headless_print_manager.cc
|
| diff --git a/headless/lib/browser/headless_print_manager.cc b/headless/lib/browser/headless_print_manager.cc
|
| index a17c5a4486f3cc2ec64a4af5d84ae67cfd8e76d9..802bc704f0c08c7de6fb3589155337ab96d90784 100644
|
| --- a/headless/lib/browser/headless_print_manager.cc
|
| +++ b/headless/lib/browser/headless_print_manager.cc
|
| @@ -8,54 +8,21 @@
|
| #include <vector>
|
|
|
| #include "base/base64.h"
|
| +#include "base/memory/ptr_util.h"
|
| +#include "base/strings/string_number_conversions.h"
|
| +#include "base/strings/string_piece.h"
|
| +#include "base/strings/string_split.h"
|
| +#include "base/strings/utf_string_conversions.h"
|
| #include "components/printing/browser/print_manager_utils.h"
|
| #include "components/printing/common/print_messages.h"
|
| #include "printing/pdf_metafile_skia.h"
|
| -#include "printing/print_settings.h"
|
| +#include "printing/print_job_constants.h"
|
| #include "printing/units.h"
|
|
|
| DEFINE_WEB_CONTENTS_USER_DATA_KEY(printing::HeadlessPrintManager);
|
|
|
| namespace printing {
|
|
|
| -namespace {
|
| -
|
| -// TODO(jzfeng): let the print settings to be configurable.
|
| -const double kTopMarginInInch = 0.25;
|
| -const double kBottomMarginInInch = 0.56;
|
| -const double kLeftMarginInInch = 0.25;
|
| -const double kRightMarginInInch = 0.25;
|
| -
|
| -PrintSettings GetDefaultPDFPrinterSettings() {
|
| -#if defined(OS_MACOSX)
|
| - // On the Mac, the printable area is in points, use kPointsPerInch to compute
|
| - // its bounds.
|
| - int dpi = kPointsPerInch;
|
| -#else
|
| - int dpi = kDefaultPdfDpi;
|
| -#endif
|
| - gfx::Size physical_size_device_units;
|
| - gfx::Rect printable_area_device_units;
|
| - double page_width_in_pixel = kLetterWidthInch * dpi;
|
| - double page_height_in_pixel = kLetterHeightInch * dpi;
|
| - physical_size_device_units.SetSize(static_cast<int>(page_width_in_pixel),
|
| - static_cast<int>(page_height_in_pixel));
|
| - printable_area_device_units.SetRect(
|
| - static_cast<int>(kLeftMarginInInch * dpi),
|
| - static_cast<int>(kTopMarginInInch * dpi),
|
| - page_width_in_pixel - (kLeftMarginInInch + kRightMarginInInch) * dpi,
|
| - page_height_in_pixel - (kTopMarginInInch + kBottomMarginInInch) * dpi);
|
| -
|
| - PrintSettings settings;
|
| - settings.set_dpi(dpi);
|
| - settings.SetPrinterPrintableArea(physical_size_device_units,
|
| - printable_area_device_units, true);
|
| - settings.set_should_print_backgrounds(true);
|
| - return settings;
|
| -}
|
| -
|
| -} // namespace
|
| -
|
| HeadlessPrintManager::HeadlessPrintManager(content::WebContents* web_contents)
|
| : PrintManager(web_contents) {
|
| Reset();
|
| @@ -84,6 +51,10 @@ std::string HeadlessPrintManager::PrintResultToString(PrintResult result) {
|
| return "Get data from metafile error";
|
| case SIMULTANEOUS_PRINT_ACTIVE:
|
| return "The previous printing job hasn't finished";
|
| + case PAGE_RANGE_SYNTAX_ERROR:
|
| + return "Page range syntax error";
|
| + case PAGE_COUNT_EXCEEDED:
|
| + return "Page range exceeds page count";
|
| default:
|
| NOTREACHED();
|
| return "Unknown PrintResult";
|
| @@ -100,7 +71,57 @@ HeadlessPrintManager::PDFContentsToDictionaryValue(const std::string& data) {
|
| return result;
|
| }
|
|
|
| +// static
|
| +HeadlessPrintManager::PageRangeStatus
|
| +HeadlessPrintManager::PageRangeTextToPages(std::string page_range_text,
|
| + int pages_count,
|
| + std::vector<int>* pages) {
|
| + PageRanges page_ranges;
|
| + for (const auto& range_string :
|
| + base::SplitStringPiece(page_range_text, ",", base::TRIM_WHITESPACE,
|
| + base::SPLIT_WANT_NONEMPTY)) {
|
| + printing::PageRange range;
|
| + if (range_string.find("-") == base::StringPiece::npos) {
|
| + if (!base::StringToInt(range_string, &range.from))
|
| + return SYNTAX_ERROR;
|
| + range.to = range.from;
|
| + } else if (range_string == "-") {
|
| + range.from = 1;
|
| + range.to = pages_count;
|
| + } else if (range_string.starts_with("-")) {
|
| + range.from = 1;
|
| + if (!base::StringToInt(range_string.substr(1), &range.to))
|
| + return SYNTAX_ERROR;
|
| + } else if (range_string.ends_with("-")) {
|
| + range.to = pages_count;
|
| + if (!base::StringToInt(range_string.substr(0, range_string.length() - 1),
|
| + &range.from))
|
| + return SYNTAX_ERROR;
|
| + } else {
|
| + auto tokens = base::SplitStringPiece(
|
| + range_string, "-", base::TRIM_WHITESPACE, base::SPLIT_WANT_NONEMPTY);
|
| + if (tokens.size() != 2 || !base::StringToInt(tokens[0], &range.from) ||
|
| + !base::StringToInt(tokens[1], &range.to))
|
| + return SYNTAX_ERROR;
|
| + }
|
| +
|
| + if (range.from < 1 || range.from > range.to)
|
| + return SYNTAX_ERROR;
|
| + if (range.to > pages_count)
|
| + return LIMIT_ERROR;
|
| +
|
| + // Page numbers are 1-based in the dictionary.
|
| + // Page numbers are 0-based for the print settings.
|
| + range.from--;
|
| + range.to--;
|
| + page_ranges.push_back(range);
|
| + }
|
| + *pages = PageRange::GetPages(page_ranges);
|
| + return NO_ERROR;
|
| +}
|
| +
|
| void HeadlessPrintManager::GetPDFContents(content::RenderFrameHost* rfh,
|
| + const HeadlessPrintSettings& settings,
|
| const GetPDFCallback& callback) {
|
| DCHECK(callback);
|
|
|
| @@ -110,9 +131,44 @@ void HeadlessPrintManager::GetPDFContents(content::RenderFrameHost* rfh,
|
| }
|
| printing_rfh_ = rfh;
|
| callback_ = callback;
|
| + print_params_ = PrintParams(settings);
|
| + page_ranges_text_ = settings.page_ranges;
|
| rfh->Send(new PrintMsg_PrintPages(rfh->GetRoutingID()));
|
| }
|
|
|
| +std::unique_ptr<PrintMsg_PrintPages_Params> HeadlessPrintManager::PrintParams(
|
| + HeadlessPrintSettings settings) {
|
| + PrintSettings print_settings;
|
| + print_settings.set_dpi(kPointsPerInch);
|
| + print_settings.set_should_print_backgrounds(
|
| + settings.should_print_backgrounds);
|
| + print_settings.set_scale_factor(settings.scale);
|
| + print_settings.SetOrientation(settings.landscape);
|
| +
|
| + print_settings.set_display_header_footer(settings.display_header_footer);
|
| + if (print_settings.display_header_footer()) {
|
| + url::Replacements<char> url_sanitizer;
|
| + url_sanitizer.ClearUsername();
|
| + url_sanitizer.ClearPassword();
|
| + std::string url = printing_rfh_->GetLastCommittedURL()
|
| + .ReplaceComponents(url_sanitizer)
|
| + .spec();
|
| + print_settings.set_url(base::UTF8ToUTF16(url));
|
| + }
|
| +
|
| + print_settings.set_margin_type(CUSTOM_MARGINS);
|
| + print_settings.SetCustomMargins(settings.margins_in_points);
|
| +
|
| + gfx::Rect printable_area_device_units(settings.paper_size_in_points);
|
| + print_settings.SetPrinterPrintableArea(settings.paper_size_in_points,
|
| + printable_area_device_units, true);
|
| +
|
| + auto print_params = base::MakeUnique<PrintMsg_PrintPages_Params>();
|
| + RenderParamsFromPrintSettings(print_settings, &print_params->params);
|
| + print_params->params.document_cookie = PrintSettings::NewCookie();
|
| + return print_params;
|
| +}
|
| +
|
| bool HeadlessPrintManager::OnMessageReceived(
|
| const IPC::Message& message,
|
| content::RenderFrameHost* render_frame_host) {
|
| @@ -123,20 +179,42 @@ bool HeadlessPrintManager::OnMessageReceived(
|
| IPC_MESSAGE_HANDLER(PrintHostMsg_DidPrintPage, OnDidPrintPage)
|
| IPC_MESSAGE_HANDLER_DELAY_REPLY(PrintHostMsg_GetDefaultPrintSettings,
|
| OnGetDefaultPrintSettings)
|
| + IPC_MESSAGE_HANDLER_DELAY_REPLY(PrintHostMsg_ScriptedPrint, OnScriptedPrint)
|
| IPC_MESSAGE_UNHANDLED(handled = false)
|
| IPC_END_MESSAGE_MAP()
|
| return handled || PrintManager::OnMessageReceived(message, render_frame_host);
|
| }
|
|
|
| void HeadlessPrintManager::OnGetDefaultPrintSettings(IPC::Message* reply_msg) {
|
| - PrintMsg_Print_Params print_params;
|
| - RenderParamsFromPrintSettings(GetDefaultPDFPrinterSettings(), &print_params);
|
| - print_params.document_cookie = PrintSettings::NewCookie();
|
| PrintHostMsg_GetDefaultPrintSettings::WriteReplyParams(reply_msg,
|
| - print_params);
|
| + print_params_->params);
|
| printing_rfh_->Send(reply_msg);
|
| }
|
|
|
| +void HeadlessPrintManager::OnScriptedPrint(
|
| + const PrintHostMsg_ScriptedPrint_Params& params,
|
| + IPC::Message* reply_msg) {
|
| + PageRangeStatus status = PageRangeTextToPages(
|
| + page_ranges_text_, params.expected_pages_count, &print_params_->pages);
|
| + switch (status) {
|
| + case SYNTAX_ERROR:
|
| + printing_rfh_->Send(reply_msg);
|
| + ReleaseJob(PAGE_RANGE_SYNTAX_ERROR);
|
| + return;
|
| + case LIMIT_ERROR:
|
| + printing_rfh_->Send(reply_msg);
|
| + ReleaseJob(PAGE_COUNT_EXCEEDED);
|
| + return;
|
| + case NO_ERROR:
|
| + PrintHostMsg_ScriptedPrint::WriteReplyParams(reply_msg, *print_params_);
|
| + printing_rfh_->Send(reply_msg);
|
| + return;
|
| + default:
|
| + NOTREACHED();
|
| + return;
|
| + }
|
| +}
|
| +
|
| void HeadlessPrintManager::OnShowInvalidPrinterSettingsError() {
|
| ReleaseJob(INVALID_PRINTER_SETTINGS);
|
| }
|
| @@ -145,6 +223,13 @@ void HeadlessPrintManager::OnPrintingFailed(int cookie) {
|
| ReleaseJob(PRINTING_FAILED);
|
| }
|
|
|
| +void HeadlessPrintManager::OnDidGetPrintedPagesCount(int cookie,
|
| + int number_pages) {
|
| + PrintManager::OnDidGetPrintedPagesCount(cookie, number_pages);
|
| + if (!print_params_->pages.empty())
|
| + number_pages_ = print_params_->pages.size();
|
| +}
|
| +
|
| void HeadlessPrintManager::OnDidPrintPage(
|
| const PrintHostMsg_DidPrintPage_Params& params) {
|
| if (!callback_) {
|
| @@ -193,6 +278,8 @@ void HeadlessPrintManager::OnDidPrintPage(
|
| void HeadlessPrintManager::Reset() {
|
| printing_rfh_ = nullptr;
|
| callback_.Reset();
|
| + print_params_.reset();
|
| + page_ranges_text_.clear();
|
| data_.clear();
|
| expecting_first_page_ = true;
|
| number_pages_ = 0;
|
|
|