X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/e7f9f819bea18d5327f27ee746afd7e722caad2e..409e6ce4dcd39c6dfe8b77cbd56d451ffe5c731c:/src/generic/graphicc.cpp diff --git a/src/generic/graphicc.cpp b/src/generic/graphicc.cpp index ab7178ce8c..b70fbd4f9a 100644 --- a/src/generic/graphicc.cpp +++ b/src/generic/graphicc.cpp @@ -11,12 +11,14 @@ #include "wx/wxprec.h" -#include "wx/dc.h" - #ifdef __BORLANDC__ #pragma hdrstop #endif +#if wxUSE_GRAPHICS_CONTEXT + +#include "wx/dc.h" + #ifndef WX_PRECOMP #include "wx/image.h" #include "wx/window.h" @@ -32,15 +34,9 @@ #include "wx/module.h" #endif -#ifdef __WXGTK__ -#include -#endif - -#include "wx/graphics.h" +#include "wx/private/graphics.h" #include "wx/rawbmp.h" -#if wxUSE_GRAPHICS_CONTEXT - #include using namespace std; @@ -101,8 +97,9 @@ static inline double RadToDeg(double deg) #include #ifdef __WXGTK__ -#include "wx/gtk/win_gtk.h" #include +#include "wx/fontutil.h" +#include "wx/gtk/dc.h" #endif #ifdef __WXMSW__ @@ -301,17 +298,24 @@ public: ~wxCairoFontData(); virtual void Apply( wxGraphicsContext* context ); +#ifdef __WXGTK__ + const PangoFontDescription* GetFont() const { return m_font; } +#endif private : - wxCharBuffer m_fontName; double m_size; - cairo_font_slant_t m_slant; - cairo_font_weight_t m_weight; double m_red; double m_green; double m_blue; double m_alpha; +#ifdef __WXMAC__ cairo_font_face_t *m_font; - wxFont m_wxFont; +#elif defined(__WXGTK__) + PangoFontDescription* m_font; +#else + wxCharBuffer m_fontName; + cairo_font_slant_t m_slant; + cairo_font_weight_t m_weight; +#endif }; class WXDLLIMPEXP_CORE wxCairoContext : public wxGraphicsContext @@ -320,6 +324,7 @@ class WXDLLIMPEXP_CORE wxCairoContext : public wxGraphicsContext public: wxCairoContext( wxGraphicsRenderer* renderer, const wxWindowDC& dc ); + wxCairoContext( wxGraphicsRenderer* renderer, const wxMemoryDC& dc ); #ifdef __WXGTK__ wxCairoContext( wxGraphicsRenderer* renderer, GdkDrawable *drawable ); #endif @@ -482,17 +487,17 @@ wxCairoPenData::wxCairoPenData( wxGraphicsRenderer* renderer, const wxPen &pen ) break; case wxLONG_DASH : - m_lengths = dotted ; + m_lengths = dashed ; m_count = WXSIZEOF(dashed); break; case wxSHORT_DASH : - m_lengths = dotted ; + m_lengths = short_dashed ; m_count = WXSIZEOF(short_dashed); break; case wxDOT_DASH : - m_lengths = dotted ; + m_lengths = dotted_dashed ; m_count = WXSIZEOF(dotted_dashed); break; @@ -701,38 +706,41 @@ wxCairoFontData::wxCairoFontData( wxGraphicsRenderer* renderer, const wxFont &fo m_green = col.Green()/255.0; m_blue = col.Blue()/255.0; m_alpha = col.Alpha()/255.0; - m_size = font.GetPointSize(); + +#ifdef __WXMAC__ + m_font = cairo_atsui_font_face_create_for_atsu_font_id( font.MacGetATSUFontID() ); +#elif defined(__WXGTK__) + m_font = pango_font_description_copy( font.GetNativeFontInfo()->description ); +#else m_fontName = font.GetFaceName().mb_str(wxConvUTF8); m_slant = font.GetStyle() == wxFONTSTYLE_ITALIC ? CAIRO_FONT_SLANT_ITALIC:CAIRO_FONT_SLANT_NORMAL; m_weight = font.GetWeight() == wxFONTWEIGHT_BOLD ? CAIRO_FONT_WEIGHT_BOLD:CAIRO_FONT_WEIGHT_NORMAL; -#ifdef __WXMAC__ - m_font = cairo_atsui_font_face_create_for_atsu_font_id( font.MacGetATSUFontID() ); -#endif -#ifdef __WXMSW__ -#endif -#ifdef __WXGTK__ - // Pango implementation uses the native descriptor - m_font = NULL; - m_wxFont = font; #endif } wxCairoFontData::~wxCairoFontData() { +#ifdef __WXMAC__ cairo_font_face_destroy( m_font ); +#elif defined(__WXGTK__) + pango_font_description_free( m_font ); +#else +#endif } void wxCairoFontData::Apply( wxGraphicsContext* context ) { -#ifdef __WXGTK__ - // Pango handled differently -#else cairo_t * ctext = (cairo_t*) context->GetNativeContext(); cairo_set_source_rgba(ctext,m_red,m_green, m_blue,m_alpha); - cairo_set_font_face(ctext, m_font ); - // TODO UNDERLINE - // TODO FIX SIZE +#ifdef __WXGTK__ + // the rest is done using Pango layouts +#elif defined(__WXMAC__) + cairo_set_font_face(ctext, m_font); + cairo_set_font_size(ctext, m_size ); +#else + cairo_select_font_face(ctext, m_fontName, m_slant, m_weights ); + cairo_set_font_size(ctext, m_size ); #endif } @@ -875,7 +883,7 @@ void wxCairoPathData::GetBox(wxDouble *x, wxDouble *y, wxDouble *w, wxDouble *h) } } -bool wxCairoPathData::Contains( wxDouble x, wxDouble y, int fillStyle ) const +bool wxCairoPathData::Contains( wxDouble x, wxDouble y, int WXUNUSED(fillStyle) ) const { return cairo_in_stroke( m_pathContext, x, y) != 0; } @@ -1030,7 +1038,25 @@ wxCairoContext::wxCairoContext( wxGraphicsRenderer* renderer, const wxWindowDC& : wxGraphicsContext(renderer) { #ifdef __WXGTK__ - Init( gdk_cairo_create( dc.m_window ) ); + wxGTKDCImpl *impldc = (wxGTKDCImpl*) dc.GetImpl(); + Init( gdk_cairo_create( impldc->GetGDKWindow() ) ); +#endif +#ifdef __WXMAC__ + int width, height; + dc.GetSize( &width, &height ); + CGContextRef cgcontext = (CGContextRef)dc.GetWindow()->MacGetCGContextRef(); + cairo_surface_t* surface = cairo_quartz_surface_create_for_cg_context(cgcontext, width, height); + Init( cairo_create( surface ) ); + cairo_surface_destroy( surface ); +#endif +} + +wxCairoContext::wxCairoContext( wxGraphicsRenderer* renderer, const wxMemoryDC& dc ) +: wxGraphicsContext(renderer) +{ +#ifdef __WXGTK__ + wxGTKDCImpl *impldc = (wxGTKDCImpl*) dc.GetImpl(); + Init( gdk_cairo_create( impldc->GetGDKWindow() ) ); #endif #ifdef __WXMAC__ int width, height; @@ -1062,22 +1088,17 @@ wxCairoContext::wxCairoContext( wxGraphicsRenderer* renderer, wxWindow *window) #ifdef __WXGTK__ // something along these lines (copied from dcclient) - GtkWidget *widget = window->m_wxwindow; - // Some controls don't have m_wxwindow - like wxStaticBox, but the user // code should still be able to create wxClientDCs for them, so we will // use the parent window here then. - if ( !widget ) + if (window->m_wxwindow == NULL) { window = window->GetParent(); - widget = window->m_wxwindow; } - wxASSERT_MSG( widget, wxT("wxCairoContext needs a widget") ); + wxASSERT_MSG( window->m_wxwindow, wxT("wxCairoContext needs a widget") ); - GtkPizza *pizza = GTK_PIZZA( widget ); - GdkDrawable* drawable = pizza->bin_window; - Init( gdk_cairo_create( drawable ) ) ; + Init(gdk_cairo_create(window->GTKGetDrawingWindow())); #endif } @@ -1107,7 +1128,7 @@ void wxCairoContext::Clip( const wxRegion& region ) while (ri) { path.AddRectangle(ri.GetX(), ri.GetY(), ri.GetW(), ri.GetH()); - ri++; + ++ri; } // Put it in the context @@ -1130,7 +1151,7 @@ void wxCairoContext::Clip( wxDouble x, wxDouble y, wxDouble w, wxDouble h ) cairo_append_path(m_context, cp); // clip to that path -// cairo_clip(m_context); + cairo_clip(m_context); path.UnGetNativePath(cp); } @@ -1325,16 +1346,17 @@ void wxCairoContext::DrawText( const wxString &str, wxDouble x, wxDouble y ) { if ( m_font.IsNull() || str.empty()) return; - + #ifdef __WXGTK__ - const wxCharBuffer data = wxGTK_CONV( str ); + const wxCharBuffer data = str.utf8_str(); if ( !data ) return; size_t datalen = strlen(data); - + ((wxCairoFontData*)m_font.GetRefData())->Apply(this); + PangoLayout *layout = pango_cairo_create_layout (m_context); - pango_layout_set_font_description( m_layout, m_wxFont->GetNativeFontInfo()->description); - pango_layout_set_text (layout, data, datalen); + pango_layout_set_font_description( layout, ((wxCairoFontData*)m_font.GetRefData())->GetFont()); + pango_layout_set_text(layout, data, datalen); cairo_move_to(m_context, x, y); pango_cairo_show_layout (m_context, layout); @@ -1371,13 +1393,13 @@ void wxCairoContext::GetTextExtent( const wxString &str, wxDouble *width, wxDoub int w, h; PangoLayout *layout = pango_cairo_create_layout (m_context); - pango_layout_set_font_description( layout, m_wxFont->GetNativeFontInfo()->description); - const wxCharBuffer dataUTF8 = wxGTK_CONV_FONT(str, m_wxFont); - if ( !dataUTF8 ) + pango_layout_set_font_description( layout, ((wxCairoFontData*)m_font.GetRefData())->GetFont()); + const wxCharBuffer data = str.utf8_str(); + if ( !data ) { return; } - pango_layout_set_text( layout, dataUTF8, strlen(dataUTF8) ); + pango_layout_set_text( layout, data, strlen(data) ); pango_layout_get_pixel_size (layout, &w, &h); if ( width ) *width = w; @@ -1406,6 +1428,17 @@ void wxCairoContext::GetTextExtent( const wxString &str, wxDouble *width, wxDoub { cairo_font_extents_t fe; cairo_font_extents(m_context, &fe); + + // some backends have negative descents + + if ( fe.descent < 0 ) + fe.descent = -fe.descent; + + if ( fe.height < (fe.ascent + fe.descent ) ) + { + // some backends are broken re height ... (eg currently ATSUI) + fe.height = fe.ascent + fe.descent; + } if (height) *height = fe.height; @@ -1447,10 +1480,7 @@ public : // Context virtual wxGraphicsContext * CreateContext( const wxWindowDC& dc); - -#ifdef __WXMSW__ virtual wxGraphicsContext * CreateContext( const wxMemoryDC& dc); -#endif virtual wxGraphicsContext * CreateContextFromNativeContext( void * context ); @@ -1497,6 +1527,9 @@ private : IMPLEMENT_DYNAMIC_CLASS(wxCairoRenderer,wxGraphicsRenderer) static wxCairoRenderer gs_cairoGraphicsRenderer; +// temporary hack to allow creating a cairo context on any platform +extern wxGraphicsRenderer* gCairoRenderer; +wxGraphicsRenderer* gCairoRenderer = &gs_cairoGraphicsRenderer; #ifdef __WXGTK__ wxGraphicsRenderer* wxGraphicsRenderer::GetDefaultRenderer() @@ -1510,12 +1543,10 @@ wxGraphicsContext * wxCairoRenderer::CreateContext( const wxWindowDC& dc) return new wxCairoContext(this,dc); } -#ifdef __WXMSW__ wxGraphicsContext * wxCairoRenderer::CreateContext( const wxMemoryDC& dc) { - return NULL; + return new wxCairoContext(this,dc); } -#endif wxGraphicsContext * wxCairoRenderer::CreateContextFromNativeContext( void * context ) {