diff options
-rw-r--r-- | chrome/common/plugin_messages_internal.h | 6 | ||||
-rw-r--r-- | chrome/plugin/webplugin_delegate_stub.cc | 10 | ||||
-rw-r--r-- | chrome/plugin/webplugin_delegate_stub.h | 2 | ||||
-rw-r--r-- | chrome/renderer/render_view.cc | 14 | ||||
-rw-r--r-- | chrome/renderer/render_view.h | 7 | ||||
-rw-r--r-- | chrome/renderer/webplugin_delegate_proxy.cc | 18 | ||||
-rw-r--r-- | chrome/renderer/webplugin_delegate_proxy.h | 6 | ||||
-rw-r--r-- | webkit/glue/plugins/webplugin_delegate_impl.cc | 24 | ||||
-rw-r--r-- | webkit/glue/plugins/webplugin_delegate_impl.h | 40 | ||||
-rw-r--r-- | webkit/glue/plugins/webplugin_delegate_impl_gtk.cc | 8 | ||||
-rw-r--r-- | webkit/glue/plugins/webplugin_delegate_impl_mac.mm | 39 | ||||
-rw-r--r-- | webkit/glue/plugins/webplugin_delegate_impl_win.cc | 8 |
12 files changed, 101 insertions, 81 deletions
diff --git a/chrome/common/plugin_messages_internal.h b/chrome/common/plugin_messages_internal.h index 29388a4..99e265a 100644 --- a/chrome/common/plugin_messages_internal.h +++ b/chrome/common/plugin_messages_internal.h @@ -221,11 +221,11 @@ IPC_BEGIN_MESSAGES(Plugin) bool /* handled */, WebCursor /* cursor type*/) -#if defined(OS_MACOSX) - IPC_MESSAGE_ROUTED1(PluginMsg_SetWindowFocus, + IPC_MESSAGE_ROUTED1(PluginMsg_SetContentAreaFocus, bool /* has_focus */) - IPC_MESSAGE_ROUTED1(PluginMsg_SetContentAreaFocus, +#if defined(OS_MACOSX) + IPC_MESSAGE_ROUTED1(PluginMsg_SetWindowFocus, bool /* has_focus */) IPC_MESSAGE_ROUTED0(PluginMsg_ContainerHidden) diff --git a/chrome/plugin/webplugin_delegate_stub.cc b/chrome/plugin/webplugin_delegate_stub.cc index 0802d31..8e74aa7 100644 --- a/chrome/plugin/webplugin_delegate_stub.cc +++ b/chrome/plugin/webplugin_delegate_stub.cc @@ -116,9 +116,9 @@ void WebPluginDelegateStub::OnMessageReceived(const IPC::Message& msg) { IPC_MESSAGE_HANDLER(PluginMsg_UpdateGeometrySync, OnUpdateGeometry) IPC_MESSAGE_HANDLER(PluginMsg_SendJavaScriptStream, OnSendJavaScriptStream) + IPC_MESSAGE_HANDLER(PluginMsg_SetContentAreaFocus, OnSetContentAreaFocus) #if defined(OS_MACOSX) IPC_MESSAGE_HANDLER(PluginMsg_SetWindowFocus, OnSetWindowFocus) - IPC_MESSAGE_HANDLER(PluginMsg_SetContentAreaFocus, OnSetContentAreaFocus) IPC_MESSAGE_HANDLER(PluginMsg_ContainerHidden, OnContainerHidden) IPC_MESSAGE_HANDLER(PluginMsg_ContainerShown, OnContainerShown) IPC_MESSAGE_HANDLER(PluginMsg_WindowFrameChanged, OnWindowFrameChanged) @@ -336,15 +336,15 @@ void WebPluginDelegateStub::OnSendJavaScriptStream(const GURL& url, delegate_->SendJavaScriptStream(url, result, success, notify_id); } +void WebPluginDelegateStub::OnSetContentAreaFocus(bool has_focus) { + delegate_->SetContentAreaHasFocus(has_focus); +} + #if defined(OS_MACOSX) void WebPluginDelegateStub::OnSetWindowFocus(bool has_focus) { delegate_->SetWindowHasFocus(has_focus); } -void WebPluginDelegateStub::OnSetContentAreaFocus(bool has_focus) { - delegate_->SetContentAreaHasFocus(has_focus); -} - void WebPluginDelegateStub::OnContainerHidden() { delegate_->SetContainerVisibility(false); } diff --git a/chrome/plugin/webplugin_delegate_stub.h b/chrome/plugin/webplugin_delegate_stub.h index 84b22a0..0c1101e 100644 --- a/chrome/plugin/webplugin_delegate_stub.h +++ b/chrome/plugin/webplugin_delegate_stub.h @@ -77,9 +77,9 @@ class WebPluginDelegateStub : public IPC::Channel::Listener, bool success, int notify_id); + void OnSetContentAreaFocus(bool has_focus); #if defined(OS_MACOSX) void OnSetWindowFocus(bool has_focus); - void OnSetContentAreaFocus(bool has_focus); void OnContainerHidden(); void OnContainerShown(gfx::Rect window_frame, gfx::Rect view_frame, bool has_focus); diff --git a/chrome/renderer/render_view.cc b/chrome/renderer/render_view.cc index 9f1fcb6..9e33f83 100644 --- a/chrome/renderer/render_view.cc +++ b/chrome/renderer/render_view.cc @@ -597,23 +597,25 @@ WebPlugin* RenderView::CreatePluginNoCheck(WebFrame* frame, return CreateNPAPIPlugin(frame, params, info.path, mime_type); } -#if defined(OS_MACOSX) void RenderView::RegisterPluginDelegate(WebPluginDelegateProxy* delegate) { plugin_delegates_.insert(delegate); // If the renderer is visible, set initial visibility and focus state. if (!is_hidden()) { +#if defined(OS_MACOSX) delegate->SetContainerVisibility(true); if (webview() && webview()->isActive()) delegate->SetWindowFocus(true); - if (has_focus()) - delegate->SetContentAreaFocus(true); +#endif } + // Plugins start assuming the content has focus (so that they work in + // environments where RenderView isn't hosting them), so we always have to + // set the initial state. See webplugin_delegate_impl.h for details. + delegate->SetContentAreaFocus(has_focus()); } void RenderView::UnregisterPluginDelegate(WebPluginDelegateProxy* delegate) { plugin_delegates_.erase(delegate); } -#endif void RenderView::Init(gfx::NativeViewId parent_hwnd, int32 opener_id, @@ -5632,6 +5634,7 @@ void RenderView::OnWasRestored(bool needs_repainting) { (*plugin_it)->SetContainerVisibility(true); } } +#endif // OS_MACOSX void RenderView::OnSetFocus(bool enable) { RenderWidget::OnSetFocus(enable); @@ -5640,15 +5643,16 @@ void RenderView::OnSetFocus(bool enable) { std::set<WebPluginDelegateProxy*>::iterator plugin_it; for (plugin_it = plugin_delegates_.begin(); plugin_it != plugin_delegates_.end(); ++plugin_it) { +#if defined(OS_MACOSX) // RenderWidget's call to setFocus can cause the underlying webview's // activation state to change just like a call to setIsActive. if (enable) (*plugin_it)->SetWindowFocus(true); +#endif (*plugin_it)->SetContentAreaFocus(enable); } } } -#endif // OS_MACOSX void RenderView::EnsureDocumentTag() { // TODO(darin): There's actually no reason for this to be here. We should diff --git a/chrome/renderer/render_view.h b/chrome/renderer/render_view.h index 0013ee9..01f9655 100644 --- a/chrome/renderer/render_view.h +++ b/chrome/renderer/render_view.h @@ -318,10 +318,10 @@ class RenderView : public RenderWidget, int32 height, TransportDIB::Handle transport_dib); void AcceleratedSurfaceBuffersSwapped(gfx::PluginWindowHandle window); +#endif void RegisterPluginDelegate(WebPluginDelegateProxy* delegate); void UnregisterPluginDelegate(WebPluginDelegateProxy* delegate); -#endif // IPC::Channel::Listener implementation ------------------------------------- @@ -610,9 +610,8 @@ class RenderView : public RenderWidget, virtual void DidFlushPaint(); virtual void DidHandleKeyEvent(); virtual void DidHandleMouseEvent(const WebKit::WebMouseEvent& event); - -#if OS_MACOSX virtual void OnSetFocus(bool enable); +#if OS_MACOSX virtual void OnWasHidden(); virtual void OnWasRestored(bool needs_repainting); #endif @@ -1218,12 +1217,10 @@ class RenderView : public RenderWidget, PepperPluginDelegateImpl pepper_delegate_; -#if defined(OS_MACOSX) // All the currently active plugin delegates for this RenderView; kept so that // we can enumerate them to send updates about things like window location // or tab focus and visibily. These are non-owning references. std::set<WebPluginDelegateProxy*> plugin_delegates_; -#endif // A list of all Pepper v1 plugins that we've created that haven't been // destroyed yet. Pepper v2 plugins are tracked by the pepper_delegate_. diff --git a/chrome/renderer/webplugin_delegate_proxy.cc b/chrome/renderer/webplugin_delegate_proxy.cc index a5490af..2dd4581 100644 --- a/chrome/renderer/webplugin_delegate_proxy.cc +++ b/chrome/renderer/webplugin_delegate_proxy.cc @@ -204,10 +204,8 @@ void WebPluginDelegateProxy::PluginDestroyed() { if (window_) WillDestroyWindow(); -#if defined(OS_MACOSX) if (render_view_) render_view_->UnregisterPluginDelegate(this); -#endif if (channel_host_) { Send(new PluginMsg_DestroyInstance(instance_id_)); @@ -384,9 +382,7 @@ bool WebPluginDelegateProxy::Initialize(const GURL& url, IPC::Message* msg = new PluginMsg_Init(instance_id_, params, &result); Send(msg); -#if defined(OS_MACOSX) render_view_->RegisterPluginDelegate(this); -#endif return result; } @@ -983,19 +979,19 @@ int WebPluginDelegateProxy::GetProcessId() { return channel_host_->peer_pid(); } -#if defined(OS_MACOSX) -void WebPluginDelegateProxy::SetWindowFocus(bool window_has_focus) { - IPC::Message* msg = new PluginMsg_SetWindowFocus(instance_id_, - window_has_focus); +void WebPluginDelegateProxy::SetContentAreaFocus(bool has_focus) { + IPC::Message* msg = new PluginMsg_SetContentAreaFocus(instance_id_, + has_focus); // Make sure focus events are delivered in the right order relative to // sync messages they might interact with (Paint, HandleEvent, etc.). msg->set_unblock(true); Send(msg); } -void WebPluginDelegateProxy::SetContentAreaFocus(bool has_focus) { - IPC::Message* msg = new PluginMsg_SetContentAreaFocus(instance_id_, - has_focus); +#if defined(OS_MACOSX) +void WebPluginDelegateProxy::SetWindowFocus(bool window_has_focus) { + IPC::Message* msg = new PluginMsg_SetWindowFocus(instance_id_, + window_has_focus); // Make sure focus events are delivered in the right order relative to // sync messages they might interact with (Paint, HandleEvent, etc.). msg->set_unblock(true); diff --git a/chrome/renderer/webplugin_delegate_proxy.h b/chrome/renderer/webplugin_delegate_proxy.h index 1660556..0cabc1b 100644 --- a/chrome/renderer/webplugin_delegate_proxy.h +++ b/chrome/renderer/webplugin_delegate_proxy.h @@ -78,12 +78,12 @@ class WebPluginDelegateProxy WebKit::WebCursorInfo* cursor); virtual int GetProcessId(); -#if defined(OS_MACOSX) - // Informs the plugin that its enclosing window has gained or lost focus. - virtual void SetWindowFocus(bool window_has_focus); // Informs the plugin that its containing content view has gained or lost // first responder status. virtual void SetContentAreaFocus(bool has_focus); +#if defined(OS_MACOSX) + // Informs the plugin that its enclosing window has gained or lost focus. + virtual void SetWindowFocus(bool window_has_focus); // Informs the plugin that its container (window/tab) has changed visibility. virtual void SetContainerVisibility(bool is_visible); // Informs the plugin that its enclosing window's frame has changed. diff --git a/webkit/glue/plugins/webplugin_delegate_impl.cc b/webkit/glue/plugins/webplugin_delegate_impl.cc index b73b5ae..beaddfc 100644 --- a/webkit/glue/plugins/webplugin_delegate_impl.cc +++ b/webkit/glue/plugins/webplugin_delegate_impl.cc @@ -156,6 +156,30 @@ void WebPluginDelegateImpl::UpdateGeometry( } } +void WebPluginDelegateImpl::SetFocus(bool focused) { + DCHECK(windowless_); + // This is called when internal WebKit focus (the focused element on the page) + // changes, but plugins need to know about OS-level focus, so we have an extra + // layer of focus tracking. + has_webkit_focus_ = focused; + if (containing_view_has_focus_) + SetPluginHasFocus(focused); +} + +void WebPluginDelegateImpl::SetPluginHasFocus(bool focused) { + if (focused == plugin_has_focus_) + return; + if (PlatformSetPluginHasFocus(focused)) + plugin_has_focus_ = focused; +} + +void WebPluginDelegateImpl::SetContentAreaHasFocus(bool has_focus) { + containing_view_has_focus_ = has_focus; + if (!windowless_) + return; + SetPluginHasFocus(containing_view_has_focus_ && has_webkit_focus_); +} + NPObject* WebPluginDelegateImpl::GetPluginScriptableObject() { return instance_->GetPluginScriptableObject(); } diff --git a/webkit/glue/plugins/webplugin_delegate_impl.h b/webkit/glue/plugins/webplugin_delegate_impl.h index b20cd67..650d398 100644 --- a/webkit/glue/plugins/webplugin_delegate_impl.h +++ b/webkit/glue/plugins/webplugin_delegate_impl.h @@ -137,6 +137,9 @@ class WebPluginDelegateImpl : public webkit_glue::WebPluginDelegate { // Returns a combination of PluginQuirks. int GetQuirks() const { return quirks_; } + // Informs the plugin that the view it is in has gained or lost focus. + void SetContentAreaHasFocus(bool has_focus); + #if defined(OS_MACOSX) // Informs the plugin that the geometry has changed, as with UpdateGeometry, // but also includes the new buffer context for that new geometry. @@ -150,16 +153,14 @@ class WebPluginDelegateImpl : public webkit_glue::WebPluginDelegate { static WebPluginDelegateImpl* GetActiveDelegate(); // Informs the plugin that the window it is in has gained or lost focus. void SetWindowHasFocus(bool has_focus); - // Informs the plugin that the view it is in has gained or lost first - // responder status. - void SetContentAreaHasFocus(bool has_focus); // Returns whether or not the window the plugin is in has focus. bool GetWindowHasFocus() const { return containing_window_has_focus_; } // Informs the plugin that its tab or window has been hidden or shown. void SetContainerVisibility(bool is_visible); // Informs the plugin that its containing window's frame has changed. // Frames are in screen coordinates. - void WindowFrameChanged(gfx::Rect window_frame, gfx::Rect view_frame); + void WindowFrameChanged(const gfx::Rect& window_frame, + const gfx::Rect& view_frame); // Informs the delegate that the plugin set a Carbon ThemeCursor. void SetThemeCursor(ThemeCursor cursor); // Informs the delegate that the plugin set a Carbon Cursor. @@ -254,6 +255,14 @@ class WebPluginDelegateImpl : public webkit_glue::WebPluginDelegate { // See NPAPI NPP_SetWindow for more information. void WindowlessSetWindow(); + // Informs the plugin that it has gained or lost keyboard focus (on the Mac, + // this just means window first responder status). + void SetPluginHasFocus(bool focused); + + // Handles the platform specific details of setting plugin focus. Returns + // false if the platform cancelled the focus tranfer. + bool PlatformSetPluginHasFocus(bool focused); + //----------------------------------------- // used for windowed and windowless plugins @@ -377,10 +386,6 @@ class WebPluginDelegateImpl : public webkit_glue::WebPluginDelegate { // Updates everything that depends on the plugin's absolute screen location. void PluginScreenLocationChanged(); - // Informs the plugin that it has gained or lost keyboard focus (i.e., window - // first responder status). - void SetPluginHasFocus(bool has_focus); - // Returns the apparent zoom ratio for the given event, as inferred from our // current knowledge about about where on screen the plugin is. // This is a temporary workaround for <http://crbug.com/9996>; once that is @@ -435,14 +440,6 @@ class WebPluginDelegateImpl : public webkit_glue::WebPluginDelegate { // relative to an upper-left (0,0). gfx::Point content_area_origin_; - // True if the plugin thinks it has keyboard focus - bool plugin_has_focus_; - // True if the plugin element has focus within the page, regardless of whether - // its containing view is currently the first responder for the window. - bool has_webkit_focus_; - // True if the containing view is the window's first responder. - bool containing_view_has_focus_; - bool containing_window_has_focus_; bool initial_window_focus_; bool container_is_visible_; @@ -495,6 +492,17 @@ class WebPluginDelegateImpl : public webkit_glue::WebPluginDelegate { // call received by the plugin. bool first_set_window_call_; + // True if the plugin thinks it has keyboard focus + bool plugin_has_focus_; + // True if the plugin element has focus within the web content, regardless of + // whether its containing view currently has focus. + bool has_webkit_focus_; + // True if the containing view currently has focus. + // Initially set to true so that plugin focus still works in environments + // where SetContentAreaHasFocus is never called. See + // https://bugs.webkit.org/show_bug.cgi?id=46013 for details. + bool containing_view_has_focus_; + DISALLOW_COPY_AND_ASSIGN(WebPluginDelegateImpl); }; diff --git a/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc b/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc index d4a98a8..3d112fa 100644 --- a/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc +++ b/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc @@ -52,7 +52,10 @@ WebPluginDelegateImpl::WebPluginDelegateImpl( parent_(containing_view), quirks_(0), handle_event_depth_(0), - first_set_window_call_(true) { + first_set_window_call_(true), + plugin_has_focus_(false), + has_webkit_focus_(false), + containing_view_has_focus_(true) { memset(&window_, 0, sizeof(window_)); if (instance_->mime_type() == "application/x-shockwave-flash") { // Flash is tied to Firefox's whacky behavior with windowless plugins. See @@ -538,7 +541,7 @@ void WebPluginDelegateImpl::WindowlessSetWindow() { } } -void WebPluginDelegateImpl::SetFocus(bool focused) { +bool WebPluginDelegateImpl::PlatformSetPluginHasFocus(bool focused) { DCHECK(instance()->windowless()); NPEvent np_event = {0}; @@ -549,6 +552,7 @@ void WebPluginDelegateImpl::SetFocus(bool focused) { event.mode = -1; event.detail = NotifyDetailNone; instance()->NPP_HandleEvent(&np_event); + return true; } // Converts a WebInputEvent::Modifiers bitfield into a diff --git a/webkit/glue/plugins/webplugin_delegate_impl_mac.mm b/webkit/glue/plugins/webplugin_delegate_impl_mac.mm index dd3a83b..614f1d2 100644 --- a/webkit/glue/plugins/webplugin_delegate_impl_mac.mm +++ b/webkit/glue/plugins/webplugin_delegate_impl_mac.mm @@ -258,16 +258,16 @@ WebPluginDelegateImpl::WebPluginDelegateImpl( layer_(nil), surface_(NULL), renderer_(nil), - plugin_has_focus_(false), - has_webkit_focus_(false), - containing_view_has_focus_(false), containing_window_has_focus_(false), initial_window_focus_(false), container_is_visible_(false), have_called_set_window_(false), external_drag_tracker_(new ExternalDragTracker()), handle_event_depth_(0), - first_set_window_call_(true) { + first_set_window_call_(true), + plugin_has_focus_(false), + has_webkit_focus_(false), + containing_view_has_focus_(true) { memset(&window_, 0, sizeof(window_)); #ifndef NP_NO_CARBON memset(&np_cg_context_, 0, sizeof(np_cg_context_)); @@ -466,15 +466,6 @@ void WebPluginDelegateImpl::Print(CGContextRef context) { NOTIMPLEMENTED(); } -void WebPluginDelegateImpl::SetFocus(bool focused) { - // This is called when internal WebKit focus (the focused element on the page) - // changes, but plugins need to know about actual first responder status, so - // we have an extra layer of focus tracking. - has_webkit_focus_ = focused; - if (containing_view_has_focus_) - SetPluginHasFocus(focused); -} - bool WebPluginDelegateImpl::PlatformHandleInputEvent( const WebInputEvent& event, WebCursorInfo* cursor_info) { DCHECK(cursor_info != NULL); @@ -823,13 +814,9 @@ void WebPluginDelegateImpl::SetWindowHasFocus(bool has_focus) { } } -void WebPluginDelegateImpl::SetPluginHasFocus(bool has_focus) { +bool WebPluginDelegateImpl::PlatformSetPluginHasFocus(bool focused) { if (!have_called_set_window_) - return; - - if (has_focus == plugin_has_focus_) - return; - plugin_has_focus_ = has_focus; + return false; ScopedActiveDelegate active_delegate(this); @@ -837,7 +824,7 @@ void WebPluginDelegateImpl::SetPluginHasFocus(bool has_focus) { #ifndef NP_NO_CARBON case NPEventModelCarbon: { NPEvent focus_event = { 0 }; - if (plugin_has_focus_) + if (focused) focus_event.what = NPEventType_GetFocusEvent; else focus_event.what = NPEventType_LoseFocusEvent; @@ -850,16 +837,12 @@ void WebPluginDelegateImpl::SetPluginHasFocus(bool has_focus) { NPCocoaEvent focus_event; memset(&focus_event, 0, sizeof(focus_event)); focus_event.type = NPCocoaEventFocusChanged; - focus_event.data.focus.hasFocus = plugin_has_focus_; + focus_event.data.focus.hasFocus = focused; instance()->NPP_HandleEvent(&focus_event); break; } } -} - -void WebPluginDelegateImpl::SetContentAreaHasFocus(bool has_focus) { - containing_view_has_focus_ = has_focus; - SetPluginHasFocus(containing_view_has_focus_ && has_webkit_focus_); + return true; } void WebPluginDelegateImpl::SetContainerVisibility(bool is_visible) { @@ -893,8 +876,8 @@ void WebPluginDelegateImpl::SetContainerVisibility(bool is_visible) { instance()->webplugin()->InvalidateRect(gfx::Rect()); } -void WebPluginDelegateImpl::WindowFrameChanged(gfx::Rect window_frame, - gfx::Rect view_frame) { +void WebPluginDelegateImpl::WindowFrameChanged(const gfx::Rect& window_frame, + const gfx::Rect& view_frame) { instance()->set_window_frame(window_frame); SetContentAreaOrigin(gfx::Point(view_frame.x(), view_frame.y())); } diff --git a/webkit/glue/plugins/webplugin_delegate_impl_win.cc b/webkit/glue/plugins/webplugin_delegate_impl_win.cc index 7a2e314..782f873 100644 --- a/webkit/glue/plugins/webplugin_delegate_impl_win.cc +++ b/webkit/glue/plugins/webplugin_delegate_impl_win.cc @@ -265,7 +265,10 @@ WebPluginDelegateImpl::WebPluginDelegateImpl( user_gesture_msg_factory_(this), handle_event_depth_(0), mouse_hook_(NULL), - first_set_window_call_(true) { + first_set_window_call_(true), + plugin_has_focus_(false), + has_webkit_focus_(false), + containing_view_has_focus_(true) { memset(&window_, 0, sizeof(window_)); const WebPluginInfo& plugin_info = instance_->plugin_lib()->plugin_info(); @@ -1051,7 +1054,7 @@ void WebPluginDelegateImpl::WindowlessSetWindow() { DCHECK(err == NPERR_NO_ERROR); } -void WebPluginDelegateImpl::SetFocus(bool focused) { +bool WebPluginDelegateImpl::PlatformSetPluginHasFocus(bool focused) { DCHECK(instance()->windowless()); NPEvent focus_event; @@ -1060,6 +1063,7 @@ void WebPluginDelegateImpl::SetFocus(bool focused) { focus_event.lParam = 0; instance()->NPP_HandleEvent(&focus_event); + return true; } static bool NPEventFromWebMouseEvent(const WebMouseEvent& event, |