| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "content/renderer/npapi/webplugin_delegate_proxy.h" | 5 #include "content/renderer/npapi/webplugin_delegate_proxy.h" |
| 6 | 6 |
| 7 #include <stddef.h> | 7 #include <stddef.h> |
| 8 | 8 |
| 9 #include <algorithm> | 9 #include <algorithm> |
| 10 #include <utility> | 10 #include <utility> |
| (...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 101 WebPluginImpl* plugin, | 101 WebPluginImpl* plugin, |
| 102 const std::string& mime_type, | 102 const std::string& mime_type, |
| 103 const base::WeakPtr<RenderViewImpl>& render_view, | 103 const base::WeakPtr<RenderViewImpl>& render_view, |
| 104 RenderFrameImpl* render_frame) | 104 RenderFrameImpl* render_frame) |
| 105 : render_view_(render_view), | 105 : render_view_(render_view), |
| 106 render_frame_(render_frame), | 106 render_frame_(render_frame), |
| 107 plugin_(plugin), | 107 plugin_(plugin), |
| 108 uses_shared_bitmaps_(true), | 108 uses_shared_bitmaps_(true), |
| 109 #if defined(OS_MACOSX) | 109 #if defined(OS_MACOSX) |
| 110 uses_compositor_(false), | 110 uses_compositor_(false), |
| 111 #elif defined(OS_WIN) | |
| 112 dummy_activation_window_(NULL), | |
| 113 #endif | 111 #endif |
| 114 mime_type_(mime_type), | 112 mime_type_(mime_type), |
| 115 instance_id_(MSG_ROUTING_NONE), | 113 instance_id_(MSG_ROUTING_NONE), |
| 116 npobject_(NULL), | 114 npobject_(NULL), |
| 117 npp_(new NPP_t), | 115 npp_(new NPP_t), |
| 118 sad_plugin_(NULL), | 116 sad_plugin_(NULL), |
| 119 invalidate_pending_(false), | 117 invalidate_pending_(false), |
| 120 transparent_(false), | 118 transparent_(false), |
| 121 front_buffer_index_(0), | 119 front_buffer_index_(0), |
| 122 page_url_(render_view_->webview()->mainFrame()->document().url()) { | 120 page_url_(render_view_->webview()->mainFrame()->document().url()) { |
| 123 } | 121 } |
| 124 | 122 |
| 125 WebPluginDelegateProxy::~WebPluginDelegateProxy() { | 123 WebPluginDelegateProxy::~WebPluginDelegateProxy() { |
| 126 if (npobject_) | 124 if (npobject_) |
| 127 WebBindings::releaseObject(npobject_); | 125 WebBindings::releaseObject(npobject_); |
| 128 } | 126 } |
| 129 | 127 |
| 130 WebPluginDelegateProxy::SharedBitmap::SharedBitmap() {} | 128 WebPluginDelegateProxy::SharedBitmap::SharedBitmap() {} |
| 131 | 129 |
| 132 WebPluginDelegateProxy::SharedBitmap::~SharedBitmap() {} | 130 WebPluginDelegateProxy::SharedBitmap::~SharedBitmap() {} |
| 133 | 131 |
| 134 void WebPluginDelegateProxy::PluginDestroyed() { | 132 void WebPluginDelegateProxy::PluginDestroyed() { |
| 135 #if defined(OS_MACOSX) || defined(OS_WIN) | 133 #if defined(OS_MACOSX) |
| 136 // Ensure that the renderer doesn't think the plugin still has focus. | 134 // Ensure that the renderer doesn't think the plugin still has focus. |
| 137 if (render_view_) | 135 if (render_view_) |
| 138 render_view_->PluginFocusChanged(false, instance_id_); | 136 render_view_->PluginFocusChanged(false, instance_id_); |
| 139 #endif | 137 #endif |
| 140 | 138 |
| 141 #if defined(OS_WIN) | |
| 142 if (dummy_activation_window_ && render_view_) { | |
| 143 render_view_->Send(new ViewHostMsg_WindowlessPluginDummyWindowDestroyed( | |
| 144 render_view_->GetRoutingID(), dummy_activation_window_)); | |
| 145 } | |
| 146 dummy_activation_window_ = NULL; | |
| 147 #endif | |
| 148 | |
| 149 if (render_view_.get()) | 139 if (render_view_.get()) |
| 150 render_view_->UnregisterPluginDelegate(this); | 140 render_view_->UnregisterPluginDelegate(this); |
| 151 | 141 |
| 152 if (channel_host_.get()) { | 142 if (channel_host_.get()) { |
| 153 Send(new PluginMsg_DestroyInstance(instance_id_)); | 143 Send(new PluginMsg_DestroyInstance(instance_id_)); |
| 154 | 144 |
| 155 // Must remove the route after sending the destroy message, rather than | 145 // Must remove the route after sending the destroy message, rather than |
| 156 // before, since RemoveRoute can lead to all the outstanding NPObjects | 146 // before, since RemoveRoute can lead to all the outstanding NPObjects |
| 157 // being told the channel went away if this was the last instance. | 147 // being told the channel went away if this was the last instance. |
| 158 channel_host_->RemoveRoute(instance_id_); | 148 channel_host_->RemoveRoute(instance_id_); |
| (...skipping 138 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 297 IPC_MESSAGE_HANDLER(PluginHostMsg_InvalidateRect, OnInvalidateRect) | 287 IPC_MESSAGE_HANDLER(PluginHostMsg_InvalidateRect, OnInvalidateRect) |
| 298 IPC_MESSAGE_HANDLER(PluginHostMsg_GetWindowScriptNPObject, | 288 IPC_MESSAGE_HANDLER(PluginHostMsg_GetWindowScriptNPObject, |
| 299 OnGetWindowScriptNPObject) | 289 OnGetWindowScriptNPObject) |
| 300 IPC_MESSAGE_HANDLER(PluginHostMsg_GetPluginElement, OnGetPluginElement) | 290 IPC_MESSAGE_HANDLER(PluginHostMsg_GetPluginElement, OnGetPluginElement) |
| 301 IPC_MESSAGE_HANDLER(PluginHostMsg_ResolveProxy, OnResolveProxy) | 291 IPC_MESSAGE_HANDLER(PluginHostMsg_ResolveProxy, OnResolveProxy) |
| 302 IPC_MESSAGE_HANDLER(PluginHostMsg_SetCookie, OnSetCookie) | 292 IPC_MESSAGE_HANDLER(PluginHostMsg_SetCookie, OnSetCookie) |
| 303 IPC_MESSAGE_HANDLER(PluginHostMsg_GetCookies, OnGetCookies) | 293 IPC_MESSAGE_HANDLER(PluginHostMsg_GetCookies, OnGetCookies) |
| 304 IPC_MESSAGE_HANDLER(PluginHostMsg_CancelDocumentLoad, OnCancelDocumentLoad) | 294 IPC_MESSAGE_HANDLER(PluginHostMsg_CancelDocumentLoad, OnCancelDocumentLoad) |
| 305 IPC_MESSAGE_HANDLER(PluginHostMsg_DidStartLoading, OnDidStartLoading) | 295 IPC_MESSAGE_HANDLER(PluginHostMsg_DidStartLoading, OnDidStartLoading) |
| 306 IPC_MESSAGE_HANDLER(PluginHostMsg_DidStopLoading, OnDidStopLoading) | 296 IPC_MESSAGE_HANDLER(PluginHostMsg_DidStopLoading, OnDidStopLoading) |
| 307 #if defined(OS_WIN) | |
| 308 IPC_MESSAGE_HANDLER(PluginHostMsg_SetWindowlessData, OnSetWindowlessData) | |
| 309 IPC_MESSAGE_HANDLER(PluginHostMsg_NotifyIMEStatus, OnNotifyIMEStatus) | |
| 310 #endif | |
| 311 #if defined(OS_MACOSX) | 297 #if defined(OS_MACOSX) |
| 312 IPC_MESSAGE_HANDLER(PluginHostMsg_FocusChanged, | 298 IPC_MESSAGE_HANDLER(PluginHostMsg_FocusChanged, |
| 313 OnFocusChanged); | 299 OnFocusChanged); |
| 314 IPC_MESSAGE_HANDLER(PluginHostMsg_StartIme, | 300 IPC_MESSAGE_HANDLER(PluginHostMsg_StartIme, |
| 315 OnStartIme); | 301 OnStartIme); |
| 316 IPC_MESSAGE_HANDLER(PluginHostMsg_AcceleratedPluginEnabledRendering, | 302 IPC_MESSAGE_HANDLER(PluginHostMsg_AcceleratedPluginEnabledRendering, |
| 317 OnAcceleratedPluginEnabledRendering) | 303 OnAcceleratedPluginEnabledRendering) |
| 318 IPC_MESSAGE_HANDLER(PluginHostMsg_AcceleratedPluginAllocatedIOSurface, | 304 IPC_MESSAGE_HANDLER(PluginHostMsg_AcceleratedPluginAllocatedIOSurface, |
| 319 OnAcceleratedPluginAllocatedIOSurface) | 305 OnAcceleratedPluginAllocatedIOSurface) |
| 320 IPC_MESSAGE_HANDLER(PluginHostMsg_AcceleratedPluginSwappedIOSurface, | 306 IPC_MESSAGE_HANDLER(PluginHostMsg_AcceleratedPluginSwappedIOSurface, |
| 321 OnAcceleratedPluginSwappedIOSurface) | 307 OnAcceleratedPluginSwappedIOSurface) |
| 322 #endif | 308 #endif |
| 323 IPC_MESSAGE_UNHANDLED(handled = false) | 309 IPC_MESSAGE_UNHANDLED(handled = false) |
| 324 IPC_END_MESSAGE_MAP() | 310 IPC_END_MESSAGE_MAP() |
| 325 DCHECK(handled); | 311 DCHECK(handled); |
| 326 return handled; | 312 return handled; |
| 327 } | 313 } |
| 328 | 314 |
| 329 void WebPluginDelegateProxy::OnChannelError() { | 315 void WebPluginDelegateProxy::OnChannelError() { |
| 330 if (plugin_) { | 316 if (plugin_) { |
| 331 plugin_->Invalidate(); | 317 plugin_->Invalidate(); |
| 332 } | 318 } |
| 333 if (channel_host_.get() && !channel_host_->expecting_shutdown()) { | 319 if (channel_host_.get() && !channel_host_->expecting_shutdown()) { |
| 334 render_view_->GetMainRenderFrame()->PluginCrashed( | 320 render_view_->GetMainRenderFrame()->PluginCrashed( |
| 335 info_.path, channel_host_->peer_pid()); | 321 info_.path, channel_host_->peer_pid()); |
| 336 } | 322 } |
| 337 | 323 |
| 338 #if defined(OS_MACOSX) || defined(OS_WIN) | 324 #if defined(OS_MACOSX) |
| 339 // Ensure that the renderer doesn't think the plugin still has focus. | 325 // Ensure that the renderer doesn't think the plugin still has focus. |
| 340 if (render_view_) | 326 if (render_view_) |
| 341 render_view_->PluginFocusChanged(false, instance_id_); | 327 render_view_->PluginFocusChanged(false, instance_id_); |
| 342 #endif | 328 #endif |
| 343 } | 329 } |
| 344 | 330 |
| 345 static void CopySharedMemoryHandleForMessage( | 331 static void CopySharedMemoryHandleForMessage( |
| 346 const base::SharedMemoryHandle& handle_in, | 332 const base::SharedMemoryHandle& handle_in, |
| 347 base::SharedMemoryHandle* handle_out, | 333 base::SharedMemoryHandle* handle_out, |
| 348 base::ProcessId peer_pid) { | 334 base::ProcessId peer_pid) { |
| (...skipping 235 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 584 } | 570 } |
| 585 | 571 |
| 586 bool WebPluginDelegateProxy::GetFormValue(base::string16* value) { | 572 bool WebPluginDelegateProxy::GetFormValue(base::string16* value) { |
| 587 bool success = false; | 573 bool success = false; |
| 588 Send(new PluginMsg_GetFormValue(instance_id_, value, &success)); | 574 Send(new PluginMsg_GetFormValue(instance_id_, value, &success)); |
| 589 return success; | 575 return success; |
| 590 } | 576 } |
| 591 | 577 |
| 592 void WebPluginDelegateProxy::SetFocus(bool focused) { | 578 void WebPluginDelegateProxy::SetFocus(bool focused) { |
| 593 Send(new PluginMsg_SetFocus(instance_id_, focused)); | 579 Send(new PluginMsg_SetFocus(instance_id_, focused)); |
| 594 #if defined(OS_WIN) | |
| 595 if (render_view_) | |
| 596 render_view_->PluginFocusChanged(focused, instance_id_); | |
| 597 #endif | |
| 598 } | 580 } |
| 599 | 581 |
| 600 bool WebPluginDelegateProxy::HandleInputEvent( | 582 bool WebPluginDelegateProxy::HandleInputEvent( |
| 601 const WebInputEvent& event, | 583 const WebInputEvent& event, |
| 602 WebCursor::CursorInfo* cursor_info) { | 584 WebCursor::CursorInfo* cursor_info) { |
| 603 bool handled = false; | 585 bool handled = false; |
| 604 WebCursor cursor; | 586 WebCursor cursor; |
| 605 // A windowless plugin can enter a modal loop in the context of a | 587 Send(new PluginMsg_HandleInputEvent(instance_id_, &event, &handled, &cursor)); |
| 606 // NPP_HandleEvent call, in which case we need to pump messages to | |
| 607 // the plugin. We pass of the corresponding event handle to the | |
| 608 // plugin process, which is set if the plugin does enter a modal loop. | |
| 609 IPC::SyncMessage* message = new PluginMsg_HandleInputEvent( | |
| 610 instance_id_, &event, &handled, &cursor); | |
| 611 message->set_pump_messages_event(modal_loop_pump_messages_event_.get()); | |
| 612 Send(message); | |
| 613 return handled; | 588 return handled; |
| 614 } | 589 } |
| 615 | 590 |
| 616 int WebPluginDelegateProxy::GetProcessId() { | 591 int WebPluginDelegateProxy::GetProcessId() { |
| 617 return channel_host_->peer_pid(); | 592 return channel_host_->peer_pid(); |
| 618 } | 593 } |
| 619 | 594 |
| 620 void WebPluginDelegateProxy::SetContentAreaFocus(bool has_focus) { | 595 void WebPluginDelegateProxy::SetContentAreaFocus(bool has_focus) { |
| 621 IPC::Message* msg = new PluginMsg_SetContentAreaFocus(instance_id_, | 596 IPC::Message* msg = new PluginMsg_SetContentAreaFocus(instance_id_, |
| 622 has_focus); | 597 has_focus); |
| 623 // Make sure focus events are delivered in the right order relative to | 598 // Make sure focus events are delivered in the right order relative to |
| 624 // sync messages they might interact with (Paint, HandleEvent, etc.). | 599 // sync messages they might interact with (Paint, HandleEvent, etc.). |
| 625 msg->set_unblock(true); | 600 msg->set_unblock(true); |
| 626 Send(msg); | 601 Send(msg); |
| 627 } | 602 } |
| 628 | 603 |
| 629 #if defined(OS_WIN) | |
| 630 void WebPluginDelegateProxy::ImeCompositionUpdated( | |
| 631 const base::string16& text, | |
| 632 const std::vector<int>& clauses, | |
| 633 const std::vector<int>& target, | |
| 634 int cursor_position, | |
| 635 int plugin_id) { | |
| 636 // Dispatch the raw IME data if this plugin is the focused one. | |
| 637 if (instance_id_ != plugin_id) | |
| 638 return; | |
| 639 | |
| 640 IPC::Message* msg = new PluginMsg_ImeCompositionUpdated(instance_id_, | |
| 641 text, clauses, target, cursor_position); | |
| 642 msg->set_unblock(true); | |
| 643 Send(msg); | |
| 644 } | |
| 645 | |
| 646 void WebPluginDelegateProxy::ImeCompositionCompleted(const base::string16& text, | |
| 647 int plugin_id) { | |
| 648 // Dispatch the IME text if this plugin is the focused one. | |
| 649 if (instance_id_ != plugin_id) | |
| 650 return; | |
| 651 | |
| 652 IPC::Message* msg = new PluginMsg_ImeCompositionCompleted(instance_id_, text); | |
| 653 msg->set_unblock(true); | |
| 654 Send(msg); | |
| 655 } | |
| 656 #endif | |
| 657 | |
| 658 #if defined(OS_MACOSX) | 604 #if defined(OS_MACOSX) |
| 659 void WebPluginDelegateProxy::SetWindowFocus(bool window_has_focus) { | 605 void WebPluginDelegateProxy::SetWindowFocus(bool window_has_focus) { |
| 660 IPC::Message* msg = new PluginMsg_SetWindowFocus(instance_id_, | 606 IPC::Message* msg = new PluginMsg_SetWindowFocus(instance_id_, |
| 661 window_has_focus); | 607 window_has_focus); |
| 662 // Make sure focus events are delivered in the right order relative to | 608 // Make sure focus events are delivered in the right order relative to |
| 663 // sync messages they might interact with (Paint, HandleEvent, etc.). | 609 // sync messages they might interact with (Paint, HandleEvent, etc.). |
| 664 msg->set_unblock(true); | 610 msg->set_unblock(true); |
| 665 Send(msg); | 611 Send(msg); |
| 666 } | 612 } |
| 667 | 613 |
| (...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 699 return; | 645 return; |
| 700 | 646 |
| 701 IPC::Message* msg = new PluginMsg_ImeCompositionCompleted(instance_id_, | 647 IPC::Message* msg = new PluginMsg_ImeCompositionCompleted(instance_id_, |
| 702 text); | 648 text); |
| 703 // Order relative to other key events is important. | 649 // Order relative to other key events is important. |
| 704 msg->set_unblock(true); | 650 msg->set_unblock(true); |
| 705 Send(msg); | 651 Send(msg); |
| 706 } | 652 } |
| 707 #endif // OS_MACOSX | 653 #endif // OS_MACOSX |
| 708 | 654 |
| 709 #if defined(OS_WIN) | |
| 710 void WebPluginDelegateProxy::OnSetWindowlessData( | |
| 711 HANDLE modal_loop_pump_messages_event_handle, | |
| 712 gfx::NativeViewId dummy_activation_window) { | |
| 713 DCHECK(!modal_loop_pump_messages_event_.get()); | |
| 714 DCHECK(!dummy_activation_window_); | |
| 715 base::win::ScopedHandle modal_loop_pump_messages_event( | |
| 716 modal_loop_pump_messages_event_handle); | |
| 717 | |
| 718 dummy_activation_window_ = dummy_activation_window; | |
| 719 render_view_->Send(new ViewHostMsg_WindowlessPluginDummyWindowCreated( | |
| 720 render_view_->GetRoutingID(), dummy_activation_window_)); | |
| 721 | |
| 722 // Bug 25583: this can be null because some "virus scanners" block the | |
| 723 // DuplicateHandle call in the plugin process. | |
| 724 if (!modal_loop_pump_messages_event.IsValid()) | |
| 725 return; | |
| 726 | |
| 727 modal_loop_pump_messages_event_.reset( | |
| 728 new base::WaitableEvent(std::move(modal_loop_pump_messages_event))); | |
| 729 } | |
| 730 | |
| 731 void WebPluginDelegateProxy::OnNotifyIMEStatus(int input_type, | |
| 732 const gfx::Rect& caret_rect) { | |
| 733 if (!render_view_) | |
| 734 return; | |
| 735 | |
| 736 ViewHostMsg_TextInputState_Params params; | |
| 737 params.type = static_cast<ui::TextInputType>(input_type); | |
| 738 params.mode = ui::TEXT_INPUT_MODE_DEFAULT; | |
| 739 params.can_compose_inline = true; | |
| 740 render_view_->Send(new ViewHostMsg_TextInputStateChanged( | |
| 741 render_view_->GetRoutingID(), params)); | |
| 742 | |
| 743 ViewHostMsg_SelectionBounds_Params bounds_params; | |
| 744 bounds_params.anchor_rect = bounds_params.focus_rect = caret_rect; | |
| 745 bounds_params.anchor_dir = bounds_params.focus_dir = | |
| 746 blink::WebTextDirectionLeftToRight; | |
| 747 bounds_params.is_anchor_first = true; | |
| 748 render_view_->Send(new ViewHostMsg_SelectionBoundsChanged( | |
| 749 render_view_->GetRoutingID(), bounds_params)); | |
| 750 } | |
| 751 #endif | |
| 752 | |
| 753 void WebPluginDelegateProxy::OnInvalidateRect(const gfx::Rect& rect) { | 655 void WebPluginDelegateProxy::OnInvalidateRect(const gfx::Rect& rect) { |
| 754 if (!plugin_) | 656 if (!plugin_) |
| 755 return; | 657 return; |
| 756 | 658 |
| 757 // Clip the invalidation rect to the plugin bounds; the plugin may have been | 659 // Clip the invalidation rect to the plugin bounds; the plugin may have been |
| 758 // resized since the invalidate message was sent. | 660 // resized since the invalidate message was sent. |
| 759 gfx::Rect clipped_rect = | 661 gfx::Rect clipped_rect = |
| 760 gfx::IntersectRects(rect, gfx::Rect(plugin_rect_.size())); | 662 gfx::IntersectRects(rect, gfx::Rect(plugin_rect_.size())); |
| 761 | 663 |
| 762 invalidate_pending_ = true; | 664 invalidate_pending_ = true; |
| (...skipping 177 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 940 index->mime_type == "application/x-vnd.movenetworks.qm" || | 842 index->mime_type == "application/x-vnd.movenetworks.qm" || |
| 941 index->mime_type == "application/x-vnd.mnplayer.qm") { | 843 index->mime_type == "application/x-vnd.mnplayer.qm") { |
| 942 return true; | 844 return true; |
| 943 } | 845 } |
| 944 } | 846 } |
| 945 return false; | 847 return false; |
| 946 } | 848 } |
| 947 #endif | 849 #endif |
| 948 | 850 |
| 949 } // namespace content | 851 } // namespace content |
| OLD | NEW |