diff options
author | Derek Sollenberger <djsollen@google.com> | 2010-03-16 16:29:40 -0400 |
---|---|---|
committer | Derek Sollenberger <djsollen@google.com> | 2010-03-16 16:30:38 -0400 |
commit | 1d7ddf2fb889b97549e1041bbbf53e481b4ced2c (patch) | |
tree | 0e8c6993f084b383a6b829c135cf1145a2dbd121 | |
parent | bfcd11290caa86fe38f2f6869cb3959f5853171a (diff) | |
download | external_webkit-1d7ddf2fb889b97549e1041bbbf53e481b4ced2c.zip external_webkit-1d7ddf2fb889b97549e1041bbbf53e481b4ced2c.tar.gz external_webkit-1d7ddf2fb889b97549e1041bbbf53e481b4ced2c.tar.bz2 |
Ensure a plugin is not shown if it is completely obscured by other
html content.
Change-Id: Iffcc30d47428708842ac5dddee41cc611d879c1c
-rw-r--r-- | WebCore/plugins/android/PluginViewAndroid.cpp | 7 | ||||
-rw-r--r-- | WebKit/android/plugins/PluginWidgetAndroid.cpp | 37 | ||||
-rw-r--r-- | WebKit/android/plugins/PluginWidgetAndroid.h | 9 |
3 files changed, 41 insertions, 12 deletions
diff --git a/WebCore/plugins/android/PluginViewAndroid.cpp b/WebCore/plugins/android/PluginViewAndroid.cpp index 2da482f..ea72e23 100644 --- a/WebCore/plugins/android/PluginViewAndroid.cpp +++ b/WebCore/plugins/android/PluginViewAndroid.cpp @@ -591,7 +591,7 @@ void PluginView::show() Widget::show(); if (platformPluginWidget()) - platformPluginWidget()->updateSurfaceIfNeeded(); + platformPluginWidget()->layoutSurface(); } @@ -601,7 +601,7 @@ void PluginView::hide() Widget::hide(); if (platformPluginWidget()) - platformPluginWidget()->updateSurfaceIfNeeded(); + platformPluginWidget()->layoutSurface(); } void PluginView::setParentVisible(bool visible) { @@ -612,7 +612,7 @@ void PluginView::setParentVisible(bool visible) { Widget::setParentVisible(visible); if (platformPluginWidget()) - platformPluginWidget()->updateSurfaceIfNeeded(); + platformPluginWidget()->layoutSurface(); } @@ -638,6 +638,7 @@ void PluginView::paint(GraphicsContext* context, const IntRect& rect) notification of its global position change. */ updatePluginWidget(); + m_window->setSurfaceClip(context->platformContext()->mCanvas->getTotalClip().getBounds()); } else { m_window->inval(rect, false); context->save(); diff --git a/WebKit/android/plugins/PluginWidgetAndroid.cpp b/WebKit/android/plugins/PluginWidgetAndroid.cpp index fd46309..c4b7e97 100644 --- a/WebKit/android/plugins/PluginWidgetAndroid.cpp +++ b/WebKit/android/plugins/PluginWidgetAndroid.cpp @@ -70,6 +70,7 @@ PluginWidgetAndroid::PluginWidgetAndroid(WebCore::PluginView* view) m_embeddedView = NULL; m_embeddedViewAttached = false; m_acceptEvents = false; + m_isSurfaceClippedOut = false; } PluginWidgetAndroid::~PluginWidgetAndroid() { @@ -124,7 +125,7 @@ void PluginWidgetAndroid::setWindow(NPWindow* window, bool isTransparent) { m_pluginBounds.fLeft, m_pluginBounds.fTop, m_pluginBounds.fRight, m_pluginBounds.fBottom); - updateSurfaceIfNeeded(m_pluginBounds != oldPluginBounds); + layoutSurface(m_pluginBounds != oldPluginBounds); if (m_drawingModel != kSurface_ANPDrawingModel) { m_flipPixelRef->safeUnref(); @@ -209,16 +210,36 @@ void PluginWidgetAndroid::draw(SkCanvas* canvas) { } } -void PluginWidgetAndroid::updateSurfaceIfNeeded(bool pluginBoundsChanged) { +void PluginWidgetAndroid::setSurfaceClip(const SkIRect& clip) { if (m_drawingModel != kSurface_ANPDrawingModel) return; - PLUGIN_LOG("%p Plugin Visible self=[%d] parent=[%d]", m_pluginView->instance(), - m_pluginView->isSelfVisible(), m_pluginView->isParentVisible()); + /* don't display surfaces that are either entirely clipped or only 1x1 in + size. It appears that when an element is absolutely positioned and has + been completely clipped in CSS that webkit still sends a clip of 1x1. + */ + bool clippedOut = (clip.width() <= 1 && clip.height() <= 1); + if(clippedOut != m_isSurfaceClippedOut) { + m_isSurfaceClippedOut = clippedOut; + layoutSurface(); + } +} + +void PluginWidgetAndroid::layoutSurface(bool pluginBoundsChanged) { + + if (m_drawingModel != kSurface_ANPDrawingModel) + return; + + + + bool displayPlugin = m_pluginView->isVisible() && !m_isSurfaceClippedOut; + PLUGIN_LOG("%p DisplayPlugin[%d] visible=[%d] clipped=[%d]", + m_pluginView->instance(), displayPlugin, + m_pluginView->isVisible(), m_isSurfaceClippedOut); // if the surface does not exist then create a new surface - if (!m_embeddedView && m_pluginView->isVisible()) { + if (!m_embeddedView && displayPlugin) { WebCore::PluginPackage* pkg = m_pluginView->plugin(); NPP instance = m_pluginView->instance(); @@ -237,16 +258,16 @@ void PluginWidgetAndroid::updateSurfaceIfNeeded(bool pluginBoundsChanged) { m_embeddedViewAttached = true; } // if the view is unattached but visible then attach it - } else if (m_embeddedView && !m_embeddedViewAttached && m_pluginView->isVisible() && !m_isFullScreen) { + } else if (m_embeddedView && !m_embeddedViewAttached && displayPlugin && !m_isFullScreen) { m_core->updateSurface(m_embeddedView, m_pluginWindow->x, m_pluginWindow->y, m_pluginWindow->width, m_pluginWindow->height); m_embeddedViewAttached = true; // if the view is attached but invisible then remove it - } else if (m_embeddedView && m_embeddedViewAttached && !m_pluginView->isVisible()) { + } else if (m_embeddedView && m_embeddedViewAttached && !displayPlugin) { m_core->destroySurface(m_embeddedView); m_embeddedViewAttached = false; // if the plugin's bounds have changed and it's visible then update it - } else if (pluginBoundsChanged && m_pluginView->isVisible() && !m_isFullScreen) { + } else if (pluginBoundsChanged && displayPlugin && !m_isFullScreen) { m_core->updateSurface(m_embeddedView, m_pluginWindow->x, m_pluginWindow->y, m_pluginWindow->width, m_pluginWindow->height); diff --git a/WebKit/android/plugins/PluginWidgetAndroid.h b/WebKit/android/plugins/PluginWidgetAndroid.h index 233548d..2e55aaa 100644 --- a/WebKit/android/plugins/PluginWidgetAndroid.h +++ b/WebKit/android/plugins/PluginWidgetAndroid.h @@ -151,7 +151,13 @@ struct PluginWidgetAndroid { changed then we need to ensure the surface is added or removed from the view system. */ - void updateSurfaceIfNeeded(bool pluginBoundsChanged = false); + void layoutSurface(bool pluginBoundsChanged = false); + + /** send the surface the currently visible portion of the plugin. This is not + the portion of the plugin visible on the screen but rather the portion of + the plugin that is not obscured by other HTML content. + */ + void setSurfaceClip(const SkIRect& clip); /** Called when a plugin wishes to be zoomed and centered in the current view. */ @@ -177,6 +183,7 @@ private: jobject m_embeddedView; bool m_embeddedViewAttached; bool m_acceptEvents; + bool m_isSurfaceClippedOut; /* We limit the number of rectangles to minimize storage and ensure adequate speed. |