#include <cairo.h>
#ifdef __WXMSW__
#include <cairo-win32.h>
+// Notice that the order is important: cairo-win32.h includes windows.h which
+// pollutes the global name space with macros so include our own header which
+// #undefines them after it.
+#include "wx/msw/private.h"
#endif
#ifdef __WXGTK__
#include "wx/gtk/dc.h"
#endif
-#ifdef __WXMSW__
-#include <cairo-win32.h>
-#endif
-
#ifdef __WXMAC__
#include "wx/osx/private.h"
#include <cairo-quartz.h>
cairo_font_weight_t m_weight;
};
-class wxCairoBitmapData : public wxGraphicsObjectRefData
+class wxCairoBitmapData : public wxGraphicsBitmapData
{
public:
wxCairoBitmapData( wxGraphicsRenderer* renderer, const wxBitmap& bmp );
virtual cairo_surface_t* GetCairoSurface() { return m_surface; }
virtual cairo_pattern_t* GetCairoPattern() { return m_pattern; }
+ virtual void* GetNativeBitmap() const { return m_surface; }
virtual wxSize GetSize() { return wxSize(m_width, m_height); }
#if wxUSE_IMAGE
virtual void Clip( const wxRegion ®ion );
#ifdef __WXMSW__
cairo_surface_t* m_mswSurface;
+ WindowHDC m_mswWindowHDC;
#endif
// clips drawings to the rect
}
wxCairoBitmapData::wxCairoBitmapData( wxGraphicsRenderer* renderer, cairo_surface_t* bitmap ) :
- wxGraphicsObjectRefData( renderer )
+ wxGraphicsBitmapData( renderer )
{
m_surface = bitmap;
m_pattern = cairo_pattern_create_for_surface(m_surface);
}
-wxCairoBitmapData::wxCairoBitmapData( wxGraphicsRenderer* renderer, const wxBitmap& bmp ) : wxGraphicsObjectRefData( renderer )
+wxCairoBitmapData::wxCairoBitmapData( wxGraphicsRenderer* renderer, const wxBitmap& bmp ) : wxGraphicsBitmapData( renderer )
{
wxCHECK_RET( bmp.IsOk(), wxT("Invalid bitmap in wxCairoContext::DrawBitmap"));
wxCairoBitmapData::wxCairoBitmapData(wxGraphicsRenderer* renderer,
const wxImage& image)
- : wxGraphicsObjectRefData(renderer)
+ : wxGraphicsBitmapData(renderer)
{
const cairo_format_t bufferFormat = image.HasAlpha()
? CAIRO_FORMAT_ARGB32
m_enableOffset = true;
#ifdef __WXMSW__
- m_mswSurface = cairo_win32_surface_create((HDC)dc.GetHDC());
+
+ HDC hdc = (HDC)dc.GetHDC();
+
+ HBITMAP bitmap = (HBITMAP)GetCurrentObject(hdc, OBJ_BITMAP);
+
+ BITMAP info;
+ bool hasBitmap = false;
+
+ // cairo_win32_surface_create creates a 24-bit bitmap,
+ // so if we have alpha, we need to create a 32-bit surface instead.
+ if (!GetObject(bitmap, sizeof(info), &info) || info.bmBitsPixel < 32)
+ m_mswSurface = cairo_win32_surface_create(hdc);
+ else {
+ hasBitmap = true;
+ m_mswSurface = cairo_image_surface_create_for_data((unsigned char*)info.bmBits,
+ CAIRO_FORMAT_ARGB32,
+ info.bmWidth,
+ info.bmHeight,
+ info.bmWidthBytes);
+ }
+
Init( cairo_create(m_mswSurface) );
+ // If we've created a image surface, we need to flip the Y axis so that
+ // all drawing will appear right side up.
+ if (hasBitmap) {
+ cairo_matrix_t matrix;
+ cairo_matrix_init(&matrix, 1.0, 0.0, 0.0, -1.0, 0.0, height);
+ cairo_set_matrix(m_context, &matrix);
+ }
#endif
#ifdef __WXGTK20__
}
wxCairoContext::wxCairoContext( wxGraphicsRenderer* renderer, wxWindow *window)
-: wxGraphicsContext(renderer)
+ : wxGraphicsContext(renderer)
+#ifdef __WXMSW__
+ , m_mswWindowHDC(GetHwndOf(window))
+#endif
{
m_enableOffset = true;
#ifdef __WXGTK__
#endif
#ifdef __WXMSW__
- m_mswSurface = cairo_win32_surface_create((HDC)window->GetHandle());
+ m_mswSurface = cairo_win32_surface_create((HDC)m_mswWindowHDC);
Init(cairo_create(m_mswSurface));
#endif