summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--base/base.gyp2
-rw-r--r--base/gfx/blit.cc87
-rw-r--r--base/gfx/blit.h47
-rw-r--r--chrome/plugin/webplugin_proxy.cc11
-rw-r--r--chrome/renderer/webplugin_delegate_proxy.cc106
-rw-r--r--webkit/glue/plugins/webplugin_delegate_impl_gtk.cc26
6 files changed, 160 insertions, 119 deletions
diff --git a/base/base.gyp b/base/base.gyp
index e281a43..8aa8a3a 100644
--- a/base/base.gyp
+++ b/base/base.gyp
@@ -538,6 +538,8 @@
'type': '<(library)',
'msvs_guid': 'A508ADD3-CECE-4E0F-8448-2F5E454DF551',
'sources': [
+ 'gfx/blit.cc',
+ 'gfx/blit.h',
'gfx/gdi_util.cc',
'gfx/gdi_util.h',
'gfx/gtk_native_view_id_manager.cc',
diff --git a/base/gfx/blit.cc b/base/gfx/blit.cc
new file mode 100644
index 0000000..2965c4c
--- /dev/null
+++ b/base/gfx/blit.cc
@@ -0,0 +1,87 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "base/gfx/blit.h"
+
+#if defined(OS_LINUX)
+#include <cairo/cairo.h>
+#endif
+
+#include "base/gfx/point.h"
+#include "base/gfx/rect.h"
+#if defined(OS_MACOSX)
+#include "base/scoped_cftyperef.h"
+#endif
+#include "skia/ext/platform_canvas.h"
+#include "skia/ext/platform_device.h"
+
+namespace gfx {
+
+void BlitContextToContext(NativeDrawingContext dst_context,
+ const Rect& dst_rect,
+ NativeDrawingContext src_context,
+ const Point& src_origin) {
+#if defined(OS_WIN)
+ BitBlt(dst_context, dst_rect.x(), dst_rect.y(),
+ dst_rect.width(), dst_rect.height(),
+ src_context, src_origin.x(), src_origin.y(), SRCCOPY);
+#elif defined(OS_MACOSX)
+ Rect src_rect(src_origin, dst_rect.size());
+ scoped_cftyperef<CGImageRef>
+ src_image(CGBitmapContextCreateImage(src_context));
+ scoped_cftyperef<CGImageRef> src_sub_image(
+ CGImageCreateWithImageInRect(src_image, src_rect.ToCGRect()));
+ CGContextDrawImage(dst_context, dst_rect.ToCGRect(), src_sub_image);
+#elif defined(OS_LINUX)
+ cairo_save(dst_context);
+ double surface_x = src_origin.x();
+ double surface_y = src_origin.y();
+ cairo_user_to_device(src_context, &surface_x, &surface_y);
+ cairo_set_source_surface(dst_context, cairo_get_target(src_context),
+ dst_rect.x()-surface_x, dst_rect.y()-surface_y);
+ cairo_rectangle(dst_context, dst_rect.x(), dst_rect.y(),
+ dst_rect.width(), dst_rect.height());
+ cairo_clip(dst_context);
+ cairo_paint(dst_context);
+ cairo_restore(dst_context);
+#endif
+}
+
+static NativeDrawingContext GetContextFromCanvas(
+ skia::PlatformCanvas *canvas) {
+ skia::PlatformDevice& device = canvas->getTopPlatformDevice();
+#if defined(OS_WIN)
+ return device.getBitmapDC();
+#elif defined(OS_MACOSX)
+ return device.GetBitmapContext();
+#elif defined(OS_LINUX)
+ return device.beginPlatformPaint();
+#endif
+}
+
+void BlitContextToCanvas(skia::PlatformCanvas *dst_canvas,
+ const Rect& dst_rect,
+ NativeDrawingContext src_context,
+ const Point& src_origin) {
+ BlitContextToContext(GetContextFromCanvas(dst_canvas), dst_rect,
+ src_context, src_origin);
+}
+
+void BlitCanvasToContext(NativeDrawingContext dst_context,
+ const Rect& dst_rect,
+ skia::PlatformCanvas *src_canvas,
+ const Point& src_origin) {
+ BlitContextToContext(dst_context, dst_rect,
+ GetContextFromCanvas(src_canvas), src_origin);
+}
+
+void BlitCanvasToCanvas(skia::PlatformCanvas *dst_canvas,
+ const Rect& dst_rect,
+ skia::PlatformCanvas *src_canvas,
+ const Point& src_origin) {
+ BlitContextToContext(GetContextFromCanvas(dst_canvas), dst_rect,
+ GetContextFromCanvas(src_canvas), src_origin);
+}
+
+} // namespace gfx
diff --git a/base/gfx/blit.h b/base/gfx/blit.h
new file mode 100644
index 0000000..25f7a5e
--- /dev/null
+++ b/base/gfx/blit.h
@@ -0,0 +1,47 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef BASE_GFX_BLIT_H_
+#define BASE_GFX_BLIT_H_
+
+#include "base/gfx/native_widget_types.h"
+#include "base/gfx/point.h"
+#include "base/gfx/rect.h"
+
+namespace skia {
+class PlatformCanvas;
+} // namespace skia
+
+namespace gfx {
+
+class Point;
+class Rect;
+
+// Blits a rectangle from the source context into the destination context.
+void BlitContextToContext(NativeDrawingContext dst_context,
+ const Rect& dst_rect,
+ NativeDrawingContext src_context,
+ const Point& src_origin);
+
+// Blits a rectangle from the source context into the destination canvas.
+void BlitContextToCanvas(skia::PlatformCanvas *dst_canvas,
+ const Rect& dst_rect,
+ NativeDrawingContext src_context,
+ const Point& src_origin);
+
+// Blits a rectangle from the source canvas into the destination context.
+void BlitCanvasToContext(NativeDrawingContext dst_context,
+ const Rect& dst_rect,
+ skia::PlatformCanvas *src_canvas,
+ const Point& src_origin);
+
+// Blits a rectangle from the source canvas into the destination canvas.
+void BlitCanvasToCanvas(skia::PlatformCanvas *dst_canvas,
+ const Rect& dst_rect,
+ skia::PlatformCanvas *src_canvas,
+ const Point& src_origin);
+
+} // namespace gfx
+
+#endif // BASE_GFX_BLIT_H_
diff --git a/chrome/plugin/webplugin_proxy.cc b/chrome/plugin/webplugin_proxy.cc
index 3d34674..38cd306f 100644
--- a/chrome/plugin/webplugin_proxy.cc
+++ b/chrome/plugin/webplugin_proxy.cc
@@ -8,6 +8,7 @@
#if defined(OS_WIN)
#include "app/win_util.h"
#endif
+#include "base/gfx/blit.h"
#include "base/scoped_handle.h"
#include "base/shared_memory.h"
#include "base/singleton.h"
@@ -426,17 +427,15 @@ void WebPluginProxy::Paint(const gfx::Rect& rect) {
delegate_->Paint(windowless_context_, rect);
CGContextRestoreGState(windowless_context_);
#else
+ if (background_canvas_.get()) {
+ BlitCanvasToCanvas(windowless_canvas_.get(), rect,
+ background_canvas_.get(), rect.origin());
+ }
cairo_t* cairo =
windowless_canvas_->getTopPlatformDevice().beginPlatformPaint();
cairo_save(cairo);
cairo_rectangle(cairo, rect.x(), rect.y(), rect.width(), rect.height());
cairo_clip(cairo);
- if (background_canvas_.get()) {
- cairo_t *background =
- background_canvas_->getTopPlatformDevice().beginPlatformPaint();
- cairo_set_source_surface(cairo, cairo_get_target(background), 0, 0);
- cairo_paint(cairo);
- }
cairo_translate(cairo, -delegate_->GetRect().x(), -delegate_->GetRect().y());
delegate_->Paint(cairo, offset_rect);
cairo_restore(cairo);
diff --git a/chrome/renderer/webplugin_delegate_proxy.cc b/chrome/renderer/webplugin_delegate_proxy.cc
index 4b87f7e..016c851 100644
--- a/chrome/renderer/webplugin_delegate_proxy.cc
+++ b/chrome/renderer/webplugin_delegate_proxy.cc
@@ -17,6 +17,7 @@
#include "base/logging.h"
#include "base/ref_counted.h"
#include "base/string_util.h"
+#include "base/gfx/blit.h"
#include "base/gfx/size.h"
#include "base/gfx/native_widget_types.h"
#include "chrome/common/child_process_logging.h"
@@ -523,34 +524,8 @@ void WebPluginDelegateProxy::Paint(gfx::NativeDrawingContext context,
bool background_changed = false;
if (background_store_canvas_.get() && BackgroundChanged(context, rect)) {
background_changed = true;
-#if defined(OS_WIN)
- HDC background_hdc =
- background_store_canvas_->getTopPlatformDevice().getBitmapDC();
- BitBlt(background_hdc, offset_rect.x(), offset_rect.y(),
- rect.width(), rect.height(), context, rect.x(), rect.y(), SRCCOPY);
-#elif defined(OS_MACOSX)
- CGContextRef background_context =
- background_store_canvas_->getTopPlatformDevice().GetBitmapContext();
- scoped_cftyperef<CGImageRef>
- background_image(CGBitmapContextCreateImage(background_context));
- scoped_cftyperef<CGImageRef> sub_image(
- CGImageCreateWithImageInRect(background_image, offset_rect.ToCGRect()));
- CGContextDrawImage(context, rect.ToCGRect(), sub_image);
-#else
- cairo_t *cairo =
- background_store_canvas_->getTopPlatformDevice().beginPlatformPaint();
- cairo_save(cairo);
- double surface_x = plugin_rect_.x();
- double surface_y = plugin_rect_.y();
- cairo_user_to_device(context, &surface_x, &surface_y);
- cairo_set_source_surface(cairo, cairo_get_target(context),
- -surface_x, -surface_y);
- cairo_rectangle(cairo, offset_rect.x(), offset_rect.y(),
- offset_rect.width(), offset_rect.height());
- cairo_clip(cairo);
- cairo_paint(cairo);
- cairo_restore(cairo);
-#endif
+ BlitContextToCanvas(background_store_canvas_.get(), offset_rect,
+ context, rect.origin());
}
if (background_changed || !backing_store_painted_.Contains(offset_rect)) {
@@ -558,29 +533,8 @@ void WebPluginDelegateProxy::Paint(gfx::NativeDrawingContext context,
CopyFromTransportToBacking(offset_rect);
}
-#if defined(OS_WIN)
- HDC backing_hdc = backing_store_canvas_->getTopPlatformDevice().getBitmapDC();
- BitBlt(context, rect.x(), rect.y(), rect.width(), rect.height(), backing_hdc,
- offset_rect.x(), offset_rect.y(), SRCCOPY);
-#elif defined(OS_MACOSX)
- CGContextRef backing_context =
- backing_store_canvas_->getTopPlatformDevice().GetBitmapContext();
- scoped_cftyperef<CGImageRef>
- backing_image(CGBitmapContextCreateImage(backing_context));
- scoped_cftyperef<CGImageRef> sub_image(
- CGImageCreateWithImageInRect(backing_image, offset_rect.ToCGRect()));
- CGContextDrawImage(context, rect.ToCGRect(), sub_image);
-#else
- cairo_save(context);
- cairo_t *cairo =
- backing_store_canvas_->getTopPlatformDevice().beginPlatformPaint();
- cairo_set_source_surface(context, cairo_get_target(cairo),
- plugin_rect_.x(), plugin_rect_.y());
- cairo_rectangle(context, rect.x(), rect.y(), rect.width(), rect.height());
- cairo_paint(context);
- cairo_clip(context);
- cairo_restore(context);
-#endif
+ BlitCanvasToContext(context, rect, backing_store_canvas_.get(),
+ offset_rect.origin());
if (invalidate_pending_) {
// Only send the PaintAck message if this paint is in response to an
@@ -941,27 +895,7 @@ void WebPluginDelegateProxy::PaintSadPlugin(gfx::NativeDrawingContext context,
std::max(0, (width - sad_plugin_->width())/2),
std::max(0, (height - sad_plugin_->height())/2));
}
-
-#if defined(OS_WIN)
- skia::PlatformDevice& device = canvas.getTopPlatformDevice();
- device.drawToHDC(context, plugin_rect_.x(), plugin_rect_.y(), NULL);
-#elif defined(OS_LINUX)
- cairo_save(context);
- cairo_t* cairo = canvas.getTopPlatformDevice().beginPlatformPaint();
- cairo_set_source_surface(context, cairo_get_target(cairo),
- plugin_rect_.x(), plugin_rect_.y());
- cairo_rectangle(context, rect.x(), rect.y(), rect.width(), rect.height());
- cairo_clip(context);
- cairo_paint(context);
- cairo_restore(context);
- // We have no endPlatformPaint() on the Linux PlatformDevice.
- // The cairo_t* is owned by the device.
-#elif defined(OS_MACOSX)
- canvas.getTopPlatformDevice().DrawToContext(
- context, plugin_rect_.x(), plugin_rect_.y(), NULL);
-#else
- NOTIMPLEMENTED();
-#endif
+ BlitCanvasToContext(context, plugin_rect_, &canvas, gfx::Point(0, 0));
}
void WebPluginDelegateProxy::CopyFromTransportToBacking(const gfx::Rect& rect) {
@@ -970,32 +904,8 @@ void WebPluginDelegateProxy::CopyFromTransportToBacking(const gfx::Rect& rect) {
}
// Copy the damaged rect from the transport bitmap to the backing store.
-#if defined(OS_WIN)
- HDC backing = backing_store_canvas_->getTopPlatformDevice().getBitmapDC();
- HDC transport = transport_store_canvas_->getTopPlatformDevice().getBitmapDC();
- BitBlt(backing, rect.x(), rect.y(), rect.width(), rect.height(),
- transport, rect.x(), rect.y(), SRCCOPY);
-#elif defined(OS_MACOSX)
- gfx::NativeDrawingContext backing =
- backing_store_canvas_->getTopPlatformDevice().GetBitmapContext();
- gfx::NativeDrawingContext transport =
- transport_store_canvas_->getTopPlatformDevice().GetBitmapContext();
- scoped_cftyperef<CGImageRef> image(CGBitmapContextCreateImage(transport));
- scoped_cftyperef<CGImageRef> sub_image(
- CGImageCreateWithImageInRect(image, rect.ToCGRect()));
- CGContextDrawImage(backing, rect.ToCGRect(), sub_image);
-#else
- cairo_t *cairo =
- backing_store_canvas_->getTopPlatformDevice().beginPlatformPaint();
- cairo_save(cairo);
- cairo_t *transport =
- transport_store_canvas_->getTopPlatformDevice().beginPlatformPaint();
- cairo_set_source_surface(cairo, cairo_get_target(transport), 0, 0);
- cairo_rectangle(cairo, rect.x(), rect.y(), rect.width(), rect.height());
- cairo_clip(cairo);
- cairo_paint(cairo);
- cairo_restore(cairo);
-#endif
+ BlitCanvasToCanvas(backing_store_canvas_.get(), rect,
+ transport_store_canvas_.get(), rect.origin());
backing_store_painted_ = backing_store_painted_.Union(rect);
}
diff --git a/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc b/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc
index 265551a..d107a6d 100644
--- a/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc
+++ b/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc
@@ -12,6 +12,7 @@
#include "base/basictypes.h"
#include "base/file_util.h"
+#include "base/gfx/blit.h"
#include "base/message_loop.h"
#include "base/process_util.h"
#include "base/stats_counters.h"
@@ -516,24 +517,19 @@ void WebPluginDelegateImpl::WindowlessPaint(cairo_t* context,
DCHECK_EQ(err, NPERR_NO_ERROR);
}
+ gfx::Rect pixmap_draw_rect = draw_rect;
+ pixmap_draw_rect.Offset(offset_x, offset_y);
+
gfx::Rect pixmap_rect(0, 0,
- draw_rect.x() + offset_x + draw_rect.width(),
- draw_rect.y() + offset_y + draw_rect.height());
+ pixmap_draw_rect.right(),
+ pixmap_draw_rect.bottom());
EnsurePixmapAtLeastSize(pixmap_rect.width(), pixmap_rect.height());
// Copy the current image into the pixmap, so the plugin can draw over
// this background.
cairo_t* cairo = gdk_cairo_create(pixmap_);
- double surface_x = -offset_x;
- double surface_y = -offset_y;
- cairo_user_to_device(context, &surface_x, &surface_y);
- cairo_set_source_surface(cairo, cairo_get_target(context),
- -surface_x, -surface_y);
- cairo_rectangle(cairo, draw_rect.x() + offset_x, draw_rect.y() + offset_y,
- draw_rect.width(), draw_rect.height());
- cairo_clip(cairo);
- cairo_paint(cairo);
+ BlitContextToContext(cairo, pixmap_draw_rect, context, draw_rect.origin());
cairo_destroy(cairo);
// Construct the paint message, targeting the pixmap.
@@ -542,10 +538,10 @@ void WebPluginDelegateImpl::WindowlessPaint(cairo_t* context,
event.type = GraphicsExpose;
event.display = GDK_DISPLAY();
event.drawable = GDK_PIXMAP_XID(pixmap_);
- event.x = draw_rect.x() + offset_x;
- event.y = draw_rect.y() + offset_y;
- event.width = draw_rect.width();
- event.height = draw_rect.height();
+ event.x = pixmap_draw_rect.x();
+ event.y = pixmap_draw_rect.y();
+ event.width = pixmap_draw_rect.width();
+ event.height = pixmap_draw_rect.height();
// Tell the plugin to paint into the pixmap.
static StatsRate plugin_paint("Plugin.Paint");