Chromium Code Reviews| Index: chrome/browser/printing/print_view_manager.cc |
| diff --git a/chrome/browser/printing/print_view_manager.cc b/chrome/browser/printing/print_view_manager.cc |
| index 77dda243a46ab497e19bf7569fad4cbcfca4ebb8..e5187ea8c9ec3502eac4776a715b70e5f5cd61a9 100644 |
| --- a/chrome/browser/printing/print_view_manager.cc |
| +++ b/chrome/browser/printing/print_view_manager.cc |
| @@ -5,6 +5,7 @@ |
| #include "chrome/browser/printing/print_view_manager.h" |
| #include "base/bind.h" |
| +#include "base/lazy_instance.h" |
| #include "base/memory/scoped_ptr.h" |
| #include "base/utf_string_conversions.h" |
| #include "chrome/browser/browser_process.h" |
| @@ -50,6 +51,13 @@ void ReleasePrinterQuery(int cookie) { |
| } |
| } |
| +// Keeps track of pending scripted print preview closures. |
| +// No locking, only access on the UI thread. |
| +typedef std::map<RenderProcessHost*, base::Closure> |
| + ScriptedPrintPreviewClosureMap; |
| +static base::LazyInstance<ScriptedPrintPreviewClosureMap> |
| + g_scripted_print_preview_closure_map(base::LINKER_INITIALIZED); |
| + |
| } // namespace |
| namespace printing { |
| @@ -61,13 +69,16 @@ PrintViewManager::PrintViewManager(TabContentsWrapper* tab) |
| printing_succeeded_(false), |
| inside_inner_message_loop_(false), |
| observer_(NULL), |
| - cookie_(0) { |
| + cookie_(0), |
| + print_preview_state_(NOT_PREVIEWING), |
| + scripted_print_preview_rph_(NULL) { |
| #if defined(OS_POSIX) && !defined(OS_MACOSX) |
| expecting_first_page_ = true; |
| #endif |
| } |
| PrintViewManager::~PrintViewManager() { |
| + DCHECK_EQ(NOT_PREVIEWING, print_preview_state_); |
|
vandebo (ex-Chrome)
2011/11/10 23:59:59
What if you close a tab/window while previewing?
Lei Zhang
2011/11/11 11:45:11
RemoveInitiatorTab() will call PrintPreviewDone()
|
| ReleasePrinterQuery(cookie_); |
| DisconnectFromCurrentPrintJob(); |
| } |
| @@ -103,9 +114,34 @@ bool PrintViewManager::AdvancedPrintNow() { |
| } |
| bool PrintViewManager::PrintPreviewNow() { |
| + if (print_preview_state_ != NOT_PREVIEWING) { |
| + NOTREACHED(); |
| + return false; |
| + } |
| + print_preview_state_ = USER_INITIATED_PREVIEW; |
| return PrintNowInternal(new PrintMsg_InitiatePrintPreview(routing_id())); |
| } |
| +void PrintViewManager::PrintPreviewDone() { |
| + BrowserThread::CurrentlyOn(BrowserThread::UI); |
| + |
| + // Check for spurious call. |
|
vandebo (ex-Chrome)
2011/11/10 23:59:59
This makes me sad. If you can explain why there m
Lei Zhang
2011/11/11 11:45:11
This is a defensive move. I'll check whether it's
Lei Zhang
2011/11/11 22:34:26
Got rid of this and turned it into a DCHECK.
|
| + if (print_preview_state_ == NOT_PREVIEWING) |
| + return; |
| + |
| + if (print_preview_state_ == SCRIPTED_PREVIEW) { |
| + ScriptedPrintPreviewClosureMap& map = |
| + g_scripted_print_preview_closure_map.Get(); |
| + ScriptedPrintPreviewClosureMap::iterator it = |
| + map.find(scripted_print_preview_rph_); |
| + CHECK(it != map.end()); |
| + it->second.Run(); |
| + map.erase(scripted_print_preview_rph_); |
| + scripted_print_preview_rph_ = NULL; |
| + } |
| + print_preview_state_ = NOT_PREVIEWING; |
| +} |
| + |
| void PrintViewManager::PreviewPrintingRequestCancelled() { |
| if (!tab_contents()) |
| return; |
| @@ -227,6 +263,35 @@ void PrintViewManager::OnPrintingFailed(int cookie) { |
| content::NotificationService::NoDetails()); |
| } |
| +void PrintViewManager::OnScriptedPrintPreview(IPC::Message* reply_msg) { |
| + BrowserThread::CurrentlyOn(BrowserThread::UI); |
| + if (print_preview_state_ != NOT_PREVIEWING) { |
| + // If a user initiated print dialog is already open, ignore the scripted |
| + // print message. |
| + DCHECK_EQ(USER_INITIATED_PREVIEW, print_preview_state_); |
| + Send(reply_msg); |
| + return; |
| + } |
| + |
| + print_preview_state_ = SCRIPTED_PREVIEW; |
| + scripted_print_preview_rph_ = tab_contents()->render_view_host()->process(); |
| + base::Closure callback = |
| + base::Bind(&PrintViewManager::OnScriptedPrintPreviewReply, |
| + base::Unretained(this), |
| + reply_msg); |
| + ScriptedPrintPreviewClosureMap& map = |
| + g_scripted_print_preview_closure_map.Get(); |
| + CHECK_EQ(0U, map.count(scripted_print_preview_rph_)); |
| + map[scripted_print_preview_rph_] = callback; |
| + |
| + PrintNowInternal(new PrintMsg_InitiatePrintPreview(routing_id())); |
|
vandebo (ex-Chrome)
2011/11/10 23:59:59
This will trigger GetPrintFrame(), but the caller
Lei Zhang
2011/11/11 11:45:11
I'm surprised this didn't blow up, fixed.
|
| +} |
| + |
| +void PrintViewManager::OnScriptedPrintPreviewReply(IPC::Message* reply_msg) { |
| + BrowserThread::CurrentlyOn(BrowserThread::UI); |
| + Send(reply_msg); |
| +} |
| + |
| bool PrintViewManager::OnMessageReceived(const IPC::Message& message) { |
| bool handled = true; |
| IPC_BEGIN_MESSAGE_MAP(PrintViewManager, message) |
| @@ -237,6 +302,8 @@ bool PrintViewManager::OnMessageReceived(const IPC::Message& message) { |
| IPC_MESSAGE_HANDLER(PrintHostMsg_DidShowPrintDialog, OnDidShowPrintDialog) |
| IPC_MESSAGE_HANDLER(PrintHostMsg_DidPrintPage, OnDidPrintPage) |
| IPC_MESSAGE_HANDLER(PrintHostMsg_PrintingFailed, OnPrintingFailed) |
| + IPC_MESSAGE_HANDLER_DELAY_REPLY(PrintHostMsg_ScriptedPrintPreview, |
| + OnScriptedPrintPreview) |
| IPC_MESSAGE_UNHANDLED(handled = false) |
| IPC_END_MESSAGE_MAP() |
| return handled; |