Skip to content

Commit

Permalink
Revert 164660 - Change CanvasPaintT from a template to just a subclas…
Browse files Browse the repository at this point in the history
…s of gfx::Canvas. Greatly

simplifies source-code-readability, and will allow us to move the impl into
a .cc file, rather than carry it to every call-site.

This is also a necessary precursor to a subsequent change to remove initialize()
from PlatformCanvas, and make it just a typedef for SkCanvas.
Review URL: https://codereview.chromium.org/11193037

TBR=reed@google.com
Review URL: https://codereview.chromium.org/11347017

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@164666 0039d316-1c4b-4281-b951-d872f2087c98
  • Loading branch information
sergeyu@chromium.org committed Oct 29, 2012
1 parent 2208a74 commit ac14bd6
Show file tree
Hide file tree
Showing 15 changed files with 342 additions and 307 deletions.
4 changes: 1 addition & 3 deletions chrome/browser/ui/gtk/infobars/infobar_container_gtk.cc
Original file line number Diff line number Diff line change
Expand Up @@ -184,9 +184,7 @@ void InfoBarContainerGtk::PaintArrowOn(GtkWidget* widget,
paint.setShader(gradient_shader);
gradient_shader->unref();

gfx::CanvasSkiaPaint canvas_paint(expose, false);
SkCanvas& canvas = *canvas_paint.sk_canvas();

skia::PlatformCanvasPaint canvas(expose, false);
canvas.drawPath(path, paint);

paint.setShader(NULL);
Expand Down
23 changes: 23 additions & 0 deletions skia/ext/canvas_paint.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
// Copyright (c) 2012 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 SKIA_EXT_CANVAS_PAINT_H_
#define SKIA_EXT_CANVAS_PAINT_H_

// This file provides an easy way to include the appropriate CanvasPaint
// header file on your platform.

#if defined(WIN32)
#include "skia/ext/canvas_paint_win.h"
#elif defined(__APPLE__)
#include "skia/ext/canvas_paint_mac.h"
#elif defined(__linux__) || defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__sun)
#if defined(TOOLKIT_GTK)
#include "skia/ext/canvas_paint_gtk.h"
#else
#error "No canvas paint for this platform"
#endif
#endif

#endif // SKIA_EXT_CANVAS_PAINT_H_
23 changes: 23 additions & 0 deletions skia/ext/canvas_paint_common.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
// Copyright (c) 2012 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 SKIA_EXT_CANVAS_PAINT_COMMON_H_
#define SKIA_EXT_CANVAS_PAINT_COMMON_H_

namespace skia {
class PlatformCanvas;

template<class T> inline PlatformCanvas* GetPlatformCanvas(T* t) {
return t;
}

// TODO(pkotwicz): Push scale into PlatformCanvas such that this function
// is not needed.
template<class T> inline void RecreateBackingCanvas(T* t,
int width, int height, float scale, bool opaque) {
}

} // namespace skia

#endif // SKIA_EXT_CANVAS_PAINT_COMMON_H_
117 changes: 117 additions & 0 deletions skia/ext/canvas_paint_gtk.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,117 @@

// Copyright (c) 2011 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 SKIA_EXT_CANVAS_PAINT_LINUX_H_
#define SKIA_EXT_CANVAS_PAINT_LINUX_H_

#include "base/logging.h"
#include "skia/ext/canvas_paint_common.h"
#include "skia/ext/platform_canvas.h"

#include <gdk/gdk.h>

namespace skia {

// A class designed to translate skia painting into a region in a GdkWindow.
// On construction, it will set up a context for painting into, and on
// destruction, it will commit it to the GdkWindow.
// Note: The created context is always inialized to (0, 0, 0, 0).
template <class T>
class CanvasPaintT : public T {
public:
// This constructor assumes the result is opaque.
explicit CanvasPaintT(GdkEventExpose* event)
: context_(NULL),
window_(event->window),
region_(gdk_region_copy(event->region)),
composite_alpha_(false) {
init(true);
}

CanvasPaintT(GdkEventExpose* event, bool opaque)
: context_(NULL),
window_(event->window),
region_(gdk_region_copy(event->region)),
composite_alpha_(false) {
init(opaque);
}

virtual ~CanvasPaintT() {
if (!is_empty()) {
GetPlatformCanvas(this)->restoreToCount(1);

// Blit the dirty rect to the window.
CHECK(window_);
cairo_t* cr = gdk_cairo_create(window_);
CHECK(cr);
if (composite_alpha_)
cairo_set_operator(cr, CAIRO_OPERATOR_SOURCE);
cairo_surface_t* source_surface = cairo_get_target(context_);
CHECK(source_surface);
// Flush cairo's cache of the surface.
cairo_surface_mark_dirty(source_surface);
GdkRectangle bounds = rectangle();
cairo_set_source_surface(cr, source_surface, bounds.x, bounds.y);
gdk_cairo_region(cr, region_);
cairo_fill(cr);
cairo_destroy(cr);
}

gdk_region_destroy(region_);
}

// Sets whether the bitmap is composited in such a way that the alpha channel
// is honored. This is only useful if you've enabled an RGBA colormap on the
// widget. The default is false.
void set_composite_alpha(bool composite_alpha) {
composite_alpha_ = composite_alpha;
}

// Returns true if the invalid region is empty. The caller should call this
// function to determine if anything needs painting.
bool is_empty() const {
return gdk_region_empty(region_);
}

GdkRectangle rectangle() const {
GdkRectangle bounds;
gdk_region_get_clipbox(region_, &bounds);
return bounds;
}

private:
void init(bool opaque) {
GdkRectangle bounds = rectangle();
PlatformCanvas* canvas = GetPlatformCanvas(this);
if (!canvas->initialize(bounds.width, bounds.height, opaque, NULL)) {
// Cause a deliberate crash;
CHECK(false);
}
// No need to clear the canvas, because cairo automatically performs the
// clear.

// Need to translate so that the dirty region appears at the origin of the
// surface.
canvas->translate(-SkIntToScalar(bounds.x), -SkIntToScalar(bounds.y));

context_ = BeginPlatformPaint(canvas);
}

cairo_t* context_;
GdkWindow* window_;
GdkRegion* region_;
// See description above setter.
bool composite_alpha_;

// Disallow copy and assign.
CanvasPaintT(const CanvasPaintT&);
CanvasPaintT& operator=(const CanvasPaintT&);
};

typedef CanvasPaintT<PlatformCanvas> PlatformCanvasPaint;

} // namespace skia

#endif // SKIA_EXT_CANVAS_PAINT_LINUX_H_
120 changes: 120 additions & 0 deletions skia/ext/canvas_paint_mac.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,120 @@

// Copyright (c) 2012 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 SKIA_EXT_CANVAS_PAINT_MAC_H_
#define SKIA_EXT_CANVAS_PAINT_MAC_H_

#include "skia/ext/canvas_paint_common.h"
#include "skia/ext/platform_canvas.h"

#import <Cocoa/Cocoa.h>

namespace skia {

// A class designed to translate skia painting into a region to the current
// graphics context. On construction, it will set up a context for painting
// into, and on destruction, it will commit it to the current context.
// Note: The created context is always inialized to (0, 0, 0, 0).
template <class T>
class CanvasPaintT : public T {
public:
// This constructor assumes the result is opaque.
explicit CanvasPaintT(NSRect dirtyRect)
: context_(NULL),
rectangle_(dirtyRect),
composite_alpha_(false) {
init(true);
}

CanvasPaintT(NSRect dirtyRect, bool opaque)
: context_(NULL),
rectangle_(dirtyRect),
composite_alpha_(false) {
init(opaque);
}

virtual ~CanvasPaintT() {
if (!is_empty()) {
GetPlatformCanvas(this)->restoreToCount(1);

// Blit the dirty rect to the current context.
CGImageRef image = CGBitmapContextCreateImage(context_);
CGRect dest_rect = NSRectToCGRect(rectangle_);

CGContextRef destination_context =
(CGContextRef)[[NSGraphicsContext currentContext] graphicsPort];
CGContextSaveGState(destination_context);
CGContextSetBlendMode(
destination_context,
composite_alpha_ ? kCGBlendModeNormal : kCGBlendModeCopy);

if ([[NSGraphicsContext currentContext] isFlipped]) {
// Mirror context on the target's rect middle scanline.
CGContextTranslateCTM(destination_context, 0.0, NSMidY(rectangle_));
CGContextScaleCTM(destination_context, 1.0, -1.0);
CGContextTranslateCTM(destination_context, 0.0, -NSMidY(rectangle_));
}

CGContextDrawImage(destination_context, dest_rect, image);
CGContextRestoreGState(destination_context);

CFRelease(image);
}
}

// If true, the data painted into the CanvasPaintT is blended onto the current
// context, else it is copied.
void set_composite_alpha(bool composite_alpha) {
composite_alpha_ = composite_alpha;
}

// Returns true if the invalid region is empty. The caller should call this
// function to determine if anything needs painting.
bool is_empty() const {
return NSIsEmptyRect(rectangle_);
}

const NSRect& rectangle() const {
return rectangle_;
}

private:
void init(bool opaque) {
CGContextRef destination_context =
(CGContextRef)[[NSGraphicsContext currentContext] graphicsPort];
CGRect scaled_unit_rect = CGContextConvertRectToDeviceSpace(
destination_context, CGRectMake(0, 0, 1, 1));
// Assume that the x scale and the y scale are the same.
CGFloat scale = scaled_unit_rect.size.width;

RecreateBackingCanvas(this,
NSWidth(rectangle_), NSHeight(rectangle_), scale, opaque);
PlatformCanvas* canvas = GetPlatformCanvas(this);
canvas->clear(SkColorSetARGB(0, 0, 0, 0));

// Need to translate so that the dirty region appears at the origin of the
// surface.
canvas->translate(-SkDoubleToScalar(NSMinX(rectangle_)),
-SkDoubleToScalar(NSMinY(rectangle_)));

context_ = GetBitmapContext(GetTopDevice(*canvas));
}

CGContext* context_;
NSRect rectangle_;
// See description above setter.
bool composite_alpha_;

// Disallow copy and assign.
CanvasPaintT(const CanvasPaintT&);
CanvasPaintT& operator=(const CanvasPaintT&);
};

typedef CanvasPaintT<PlatformCanvas> PlatformCanvasPaint;

} // namespace skia


#endif // SKIA_EXT_CANVAS_PAINT_MAC_H_
36 changes: 19 additions & 17 deletions ui/gfx/canvas_paint_win.h → skia/ext/canvas_paint_win.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,13 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef UI_GFX_CANVAS_PAINT_WIN_H_
#define UI_GFX_CANVAS_PAINT_WIN_H_
#ifndef SKIA_EXT_CANVAS_PAINT_WIN_H_
#define SKIA_EXT_CANVAS_PAINT_WIN_H_

#include "skia/ext/canvas_paint_common.h"
#include "skia/ext/platform_canvas.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/canvas_paint.h"

namespace gfx {
namespace skia {

// A class designed to help with WM_PAINT operations on Windows. It will
// do BeginPaint/EndPaint on init/destruction, and will create the bitmap and
Expand All @@ -30,24 +29,25 @@ namespace gfx {
// return 0;
// }
// Note: The created context is always inialized to (0, 0, 0, 0).
class CanvasSkiaPaint : public Canvas {
template <class T>
class CanvasPaintT : public T {
public:
// This constructor assumes the canvas is opaque.
explicit CanvasSkiaPaint(HWND hwnd) : hwnd_(hwnd), paint_dc_(NULL),
explicit CanvasPaintT(HWND hwnd) : hwnd_(hwnd), paint_dc_(NULL),
for_paint_(true) {
memset(&ps_, 0, sizeof(ps_));
initPaint(true);
}

CanvasSkiaPaint(HWND hwnd, bool opaque) : hwnd_(hwnd), paint_dc_(NULL),
CanvasPaintT(HWND hwnd, bool opaque) : hwnd_(hwnd), paint_dc_(NULL),
for_paint_(true) {
memset(&ps_, 0, sizeof(ps_));
initPaint(opaque);
}

// Creates a CanvasSkiaPaint for the specified region that paints to the
// Creates a CanvasPaintT for the specified region that paints to the
// specified dc. This does NOT do BeginPaint/EndPaint.
CanvasSkiaPaint(HDC dc, bool opaque, int x, int y, int w, int h)
CanvasPaintT(HDC dc, bool opaque, int x, int y, int w, int h)
: hwnd_(NULL),
paint_dc_(dc),
for_paint_(false) {
Expand All @@ -59,9 +59,9 @@ class CanvasSkiaPaint : public Canvas {
init(opaque);
}

virtual ~CanvasSkiaPaint() {
virtual ~CanvasPaintT() {
if (!isEmpty()) {
skia::PlatformCanvas* canvas = platform_canvas();
PlatformCanvas* canvas = GetPlatformCanvas(this);
canvas->restoreToCount(1);
// Commit the drawing to the screen
skia::DrawToNativeContext(canvas, paint_dc_, ps_.rcPaint.left,
Expand Down Expand Up @@ -102,7 +102,7 @@ class CanvasSkiaPaint : public Canvas {
}

void init(bool opaque) {
skia::PlatformCanvas* canvas = platform_canvas();
PlatformCanvas* canvas = GetPlatformCanvas(this);
// FIXME(brettw) for ClearType, we probably want to expand the bounds of
// painting by one pixel so that the boundaries will be correct (ClearType
// text can depend on the adjacent pixel). Then we would paint just the
Expand All @@ -126,10 +126,12 @@ class CanvasSkiaPaint : public Canvas {
const bool for_paint_;

// Disallow copy and assign.
CanvasSkiaPaint(const CanvasSkiaPaint&);
CanvasSkiaPaint& operator=(const CanvasSkiaPaint&);
CanvasPaintT(const CanvasPaintT&);
CanvasPaintT& operator=(const CanvasPaintT&);
};

} // namespace gfx
typedef CanvasPaintT<PlatformCanvas> PlatformCanvasPaint;

#endif // UI_GFX_CANVAS_PAINT_WIN_H_
} // namespace skia

#endif // SKIA_EXT_CANVAS_PAINT_WIN_H_
5 changes: 5 additions & 0 deletions skia/skia.gyp
Original file line number Diff line number Diff line change
Expand Up @@ -156,6 +156,11 @@
'ext/bitmap_platform_device_mac.h',
'ext/bitmap_platform_device_win.cc',
'ext/bitmap_platform_device_win.h',
'ext/canvas_paint.h',
'ext/canvas_paint_common.h',
'ext/canvas_paint_gtk.h',
'ext/canvas_paint_mac.h',
'ext/canvas_paint_win.h',
'ext/convolver.cc',
'ext/convolver.h',
'ext/google_logging.cc',
Expand Down
Loading

0 comments on commit ac14bd6

Please sign in to comment.