summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorbrettw@chromium.org <brettw@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2010-12-22 20:36:46 +0000
committerbrettw@chromium.org <brettw@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2010-12-22 20:36:46 +0000
commit719b36f60b1731c3260825ef281d10b252d96b65 (patch)
tree742fbd3353bd152763efe412495182f564a07144
parentca2b1cbcace07670d6631bfe226ffc906c009453 (diff)
downloadchromium_src-719b36f60b1731c3260825ef281d10b252d96b65.zip
chromium_src-719b36f60b1731c3260825ef281d10b252d96b65.tar.gz
chromium_src-719b36f60b1731c3260825ef281d10b252d96b65.tar.bz2
Add an additional level of optimization for PPAPI plugins to paint without
doing a WebKit paint. Currently, this will not get triggered very much because the % coverage required for combining rects in the paint manager is so low. I'm going to try tweaking that but want to do it in another CL. TEST=none BUG=none Review URL: http://codereview.chromium.org/6020007 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@69974 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r--chrome/renderer/pepper_plugin_delegate_impl.cc13
-rw-r--r--chrome/renderer/pepper_plugin_delegate_impl.h2
-rw-r--r--chrome/renderer/render_view.cc2
-rw-r--r--chrome/renderer/render_view.h2
-rw-r--r--chrome/renderer/render_widget.cc59
-rw-r--r--chrome/renderer/render_widget.h19
-rw-r--r--chrome/renderer/render_widget_fullscreen_pepper.cc13
-rw-r--r--chrome/renderer/render_widget_fullscreen_pepper.h2
8 files changed, 82 insertions, 30 deletions
diff --git a/chrome/renderer/pepper_plugin_delegate_impl.cc b/chrome/renderer/pepper_plugin_delegate_impl.cc
index e223202..6e31439 100644
--- a/chrome/renderer/pepper_plugin_delegate_impl.cc
+++ b/chrome/renderer/pepper_plugin_delegate_impl.cc
@@ -379,8 +379,10 @@ PepperPluginDelegateImpl::CreatePepperPlugin(const FilePath& path) {
IPC::ChannelHandle channel_handle;
render_view_->Send(new ViewHostMsg_OpenChannelToPepperPlugin(
path, &plugin_process_handle, &channel_handle));
- if (channel_handle.name.empty())
- return scoped_refptr<webkit::ppapi::PluginModule>(); // Couldn't be initialized.
+ if (channel_handle.name.empty()) {
+ // Couldn't be initialized.
+ return scoped_refptr<webkit::ppapi::PluginModule>();
+ }
// Create a new HostDispatcher for the proxying, and hook it to a new
// PluginModule.
@@ -435,7 +437,8 @@ void PepperPluginDelegateImpl::ViewFlushedPaint() {
}
}
-bool PepperPluginDelegateImpl::GetBitmapForOptimizedPluginPaint(
+webkit::ppapi::PluginInstance*
+PepperPluginDelegateImpl::GetBitmapForOptimizedPluginPaint(
const gfx::Rect& paint_bounds,
TransportDIB** dib,
gfx::Rect* location,
@@ -446,9 +449,9 @@ bool PepperPluginDelegateImpl::GetBitmapForOptimizedPluginPaint(
webkit::ppapi::PluginInstance* instance = *i;
if (instance->GetBitmapForOptimizedPluginPaint(
paint_bounds, dib, location, clip))
- return true;
+ return *i;
}
- return false;
+ return NULL;
}
void PepperPluginDelegateImpl::InstanceCreated(
diff --git a/chrome/renderer/pepper_plugin_delegate_impl.h b/chrome/renderer/pepper_plugin_delegate_impl.h
index 783cfc8..cd732fe 100644
--- a/chrome/renderer/pepper_plugin_delegate_impl.h
+++ b/chrome/renderer/pepper_plugin_delegate_impl.h
@@ -57,7 +57,7 @@ class PepperPluginDelegateImpl
// Called by RenderView to implement the corresponding function in its base
// class RenderWidget (see that for more).
- bool GetBitmapForOptimizedPluginPaint(
+ webkit::ppapi::PluginInstance* GetBitmapForOptimizedPluginPaint(
const gfx::Rect& paint_bounds,
TransportDIB** dib,
gfx::Rect* location,
diff --git a/chrome/renderer/render_view.cc b/chrome/renderer/render_view.cc
index 3522f12..7a84c11 100644
--- a/chrome/renderer/render_view.cc
+++ b/chrome/renderer/render_view.cc
@@ -5228,7 +5228,7 @@ void RenderView::DidFlushPaint() {
}
}
-bool RenderView::GetBitmapForOptimizedPluginPaint(
+webkit::ppapi::PluginInstance* RenderView::GetBitmapForOptimizedPluginPaint(
const gfx::Rect& paint_bounds,
TransportDIB** dib,
gfx::Rect* location,
diff --git a/chrome/renderer/render_view.h b/chrome/renderer/render_view.h
index af7b969..1f97fa6 100644
--- a/chrome/renderer/render_view.h
+++ b/chrome/renderer/render_view.h
@@ -679,7 +679,7 @@ class RenderView : public RenderWidget,
const gfx::Rect& resizer_rect);
virtual void DidInitiatePaint();
virtual void DidFlushPaint();
- virtual bool GetBitmapForOptimizedPluginPaint(
+ virtual webkit::ppapi::PluginInstance* GetBitmapForOptimizedPluginPaint(
const gfx::Rect& paint_bounds,
TransportDIB** dib,
gfx::Rect* location,
diff --git a/chrome/renderer/render_widget.cc b/chrome/renderer/render_widget.cc
index 041fcd9..9cf323c 100644
--- a/chrome/renderer/render_widget.cc
+++ b/chrome/renderer/render_widget.cc
@@ -29,6 +29,7 @@
#include "third_party/WebKit/WebKit/chromium/public/WebSize.h"
#include "webkit/glue/webkit_glue.h"
#include "webkit/plugins/npapi/webplugin.h"
+#include "webkit/plugins/ppapi/ppapi_plugin_instance.h"
#if defined(OS_POSIX)
#include "ipc/ipc_channel_posix.h"
@@ -389,6 +390,7 @@ void RenderWidget::ClearFocus() {
void RenderWidget::PaintRect(const gfx::Rect& rect,
const gfx::Point& canvas_origin,
skia::PlatformCanvas* canvas) {
+
canvas->save();
// Bring the canvas into the coordinate system of the paint rect.
@@ -406,13 +408,45 @@ void RenderWidget::PaintRect(const gfx::Rect& rect,
canvas->drawPaint(paint);
}
- webwidget_->paint(webkit_glue::ToWebCanvas(canvas), rect);
-
- PaintDebugBorder(rect, canvas);
+ // First see if this rect is a plugin that can paint itself faster.
+ TransportDIB* optimized_dib = NULL;
+ gfx::Rect optimized_copy_rect, optimized_copy_location;
+ webkit::ppapi::PluginInstance* optimized_instance =
+ GetBitmapForOptimizedPluginPaint(rect, &optimized_dib,
+ &optimized_copy_location,
+ &optimized_copy_rect);
+ if (optimized_instance) {
+ // This plugin can be optimize-painted and we can just ask it to paint
+ // itself. We don't actually need the TransportDIB in this case.
+ //
+ // This is an optimization for PPAPI plugins that know they're on top of
+ // the page content. If this rect is inside such a plugin, we can save some
+ // time and avoid re-rendering the page content which we know will be
+ // covered by the plugin later (this time can be significant, especially
+ // for a playing movie that is invalidating a lot).
+ //
+ // In the plugin movie case, hopefully the similar call to
+ // GetBitmapForOptimizedPluginPaint in DoDeferredUpdate handles the
+ // painting, because that avoids copying the plugin image to a different
+ // paint rect. Unfortunately, if anything on the page is animating other
+ // than the movie, it break this optimization since the union of the
+ // invalid regions will be larger than the plugin.
+ //
+ // This code optimizes that case, where we can still avoid painting in
+ // WebKit and filling the background (which can be slow) and just painting
+ // the plugin. Unlike the DoDeferredUpdate case, an extra copy is still
+ // required.
+ optimized_instance->Paint(webkit_glue::ToWebCanvas(canvas),
+ optimized_copy_location, optimized_copy_location);
+ } else {
+ // Normal painting case.
+ webwidget_->paint(webkit_glue::ToWebCanvas(canvas), rect);
- // Flush to underlying bitmap. TODO(darin): is this needed?
- canvas->getTopPlatformDevice().accessBitmap(false);
+ // Flush to underlying bitmap. TODO(darin): is this needed?
+ canvas->getTopPlatformDevice().accessBitmap(false);
+ }
+ PaintDebugBorder(rect, canvas);
canvas->restore();
}
@@ -475,6 +509,15 @@ void RenderWidget::DoDeferredUpdate() {
// A plugin may be able to do an optimized paint. First check this, in which
// case we can skip all of the bitmap generation and regular paint code.
+ // This optimization allows PPAPI plugins that declare themselves on top of
+ // the page (like a traditional windowed plugin) to be able to animate (think
+ // movie playing) without repeatedly re-painting the page underneath, or
+ // copying the plugin backing store (since we can send the plugin's backing
+ // store directly to the browser).
+ //
+ // This optimization only works when the entire invalid region is contained
+ // within the plugin. There is a related optimization in PaintRect for the
+ // case where there may be multiple invalid regions.
TransportDIB::Id dib_id = TransportDIB::Id();
TransportDIB* dib = NULL;
std::vector<gfx::Rect> copy_rects;
@@ -864,13 +907,13 @@ void RenderWidget::OnSetTextDirection(WebTextDirection direction) {
webwidget_->setTextDirection(direction);
}
-bool RenderWidget::GetBitmapForOptimizedPluginPaint(
+webkit::ppapi::PluginInstance* RenderWidget::GetBitmapForOptimizedPluginPaint(
const gfx::Rect& paint_bounds,
TransportDIB** dib,
gfx::Rect* location,
gfx::Rect* clip) {
- // Normal RenderWidgets don't support optimized plugin painting.
- return false;
+ // Bare RenderWidgets don't support optimized plugin painting.
+ return NULL;
}
void RenderWidget::SetHidden(bool hidden) {
diff --git a/chrome/renderer/render_widget.h b/chrome/renderer/render_widget.h
index 92826e9..bf542bf 100644
--- a/chrome/renderer/render_widget.h
+++ b/chrome/renderer/render_widget.h
@@ -49,8 +49,12 @@ struct WebPopupMenuInfo;
namespace webkit {
namespace npapi {
struct WebPluginGeometry;
-}
-}
+} // namespace npapi
+
+namespace ppapi {
+class PluginInstance;
+} // namespace ppapi
+} // namespace webkit
// RenderWidget provides a communication bridge between a WebWidget and
// a RenderWidgetHost, the latter of which lives in a different process.
@@ -202,13 +206,14 @@ class RenderWidget : public IPC::Channel::Listener,
// Detects if a suitable opaque plugin covers the given paint bounds with no
// compositing necessary.
//
- // Returns true if the paint can be handled by just blitting the plugin
- // bitmap. In this case, the location, clipping, and ID of the backing store
- // will be filled into the given output parameters.
+ // Returns the plugin instance that's the source of the paint if the paint
+ // can be handled by just blitting the plugin bitmap. In this case, the
+ // location, clipping, and ID of the backing store will be filled into the
+ // given output parameters.
//
- // A return value of false means optimized painting can not be used and we
+ // A return value of null means optimized painting can not be used and we
// should continue with the normal painting code path.
- virtual bool GetBitmapForOptimizedPluginPaint(
+ virtual webkit::ppapi::PluginInstance* GetBitmapForOptimizedPluginPaint(
const gfx::Rect& paint_bounds,
TransportDIB** dib,
gfx::Rect* location,
diff --git a/chrome/renderer/render_widget_fullscreen_pepper.cc b/chrome/renderer/render_widget_fullscreen_pepper.cc
index 3df4be2..42b7a93 100644
--- a/chrome/renderer/render_widget_fullscreen_pepper.cc
+++ b/chrome/renderer/render_widget_fullscreen_pepper.cc
@@ -217,14 +217,15 @@ void RenderWidgetFullscreenPepper::GenerateFullRepaint() {
didInvalidateRect(gfx::Rect(size_.width(), size_.height()));
}
-bool RenderWidgetFullscreenPepper::GetBitmapForOptimizedPluginPaint(
+webkit::ppapi::PluginInstance*
+RenderWidgetFullscreenPepper::GetBitmapForOptimizedPluginPaint(
const gfx::Rect& paint_bounds,
TransportDIB** dib,
gfx::Rect* location,
gfx::Rect* clip) {
- if (plugin_) {
- return plugin_->GetBitmapForOptimizedPluginPaint(
- paint_bounds, dib, location, clip);
- }
- return false;
+ if (plugin_ &&
+ plugin_->GetBitmapForOptimizedPluginPaint(paint_bounds, dib,
+ location, clip))
+ return plugin_;
+ return NULL;
}
diff --git a/chrome/renderer/render_widget_fullscreen_pepper.h b/chrome/renderer/render_widget_fullscreen_pepper.h
index 4d74b1d..7133ec5 100644
--- a/chrome/renderer/render_widget_fullscreen_pepper.h
+++ b/chrome/renderer/render_widget_fullscreen_pepper.h
@@ -47,7 +47,7 @@ class RenderWidgetFullscreenPepper : public RenderWidgetFullscreen {
virtual void DidInitiatePaint();
virtual void DidFlushPaint();
virtual void Close();
- virtual bool GetBitmapForOptimizedPluginPaint(
+ virtual webkit::ppapi::PluginInstance* GetBitmapForOptimizedPluginPaint(
const gfx::Rect& paint_bounds,
TransportDIB** dib,
gfx::Rect* location,