Implement 0-width pen consistently in wxGraphicsContext
Emulate a 1-pixel pen width as closely as possible. This reverts:334cf1cc91
(Take HiDPI scale into account for wxGCDC 0-width pen, 2021-04-03)0d80050057
(Make wxGCDC behavior with 0-width wxPen consistent with MSW wxDC, 2021-03-02) See #19077, #19115
This commit is contained in:
@@ -878,6 +878,9 @@ public:
|
|||||||
void DisableOffset() { EnableOffset(false); }
|
void DisableOffset() { EnableOffset(false); }
|
||||||
bool OffsetEnabled() const { return m_enableOffset; }
|
bool OffsetEnabled() const { return m_enableOffset; }
|
||||||
|
|
||||||
|
void SetContentScaleFactor(double contentScaleFactor);
|
||||||
|
double GetContentScaleFactor() const { return m_contentScaleFactor; }
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
// These fields must be initialized in the derived class ctors.
|
// These fields must be initialized in the derived class ctors.
|
||||||
wxDouble m_width,
|
wxDouble m_width,
|
||||||
@@ -912,6 +915,7 @@ private:
|
|||||||
// Create() or the associated window of the wxDC this context was created
|
// Create() or the associated window of the wxDC this context was created
|
||||||
// from.
|
// from.
|
||||||
wxWindow* const m_window;
|
wxWindow* const m_window;
|
||||||
|
double m_contentScaleFactor;
|
||||||
|
|
||||||
wxDECLARE_NO_COPY_CLASS(wxGraphicsContext);
|
wxDECLARE_NO_COPY_CLASS(wxGraphicsContext);
|
||||||
wxDECLARE_ABSTRACT_CLASS(wxGraphicsContext);
|
wxDECLARE_ABSTRACT_CLASS(wxGraphicsContext);
|
||||||
|
@@ -522,36 +522,10 @@ void wxGCDCImpl::SetFont( const wxFont &font )
|
|||||||
void wxGCDCImpl::SetPen( const wxPen &pen )
|
void wxGCDCImpl::SetPen( const wxPen &pen )
|
||||||
{
|
{
|
||||||
m_pen = pen;
|
m_pen = pen;
|
||||||
if (m_graphicContext == NULL)
|
if ( m_graphicContext )
|
||||||
return;
|
|
||||||
|
|
||||||
wxPenStyle style;
|
|
||||||
if (!pen.IsOk() || (style = pen.GetStyle()) == wxPENSTYLE_TRANSPARENT)
|
|
||||||
{
|
{
|
||||||
m_graphicContext->SetPen(wxGraphicsPen());
|
m_graphicContext->SetPen( m_pen );
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// 0-width pen is 1 pixel wide with MSW wxDC
|
|
||||||
const int w = pen.GetWidth();
|
|
||||||
const double width = w ? double(w) : 1 / (wxMin(m_scaleX, m_scaleY) * m_contentScaleFactor);
|
|
||||||
|
|
||||||
wxGraphicsPenInfo info(pen.GetColour(), width, style);
|
|
||||||
info.Join(pen.GetJoin()).Cap(pen.GetCap());
|
|
||||||
|
|
||||||
if (style == wxPENSTYLE_USER_DASH)
|
|
||||||
{
|
|
||||||
wxDash* dashes;
|
|
||||||
if (int n = pen.GetDashes(&dashes))
|
|
||||||
info.Dashes(n, dashes);
|
|
||||||
}
|
|
||||||
else if (style == wxPENSTYLE_STIPPLE)
|
|
||||||
{
|
|
||||||
if (const wxBitmap* stipple = pen.GetStipple())
|
|
||||||
info.Stipple(*stipple);
|
|
||||||
}
|
|
||||||
|
|
||||||
m_graphicContext->SetPen(m_graphicContext->CreatePen(info));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void wxGCDCImpl::SetBrush( const wxBrush &brush )
|
void wxGCDCImpl::SetBrush( const wxBrush &brush )
|
||||||
|
@@ -572,6 +572,7 @@ wxGraphicsContext::wxGraphicsContext(wxGraphicsRenderer* renderer,
|
|||||||
m_enableOffset(false),
|
m_enableOffset(false),
|
||||||
m_window(window)
|
m_window(window)
|
||||||
{
|
{
|
||||||
|
m_contentScaleFactor = window ? window->GetContentScaleFactor() : 1.0;
|
||||||
}
|
}
|
||||||
|
|
||||||
wxGraphicsContext::~wxGraphicsContext()
|
wxGraphicsContext::~wxGraphicsContext()
|
||||||
@@ -605,6 +606,12 @@ void wxGraphicsContext::EnableOffset(bool enable)
|
|||||||
m_enableOffset = enable;
|
m_enableOffset = enable;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void wxGraphicsContext::SetContentScaleFactor(double contentScaleFactor)
|
||||||
|
{
|
||||||
|
m_enableOffset = true;
|
||||||
|
m_contentScaleFactor = contentScaleFactor;
|
||||||
|
}
|
||||||
|
|
||||||
#if 0
|
#if 0
|
||||||
void wxGraphicsContext::SetAlpha( wxDouble WXUNUSED(alpha) )
|
void wxGraphicsContext::SetAlpha( wxDouble WXUNUSED(alpha) )
|
||||||
{
|
{
|
||||||
|
@@ -441,17 +441,23 @@ public:
|
|||||||
|
|
||||||
virtual bool ShouldOffset() const wxOVERRIDE
|
virtual bool ShouldOffset() const wxOVERRIDE
|
||||||
{
|
{
|
||||||
if ( !m_enableOffset )
|
if (!m_enableOffset || m_pen.IsNull())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
int penwidth = 0 ;
|
const double width = static_cast<wxCairoPenData*>(m_pen.GetRefData())->GetWidth();
|
||||||
if ( !m_pen.IsNull() )
|
|
||||||
{
|
// always offset for 1-pixel width
|
||||||
penwidth = (int)((wxCairoPenData*)m_pen.GetRefData())->GetWidth();
|
if (width <= 0)
|
||||||
if ( penwidth == 0 )
|
return true;
|
||||||
penwidth = 1;
|
|
||||||
}
|
// no offset if overall scale is not odd integer
|
||||||
return ( penwidth % 2 ) == 1;
|
double x = GetContentScaleFactor(), y = x;
|
||||||
|
cairo_user_to_device_distance(m_context, &x, &y);
|
||||||
|
if (!wxIsSameDouble(fmod(wxMin(fabs(x), fabs(y)), 2.0), 1.0))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
// offset if pen width is odd integer
|
||||||
|
return wxIsSameDouble(fmod(width, 2.0), 1.0);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void Clip( const wxRegion ®ion ) wxOVERRIDE;
|
virtual void Clip( const wxRegion ®ion ) wxOVERRIDE;
|
||||||
@@ -844,8 +850,6 @@ wxCairoPenData::wxCairoPenData( wxGraphicsRenderer* renderer, const wxGraphicsPe
|
|||||||
{
|
{
|
||||||
Init();
|
Init();
|
||||||
m_width = info.GetWidth();
|
m_width = info.GetWidth();
|
||||||
if (m_width <= 0.0)
|
|
||||||
m_width = 0.1;
|
|
||||||
|
|
||||||
switch ( info.GetCap() )
|
switch ( info.GetCap() )
|
||||||
{
|
{
|
||||||
@@ -1017,7 +1021,14 @@ void wxCairoPenData::Apply( wxGraphicsContext* context )
|
|||||||
wxCairoPenBrushBaseData::Apply(context);
|
wxCairoPenBrushBaseData::Apply(context);
|
||||||
|
|
||||||
cairo_t * ctext = (cairo_t*) context->GetNativeContext();
|
cairo_t * ctext = (cairo_t*) context->GetNativeContext();
|
||||||
cairo_set_line_width(ctext,m_width);
|
double width = m_width;
|
||||||
|
if (width <= 0)
|
||||||
|
{
|
||||||
|
double x = context->GetContentScaleFactor(), y = x;
|
||||||
|
cairo_user_to_device_distance(ctext, &x, &y);
|
||||||
|
width = 1 / wxMin(fabs(x), fabs(y));
|
||||||
|
}
|
||||||
|
cairo_set_line_width(ctext, width);
|
||||||
cairo_set_line_cap(ctext,m_cap);
|
cairo_set_line_cap(ctext,m_cap);
|
||||||
cairo_set_line_join(ctext,m_join);
|
cairo_set_line_join(ctext,m_join);
|
||||||
cairo_set_dash(ctext, m_lengths, m_count, 0);
|
cairo_set_dash(ctext, m_lengths, m_count, 0);
|
||||||
@@ -1912,21 +1923,26 @@ wxCairoBitmapData::~wxCairoBitmapData()
|
|||||||
class wxCairoOffsetHelper
|
class wxCairoOffsetHelper
|
||||||
{
|
{
|
||||||
public :
|
public :
|
||||||
wxCairoOffsetHelper( cairo_t* ctx , bool offset )
|
wxCairoOffsetHelper(cairo_t* ctx, double scaleFactor, bool offset)
|
||||||
{
|
{
|
||||||
m_ctx = ctx;
|
m_ctx = ctx;
|
||||||
m_offset = offset;
|
m_offset = 0;
|
||||||
if ( m_offset )
|
if (offset)
|
||||||
cairo_translate( m_ctx, 0.5, 0.5 );
|
{
|
||||||
|
double x = scaleFactor, y = x;
|
||||||
|
cairo_user_to_device_distance(ctx, &x, &y);
|
||||||
|
m_offset = 0.5 / wxMin(fabs(x), fabs(y));
|
||||||
|
cairo_translate(m_ctx, m_offset, m_offset);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
~wxCairoOffsetHelper( )
|
~wxCairoOffsetHelper( )
|
||||||
{
|
{
|
||||||
if ( m_offset )
|
if (m_offset > 0)
|
||||||
cairo_translate( m_ctx, -0.5, -0.5 );
|
cairo_translate(m_ctx, -m_offset, -m_offset);
|
||||||
}
|
}
|
||||||
public :
|
private:
|
||||||
cairo_t* m_ctx;
|
cairo_t* m_ctx;
|
||||||
bool m_offset;
|
double m_offset;
|
||||||
} ;
|
} ;
|
||||||
|
|
||||||
#if wxUSE_PRINTING_ARCHITECTURE
|
#if wxUSE_PRINTING_ARCHITECTURE
|
||||||
@@ -1976,7 +1992,7 @@ wxCairoContext::wxCairoContext( wxGraphicsRenderer* renderer, const wxWindowDC&
|
|||||||
m_width = width;
|
m_width = width;
|
||||||
m_height = height;
|
m_height = height;
|
||||||
|
|
||||||
m_enableOffset = dc.GetContentScaleFactor() <= 1;
|
EnableOffset();
|
||||||
|
|
||||||
#ifdef __WXMSW__
|
#ifdef __WXMSW__
|
||||||
HDC hdc = (HDC)dc.GetHDC();
|
HDC hdc = (HDC)dc.GetHDC();
|
||||||
@@ -2029,7 +2045,7 @@ wxCairoContext::wxCairoContext( wxGraphicsRenderer* renderer, const wxMemoryDC&
|
|||||||
m_width = width;
|
m_width = width;
|
||||||
m_height = height;
|
m_height = height;
|
||||||
|
|
||||||
m_enableOffset = dc.GetContentScaleFactor() <= 1;
|
SetContentScaleFactor(dc.GetContentScaleFactor());
|
||||||
|
|
||||||
#ifdef __WXMSW__
|
#ifdef __WXMSW__
|
||||||
wxBitmap bmp = dc.GetSelectedBitmap();
|
wxBitmap bmp = dc.GetSelectedBitmap();
|
||||||
@@ -2352,7 +2368,7 @@ wxCairoContext::wxCairoContext(wxGraphicsRenderer* renderer, HWND hWnd)
|
|||||||
{
|
{
|
||||||
// See remarks for wxWindowBase::GetContentScaleFactor
|
// See remarks for wxWindowBase::GetContentScaleFactor
|
||||||
double scaleY = ::GetDeviceCaps((HDC)m_mswWindowHDC, LOGPIXELSY) / 96.0f;
|
double scaleY = ::GetDeviceCaps((HDC)m_mswWindowHDC, LOGPIXELSY) / 96.0f;
|
||||||
m_enableOffset = scaleY <= 1.0;
|
SetContentScaleFactor(scaleY);
|
||||||
|
|
||||||
m_mswStateSavedDC = 0;
|
m_mswStateSavedDC = 0;
|
||||||
m_mswSurface = cairo_win32_surface_create((HDC)m_mswWindowHDC);
|
m_mswSurface = cairo_win32_surface_create((HDC)m_mswWindowHDC);
|
||||||
@@ -2393,7 +2409,7 @@ wxCairoContext::wxCairoContext( wxGraphicsRenderer* renderer, wxWindow *window)
|
|||||||
, m_mswWindowHDC(GetHwndOf(window))
|
, m_mswWindowHDC(GetHwndOf(window))
|
||||||
#endif
|
#endif
|
||||||
{
|
{
|
||||||
m_enableOffset = window->GetContentScaleFactor() <= 1;
|
EnableOffset();
|
||||||
#ifdef __WXGTK__
|
#ifdef __WXGTK__
|
||||||
// something along these lines (copied from dcclient)
|
// something along these lines (copied from dcclient)
|
||||||
|
|
||||||
@@ -2605,7 +2621,7 @@ void wxCairoContext::StrokePath( const wxGraphicsPath& path )
|
|||||||
{
|
{
|
||||||
if ( !m_pen.IsNull() )
|
if ( !m_pen.IsNull() )
|
||||||
{
|
{
|
||||||
wxCairoOffsetHelper helper( m_context, ShouldOffset() ) ;
|
wxCairoOffsetHelper helper(m_context, GetContentScaleFactor(), ShouldOffset());
|
||||||
cairo_path_t* cp = (cairo_path_t*) path.GetNativePath() ;
|
cairo_path_t* cp = (cairo_path_t*) path.GetNativePath() ;
|
||||||
cairo_append_path(m_context,cp);
|
cairo_append_path(m_context,cp);
|
||||||
((wxCairoPenData*)m_pen.GetRefData())->Apply(this);
|
((wxCairoPenData*)m_pen.GetRefData())->Apply(this);
|
||||||
@@ -2618,7 +2634,7 @@ void wxCairoContext::FillPath( const wxGraphicsPath& path , wxPolygonFillMode fi
|
|||||||
{
|
{
|
||||||
if ( !m_brush.IsNull() )
|
if ( !m_brush.IsNull() )
|
||||||
{
|
{
|
||||||
wxCairoOffsetHelper helper( m_context, ShouldOffset() ) ;
|
wxCairoOffsetHelper helper(m_context, GetContentScaleFactor(), ShouldOffset());
|
||||||
cairo_path_t* cp = (cairo_path_t*) path.GetNativePath() ;
|
cairo_path_t* cp = (cairo_path_t*) path.GetNativePath() ;
|
||||||
cairo_append_path(m_context,cp);
|
cairo_append_path(m_context,cp);
|
||||||
((wxCairoBrushData*)m_brush.GetRefData())->Apply(this);
|
((wxCairoBrushData*)m_brush.GetRefData())->Apply(this);
|
||||||
@@ -2647,7 +2663,7 @@ void wxCairoContext::DrawRectangle( wxDouble x, wxDouble y, wxDouble w, wxDouble
|
|||||||
}
|
}
|
||||||
if ( !m_pen.IsNull() )
|
if ( !m_pen.IsNull() )
|
||||||
{
|
{
|
||||||
wxCairoOffsetHelper helper( m_context, ShouldOffset() ) ;
|
wxCairoOffsetHelper helper(m_context, GetContentScaleFactor(), ShouldOffset());
|
||||||
((wxCairoPenData*)m_pen.GetRefData())->Apply(this);
|
((wxCairoPenData*)m_pen.GetRefData())->Apply(this);
|
||||||
cairo_rectangle(m_context, x, y, w, h);
|
cairo_rectangle(m_context, x, y, w, h);
|
||||||
cairo_stroke(m_context);
|
cairo_stroke(m_context);
|
||||||
|
@@ -407,7 +407,7 @@ wxWindowDCImpl::wxWindowDCImpl(wxWindowDC* owner, wxWindow* window)
|
|||||||
AdjustForRTL(cr);
|
AdjustForRTL(cr);
|
||||||
wxGraphicsContext* gc = wxGraphicsContext::CreateFromNative(cr);
|
wxGraphicsContext* gc = wxGraphicsContext::CreateFromNative(cr);
|
||||||
cairo_destroy(cr);
|
cairo_destroy(cr);
|
||||||
gc->EnableOffset(m_contentScaleFactor <= 1);
|
gc->SetContentScaleFactor(m_contentScaleFactor);
|
||||||
SetGraphicsContext(gc);
|
SetGraphicsContext(gc);
|
||||||
GtkAllocation a;
|
GtkAllocation a;
|
||||||
gtk_widget_get_allocation(widget, &a);
|
gtk_widget_get_allocation(widget, &a);
|
||||||
@@ -456,7 +456,7 @@ wxClientDCImpl::wxClientDCImpl(wxClientDC* owner, wxWindow* window)
|
|||||||
AdjustForRTL(cr);
|
AdjustForRTL(cr);
|
||||||
wxGraphicsContext* gc = wxGraphicsContext::CreateFromNative(cr);
|
wxGraphicsContext* gc = wxGraphicsContext::CreateFromNative(cr);
|
||||||
cairo_destroy(cr);
|
cairo_destroy(cr);
|
||||||
gc->EnableOffset(m_contentScaleFactor <= 1);
|
gc->SetContentScaleFactor(m_contentScaleFactor);
|
||||||
SetGraphicsContext(gc);
|
SetGraphicsContext(gc);
|
||||||
if (!gtk_widget_get_has_window(widget))
|
if (!gtk_widget_get_has_window(widget))
|
||||||
{
|
{
|
||||||
@@ -480,7 +480,7 @@ wxPaintDCImpl::wxPaintDCImpl(wxPaintDC* owner, wxWindow* window)
|
|||||||
wxCHECK_RET(cr, "using wxPaintDC without being in a native paint event");
|
wxCHECK_RET(cr, "using wxPaintDC without being in a native paint event");
|
||||||
InitSize(gtk_widget_get_window(window->m_wxwindow));
|
InitSize(gtk_widget_get_window(window->m_wxwindow));
|
||||||
wxGraphicsContext* gc = wxGraphicsContext::CreateFromNative(cr);
|
wxGraphicsContext* gc = wxGraphicsContext::CreateFromNative(cr);
|
||||||
gc->EnableOffset(m_contentScaleFactor <= 1);
|
gc->SetContentScaleFactor(m_contentScaleFactor);
|
||||||
SetGraphicsContext(gc);
|
SetGraphicsContext(gc);
|
||||||
// context is already adjusted for RTL
|
// context is already adjusted for RTL
|
||||||
m_layoutDir = window->GetLayoutDirection();
|
m_layoutDir = window->GetLayoutDirection();
|
||||||
@@ -510,7 +510,7 @@ wxScreenDCImpl::wxScreenDCImpl(wxScreenDC* owner)
|
|||||||
cairo_t* cr = gdk_cairo_create(window);
|
cairo_t* cr = gdk_cairo_create(window);
|
||||||
wxGraphicsContext* gc = wxGraphicsContext::CreateFromNative(cr);
|
wxGraphicsContext* gc = wxGraphicsContext::CreateFromNative(cr);
|
||||||
cairo_destroy(cr);
|
cairo_destroy(cr);
|
||||||
gc->EnableOffset(m_contentScaleFactor <= 1);
|
gc->SetContentScaleFactor(m_contentScaleFactor);
|
||||||
SetGraphicsContext(gc);
|
SetGraphicsContext(gc);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -573,7 +573,7 @@ void wxMemoryDCImpl::Setup()
|
|||||||
AdjustForRTL(cr);
|
AdjustForRTL(cr);
|
||||||
gc = wxGraphicsContext::CreateFromNative(cr);
|
gc = wxGraphicsContext::CreateFromNative(cr);
|
||||||
cairo_destroy(cr);
|
cairo_destroy(cr);
|
||||||
gc->EnableOffset(m_contentScaleFactor <= 1);
|
gc->SetContentScaleFactor(m_contentScaleFactor);
|
||||||
}
|
}
|
||||||
SetGraphicsContext(gc);
|
SetGraphicsContext(gc);
|
||||||
}
|
}
|
||||||
@@ -583,7 +583,7 @@ wxGTKCairoDC::wxGTKCairoDC(cairo_t* cr, wxWindow* window, wxLayoutDirection dir,
|
|||||||
: wxDC(new wxGTKCairoDCImpl(this, window, dir, width))
|
: wxDC(new wxGTKCairoDCImpl(this, window, dir, width))
|
||||||
{
|
{
|
||||||
wxGraphicsContext* gc = wxGraphicsContext::CreateFromNative(cr);
|
wxGraphicsContext* gc = wxGraphicsContext::CreateFromNative(cr);
|
||||||
gc->EnableOffset(window->GetContentScaleFactor() <= 1);
|
gc->SetContentScaleFactor(window->GetContentScaleFactor());
|
||||||
SetGraphicsContext(gc);
|
SetGraphicsContext(gc);
|
||||||
if (dir == wxLayout_Default)
|
if (dir == wxLayout_Default)
|
||||||
SetLayoutDirection(window->GetLayoutDirection());
|
SetLayoutDirection(window->GetLayoutDirection());
|
||||||
|
@@ -827,8 +827,6 @@ wxGDIPlusPenData::wxGDIPlusPenData( wxGraphicsRenderer* renderer,
|
|||||||
{
|
{
|
||||||
Init();
|
Init();
|
||||||
m_width = info.GetWidth();
|
m_width = info.GetWidth();
|
||||||
if (m_width <= 0.0)
|
|
||||||
m_width = 0.1;
|
|
||||||
|
|
||||||
m_pen = new Pen(wxColourToColor(info.GetColour()), m_width );
|
m_pen = new Pen(wxColourToColor(info.GetColour()), m_width );
|
||||||
|
|
||||||
@@ -1827,21 +1825,29 @@ void * wxGDIPlusMatrixData::GetNativeMatrix() const
|
|||||||
class wxGDIPlusOffsetHelper
|
class wxGDIPlusOffsetHelper
|
||||||
{
|
{
|
||||||
public :
|
public :
|
||||||
wxGDIPlusOffsetHelper( Graphics* gr , bool offset )
|
wxGDIPlusOffsetHelper(Graphics* gr, double scaleFactor, bool offset)
|
||||||
{
|
{
|
||||||
m_gr = gr;
|
m_gr = gr;
|
||||||
m_offset = offset;
|
m_offset = 0;
|
||||||
if ( m_offset )
|
if (offset)
|
||||||
m_gr->TranslateTransform( 0.5, 0.5 );
|
{
|
||||||
|
Matrix matrix;
|
||||||
|
gr->GetTransform(&matrix);
|
||||||
|
const float f = float(scaleFactor);
|
||||||
|
PointF pt(f, f);
|
||||||
|
matrix.TransformVectors(&pt);
|
||||||
|
m_offset = 0.5f / wxMin(std::abs(pt.X), std::abs(pt.Y));
|
||||||
|
m_gr->TranslateTransform(m_offset, m_offset);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
~wxGDIPlusOffsetHelper( )
|
~wxGDIPlusOffsetHelper( )
|
||||||
{
|
{
|
||||||
if ( m_offset )
|
if (m_offset > 0)
|
||||||
m_gr->TranslateTransform( -0.5, -0.5 );
|
m_gr->TranslateTransform(-m_offset, -m_offset);
|
||||||
}
|
}
|
||||||
public :
|
public :
|
||||||
Graphics* m_gr;
|
Graphics* m_gr;
|
||||||
bool m_offset;
|
float m_offset;
|
||||||
} ;
|
} ;
|
||||||
|
|
||||||
wxGDIPlusContext::wxGDIPlusContext( wxGraphicsRenderer* renderer, HDC hdc, wxDouble width, wxDouble height )
|
wxGDIPlusContext::wxGDIPlusContext( wxGraphicsRenderer* renderer, HDC hdc, wxDouble width, wxDouble height )
|
||||||
@@ -1952,7 +1958,7 @@ void wxGDIPlusContext::DrawRectangle( wxDouble x, wxDouble y, wxDouble w, wxDoub
|
|||||||
if (m_composition == wxCOMPOSITION_DEST)
|
if (m_composition == wxCOMPOSITION_DEST)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
wxGDIPlusOffsetHelper helper( m_context , ShouldOffset() );
|
wxGDIPlusOffsetHelper helper(m_context, GetContentScaleFactor(), ShouldOffset());
|
||||||
Brush *brush = m_brush.IsNull() ? NULL : ((wxGDIPlusBrushData*)m_brush.GetRefData())->GetGDIPlusBrush();
|
Brush *brush = m_brush.IsNull() ? NULL : ((wxGDIPlusBrushData*)m_brush.GetRefData())->GetGDIPlusBrush();
|
||||||
Pen *pen = m_pen.IsNull() ? NULL : ((wxGDIPlusPenData*)m_pen.GetGraphicsData())->GetGDIPlusPen();
|
Pen *pen = m_pen.IsNull() ? NULL : ((wxGDIPlusPenData*)m_pen.GetGraphicsData())->GetGDIPlusPen();
|
||||||
|
|
||||||
@@ -1991,7 +1997,7 @@ void wxGDIPlusContext::StrokeLines( size_t n, const wxPoint2DDouble *points)
|
|||||||
|
|
||||||
if ( !m_pen.IsNull() )
|
if ( !m_pen.IsNull() )
|
||||||
{
|
{
|
||||||
wxGDIPlusOffsetHelper helper( m_context , ShouldOffset() );
|
wxGDIPlusOffsetHelper helper(m_context, GetContentScaleFactor(), ShouldOffset());
|
||||||
PointF *cpoints = new PointF[n];
|
PointF *cpoints = new PointF[n];
|
||||||
for (size_t i = 0; i < n; i++)
|
for (size_t i = 0; i < n; i++)
|
||||||
{
|
{
|
||||||
@@ -2009,7 +2015,7 @@ void wxGDIPlusContext::DrawLines( size_t n, const wxPoint2DDouble *points, wxPol
|
|||||||
if (m_composition == wxCOMPOSITION_DEST)
|
if (m_composition == wxCOMPOSITION_DEST)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
wxGDIPlusOffsetHelper helper( m_context , ShouldOffset() );
|
wxGDIPlusOffsetHelper helper(m_context, GetContentScaleFactor(), ShouldOffset());
|
||||||
PointF *cpoints = new PointF[n];
|
PointF *cpoints = new PointF[n];
|
||||||
for (size_t i = 0; i < n; i++)
|
for (size_t i = 0; i < n; i++)
|
||||||
{
|
{
|
||||||
@@ -2032,7 +2038,7 @@ void wxGDIPlusContext::StrokePath( const wxGraphicsPath& path )
|
|||||||
|
|
||||||
if ( !m_pen.IsNull() )
|
if ( !m_pen.IsNull() )
|
||||||
{
|
{
|
||||||
wxGDIPlusOffsetHelper helper( m_context , ShouldOffset() );
|
wxGDIPlusOffsetHelper helper(m_context, GetContentScaleFactor(), ShouldOffset());
|
||||||
m_context->DrawPath( ((wxGDIPlusPenData*)m_pen.GetGraphicsData())->GetGDIPlusPen() , (GraphicsPath*) path.GetNativePath() );
|
m_context->DrawPath( ((wxGDIPlusPenData*)m_pen.GetGraphicsData())->GetGDIPlusPen() , (GraphicsPath*) path.GetNativePath() );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -2044,7 +2050,7 @@ void wxGDIPlusContext::FillPath( const wxGraphicsPath& path , wxPolygonFillMode
|
|||||||
|
|
||||||
if ( !m_brush.IsNull() )
|
if ( !m_brush.IsNull() )
|
||||||
{
|
{
|
||||||
wxGDIPlusOffsetHelper helper( m_context , ShouldOffset() );
|
wxGDIPlusOffsetHelper helper(m_context, GetContentScaleFactor(), ShouldOffset());
|
||||||
((GraphicsPath*) path.GetNativePath())->SetFillMode( fillStyle == wxODDEVEN_RULE ? FillModeAlternate : FillModeWinding);
|
((GraphicsPath*) path.GetNativePath())->SetFillMode( fillStyle == wxODDEVEN_RULE ? FillModeAlternate : FillModeWinding);
|
||||||
m_context->FillPath( ((wxGDIPlusBrushData*)m_brush.GetRefData())->GetGDIPlusBrush() ,
|
m_context->FillPath( ((wxGDIPlusBrushData*)m_brush.GetRefData())->GetGDIPlusBrush() ,
|
||||||
(GraphicsPath*) path.GetNativePath());
|
(GraphicsPath*) path.GetNativePath());
|
||||||
@@ -2429,17 +2435,24 @@ void wxGDIPlusContext::GetPartialTextExtents(const wxString& text, wxArrayDouble
|
|||||||
|
|
||||||
bool wxGDIPlusContext::ShouldOffset() const
|
bool wxGDIPlusContext::ShouldOffset() const
|
||||||
{
|
{
|
||||||
if ( !m_enableOffset )
|
if (!m_enableOffset || m_pen.IsNull())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
int penwidth = 0 ;
|
double width = static_cast<wxGDIPlusPenData*>(m_pen.GetRefData())->GetWidth();
|
||||||
if ( !m_pen.IsNull() )
|
|
||||||
{
|
// always offset for 1-pixel width
|
||||||
penwidth = (int)((wxGDIPlusPenData*)m_pen.GetRefData())->GetWidth();
|
if (width <= 0)
|
||||||
if ( penwidth == 0 )
|
return true;
|
||||||
penwidth = 1;
|
|
||||||
}
|
// no offset if overall scale is not odd integer
|
||||||
return ( penwidth % 2 ) == 1;
|
const wxGraphicsMatrix matrix(GetTransform());
|
||||||
|
double x = GetContentScaleFactor(), y = x;
|
||||||
|
matrix.TransformDistance(&x, &y);
|
||||||
|
if (!wxIsSameDouble(fmod(wxMin(fabs(x), fabs(y)), 2.0), 1.0))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
// offset if pen width is odd integer
|
||||||
|
return wxIsSameDouble(fmod(width, 2.0), 1.0);
|
||||||
}
|
}
|
||||||
|
|
||||||
void* wxGDIPlusContext::GetNativeContext()
|
void* wxGDIPlusContext::GetNativeContext()
|
||||||
|
@@ -1107,24 +1107,31 @@ wxCOMPtr<ID2D1Geometry> wxD2DConvertRegionToGeometry(ID2D1Factory* direct2dFacto
|
|||||||
class wxD2DOffsetHelper
|
class wxD2DOffsetHelper
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
wxD2DOffsetHelper(wxGraphicsContext* g) : m_context(g)
|
wxD2DOffsetHelper(wxGraphicsContext* g, double scaleFactor)
|
||||||
|
: m_context(g)
|
||||||
{
|
{
|
||||||
|
m_offset = 0;
|
||||||
if (m_context->ShouldOffset())
|
if (m_context->ShouldOffset())
|
||||||
{
|
{
|
||||||
m_context->Translate(0.5, 0.5);
|
const wxGraphicsMatrix matrix(m_context->GetTransform());
|
||||||
|
double x = m_context->GetContentScaleFactor(), y = x;
|
||||||
|
matrix.TransformDistance(&x, &y);
|
||||||
|
m_offset = 0.5 / wxMin(fabs(x), fabs(y));
|
||||||
|
m_context->Translate(m_offset, m_offset);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
~wxD2DOffsetHelper()
|
~wxD2DOffsetHelper()
|
||||||
{
|
{
|
||||||
if (m_context->ShouldOffset())
|
if (m_offset > 0)
|
||||||
{
|
{
|
||||||
m_context->Translate(-0.5, -0.5);
|
m_context->Translate(-m_offset, -m_offset);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
wxGraphicsContext* m_context;
|
wxGraphicsContext* m_context;
|
||||||
|
double m_offset;
|
||||||
};
|
};
|
||||||
|
|
||||||
bool operator==(const D2D1::Matrix3x2F& lhs, const D2D1::Matrix3x2F& rhs)
|
bool operator==(const D2D1::Matrix3x2F& lhs, const D2D1::Matrix3x2F& rhs)
|
||||||
@@ -3033,6 +3040,8 @@ public:
|
|||||||
ID2D1Brush* GetBrush();
|
ID2D1Brush* GetBrush();
|
||||||
|
|
||||||
FLOAT GetWidth();
|
FLOAT GetWidth();
|
||||||
|
bool IsZeroWidth() const;
|
||||||
|
void SetWidth(const wxGraphicsContext* context);
|
||||||
|
|
||||||
ID2D1StrokeStyle* GetStrokeStyle();
|
ID2D1StrokeStyle* GetStrokeStyle();
|
||||||
|
|
||||||
@@ -3146,6 +3155,17 @@ void wxD2DPenData::CreateStrokeStyle(ID2D1Factory* const direct2dfactory)
|
|||||||
delete[] dashes;
|
delete[] dashes;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void wxD2DPenData::SetWidth(const wxGraphicsContext* context)
|
||||||
|
{
|
||||||
|
if (m_penInfo.GetWidth() <= 0)
|
||||||
|
{
|
||||||
|
const wxGraphicsMatrix matrix(context->GetTransform());
|
||||||
|
double x = context->GetContentScaleFactor(), y = x;
|
||||||
|
matrix.TransformDistance(&x, &y);
|
||||||
|
m_width = 1 / wxMin(fabs(x), fabs(y));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
ID2D1Brush* wxD2DPenData::GetBrush()
|
ID2D1Brush* wxD2DPenData::GetBrush()
|
||||||
{
|
{
|
||||||
return m_stippleBrush->GetBrush();
|
return m_stippleBrush->GetBrush();
|
||||||
@@ -3156,6 +3176,11 @@ FLOAT wxD2DPenData::GetWidth()
|
|||||||
return m_width;
|
return m_width;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool wxD2DPenData::IsZeroWidth() const
|
||||||
|
{
|
||||||
|
return m_penInfo.GetWidth() <= 0;
|
||||||
|
}
|
||||||
|
|
||||||
ID2D1StrokeStyle* wxD2DPenData::GetStrokeStyle()
|
ID2D1StrokeStyle* wxD2DPenData::GetStrokeStyle()
|
||||||
{
|
{
|
||||||
return m_strokeStyle;
|
return m_strokeStyle;
|
||||||
@@ -4321,7 +4346,7 @@ void wxD2DContext::StrokePath(const wxGraphicsPath& p)
|
|||||||
if (m_composition == wxCOMPOSITION_DEST)
|
if (m_composition == wxCOMPOSITION_DEST)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
wxD2DOffsetHelper helper(this);
|
wxD2DOffsetHelper helper(this, GetContentScaleFactor());
|
||||||
|
|
||||||
EnsureInitialized();
|
EnsureInitialized();
|
||||||
AdjustRenderTargetSize();
|
AdjustRenderTargetSize();
|
||||||
@@ -4332,6 +4357,7 @@ void wxD2DContext::StrokePath(const wxGraphicsPath& p)
|
|||||||
if (!m_pen.IsNull())
|
if (!m_pen.IsNull())
|
||||||
{
|
{
|
||||||
wxD2DPenData* penData = wxGetD2DPenData(m_pen);
|
wxD2DPenData* penData = wxGetD2DPenData(m_pen);
|
||||||
|
penData->SetWidth(this);
|
||||||
penData->Bind(this);
|
penData->Bind(this);
|
||||||
ID2D1Brush* nativeBrush = penData->GetBrush();
|
ID2D1Brush* nativeBrush = penData->GetBrush();
|
||||||
GetRenderTarget()->DrawGeometry((ID2D1Geometry*)pathData->GetNativePath(), nativeBrush, penData->GetWidth(), penData->GetStrokeStyle());
|
GetRenderTarget()->DrawGeometry((ID2D1Geometry*)pathData->GetNativePath(), nativeBrush, penData->GetWidth(), penData->GetStrokeStyle());
|
||||||
@@ -4690,19 +4716,24 @@ void wxD2DContext::GetPartialTextExtents(const wxString& text, wxArrayDouble& wi
|
|||||||
|
|
||||||
bool wxD2DContext::ShouldOffset() const
|
bool wxD2DContext::ShouldOffset() const
|
||||||
{
|
{
|
||||||
if (!m_enableOffset)
|
if (!m_enableOffset || m_pen.IsNull())
|
||||||
{
|
|
||||||
return false;
|
return false;
|
||||||
}
|
|
||||||
|
|
||||||
int penWidth = 0;
|
wxD2DPenData* const penData = wxGetD2DPenData(m_pen);
|
||||||
if (!m_pen.IsNull())
|
|
||||||
{
|
|
||||||
penWidth = wxGetD2DPenData(m_pen)->GetWidth();
|
|
||||||
penWidth = wxMax(penWidth, 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
return (penWidth % 2) == 1;
|
// always offset for 1-pixel width
|
||||||
|
if (penData->IsZeroWidth())
|
||||||
|
return true;
|
||||||
|
|
||||||
|
// no offset if overall scale is not odd integer
|
||||||
|
const wxGraphicsMatrix matrix(GetTransform());
|
||||||
|
double x = GetContentScaleFactor(), y = x;
|
||||||
|
matrix.TransformDistance(&x, &y);
|
||||||
|
if (!wxIsSameDouble(fmod(wxMin(fabs(x), fabs(y)), 2.0), 1.0))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
// offset if pen width is odd integer
|
||||||
|
return wxIsSameDouble(fmod(double(penData->GetWidth()), 2.0), 1.0);
|
||||||
}
|
}
|
||||||
|
|
||||||
void wxD2DContext::DoDrawText(const wxString& str, wxDouble x, wxDouble y)
|
void wxD2DContext::DoDrawText(const wxString& str, wxDouble x, wxDouble y)
|
||||||
@@ -4779,7 +4810,7 @@ void wxD2DContext::DrawRectangle(wxDouble x, wxDouble y, wxDouble w, wxDouble h)
|
|||||||
if (m_composition == wxCOMPOSITION_DEST)
|
if (m_composition == wxCOMPOSITION_DEST)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
wxD2DOffsetHelper helper(this);
|
wxD2DOffsetHelper helper(this, GetContentScaleFactor());
|
||||||
|
|
||||||
EnsureInitialized();
|
EnsureInitialized();
|
||||||
AdjustRenderTargetSize();
|
AdjustRenderTargetSize();
|
||||||
@@ -4797,6 +4828,7 @@ void wxD2DContext::DrawRectangle(wxDouble x, wxDouble y, wxDouble w, wxDouble h)
|
|||||||
if (!m_pen.IsNull())
|
if (!m_pen.IsNull())
|
||||||
{
|
{
|
||||||
wxD2DPenData* penData = wxGetD2DPenData(m_pen);
|
wxD2DPenData* penData = wxGetD2DPenData(m_pen);
|
||||||
|
penData->SetWidth(this);
|
||||||
penData->Bind(this);
|
penData->Bind(this);
|
||||||
GetRenderTarget()->DrawRectangle(rect, penData->GetBrush(), penData->GetWidth(), penData->GetStrokeStyle());
|
GetRenderTarget()->DrawRectangle(rect, penData->GetBrush(), penData->GetWidth(), penData->GetStrokeStyle());
|
||||||
}
|
}
|
||||||
@@ -4807,7 +4839,7 @@ void wxD2DContext::DrawRoundedRectangle(wxDouble x, wxDouble y, wxDouble w, wxDo
|
|||||||
if (m_composition == wxCOMPOSITION_DEST)
|
if (m_composition == wxCOMPOSITION_DEST)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
wxD2DOffsetHelper helper(this);
|
wxD2DOffsetHelper helper(this, GetContentScaleFactor());
|
||||||
|
|
||||||
EnsureInitialized();
|
EnsureInitialized();
|
||||||
AdjustRenderTargetSize();
|
AdjustRenderTargetSize();
|
||||||
@@ -4826,6 +4858,7 @@ void wxD2DContext::DrawRoundedRectangle(wxDouble x, wxDouble y, wxDouble w, wxDo
|
|||||||
if (!m_pen.IsNull())
|
if (!m_pen.IsNull())
|
||||||
{
|
{
|
||||||
wxD2DPenData* penData = wxGetD2DPenData(m_pen);
|
wxD2DPenData* penData = wxGetD2DPenData(m_pen);
|
||||||
|
penData->SetWidth(this);
|
||||||
penData->Bind(this);
|
penData->Bind(this);
|
||||||
GetRenderTarget()->DrawRoundedRectangle(roundedRect, penData->GetBrush(), penData->GetWidth(), penData->GetStrokeStyle());
|
GetRenderTarget()->DrawRoundedRectangle(roundedRect, penData->GetBrush(), penData->GetWidth(), penData->GetStrokeStyle());
|
||||||
}
|
}
|
||||||
@@ -4836,7 +4869,7 @@ void wxD2DContext::DrawEllipse(wxDouble x, wxDouble y, wxDouble w, wxDouble h)
|
|||||||
if (m_composition == wxCOMPOSITION_DEST)
|
if (m_composition == wxCOMPOSITION_DEST)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
wxD2DOffsetHelper helper(this);
|
wxD2DOffsetHelper helper(this, GetContentScaleFactor());
|
||||||
|
|
||||||
EnsureInitialized();
|
EnsureInitialized();
|
||||||
AdjustRenderTargetSize();
|
AdjustRenderTargetSize();
|
||||||
@@ -4857,6 +4890,7 @@ void wxD2DContext::DrawEllipse(wxDouble x, wxDouble y, wxDouble w, wxDouble h)
|
|||||||
if (!m_pen.IsNull())
|
if (!m_pen.IsNull())
|
||||||
{
|
{
|
||||||
wxD2DPenData* penData = wxGetD2DPenData(m_pen);
|
wxD2DPenData* penData = wxGetD2DPenData(m_pen);
|
||||||
|
penData->SetWidth(this);
|
||||||
penData->Bind(this);
|
penData->Bind(this);
|
||||||
GetRenderTarget()->DrawEllipse(ellipse, penData->GetBrush(), penData->GetWidth(), penData->GetStrokeStyle());
|
GetRenderTarget()->DrawEllipse(ellipse, penData->GetBrush(), penData->GetWidth(), penData->GetStrokeStyle());
|
||||||
}
|
}
|
||||||
|
@@ -76,7 +76,7 @@ wxWindowDCImpl::wxWindowDCImpl( wxDC *owner, wxWindow *window )
|
|||||||
CGContextTranslateCTM( cg , -window->MacGetLeftBorderSize() , -window->MacGetTopBorderSize() );
|
CGContextTranslateCTM( cg , -window->MacGetLeftBorderSize() , -window->MacGetTopBorderSize() );
|
||||||
|
|
||||||
wxGraphicsContext* context = wxGraphicsContext::CreateFromNative( cg );
|
wxGraphicsContext* context = wxGraphicsContext::CreateFromNative( cg );
|
||||||
context->EnableOffset(m_contentScaleFactor <= 1);
|
context->SetContentScaleFactor(m_contentScaleFactor);
|
||||||
SetGraphicsContext( context );
|
SetGraphicsContext( context );
|
||||||
}
|
}
|
||||||
DoSetClippingRegion( 0 , 0 , m_width , m_height ) ;
|
DoSetClippingRegion( 0 , 0 , m_width , m_height ) ;
|
||||||
|
@@ -743,8 +743,6 @@ wxMacCoreGraphicsPenData::wxMacCoreGraphicsPenData( wxGraphicsRenderer* renderer
|
|||||||
|
|
||||||
// TODO: * m_dc->m_scaleX
|
// TODO: * m_dc->m_scaleX
|
||||||
m_width = info.GetWidth();
|
m_width = info.GetWidth();
|
||||||
if (m_width <= 0.0)
|
|
||||||
m_width = (CGFloat) 0.1;
|
|
||||||
|
|
||||||
switch ( info.GetCap() )
|
switch ( info.GetCap() )
|
||||||
{
|
{
|
||||||
@@ -912,7 +910,15 @@ void wxMacCoreGraphicsPenData::Init()
|
|||||||
void wxMacCoreGraphicsPenData::Apply( wxGraphicsContext* context )
|
void wxMacCoreGraphicsPenData::Apply( wxGraphicsContext* context )
|
||||||
{
|
{
|
||||||
CGContextRef cg = (CGContextRef) context->GetNativeContext();
|
CGContextRef cg = (CGContextRef) context->GetNativeContext();
|
||||||
CGContextSetLineWidth( cg , m_width );
|
double width = m_width;
|
||||||
|
if (width <= 0)
|
||||||
|
{
|
||||||
|
const double scaleFactor = context->GetContentScaleFactor();
|
||||||
|
CGSize s = { scaleFactor, scaleFactor };
|
||||||
|
s = CGContextConvertSizeToUserSpace(cg, s);
|
||||||
|
width = 1 / wxMin(fabs(s.width), fabs(s.height));
|
||||||
|
}
|
||||||
|
CGContextSetLineWidth( cg, width );
|
||||||
CGContextSetLineJoin( cg , m_join );
|
CGContextSetLineJoin( cg , m_join );
|
||||||
|
|
||||||
CGContextSetLineDash( cg , 0 , m_lengths , m_count );
|
CGContextSetLineDash( cg , 0 , m_lengths , m_count );
|
||||||
@@ -1391,12 +1397,6 @@ public:
|
|||||||
|
|
||||||
~wxMacCoreGraphicsContext();
|
~wxMacCoreGraphicsContext();
|
||||||
|
|
||||||
// Enable offset on non-high DPI displays, i.e. those with scale factor <= 1.
|
|
||||||
void SetEnableOffsetFromScaleFactor(double factor)
|
|
||||||
{
|
|
||||||
m_enableOffset = factor <= 1.0;
|
|
||||||
}
|
|
||||||
|
|
||||||
void Init();
|
void Init();
|
||||||
|
|
||||||
virtual void StartPage( wxDouble width, wxDouble height ) wxOVERRIDE;
|
virtual void StartPage( wxDouble width, wxDouble height ) wxOVERRIDE;
|
||||||
@@ -1474,17 +1474,24 @@ public:
|
|||||||
|
|
||||||
virtual bool ShouldOffset() const wxOVERRIDE
|
virtual bool ShouldOffset() const wxOVERRIDE
|
||||||
{
|
{
|
||||||
if ( !m_enableOffset )
|
if (!m_enableOffset || m_pen.IsNull())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
int penwidth = 0 ;
|
double width = static_cast<wxMacCoreGraphicsPenData*>(m_pen.GetRefData())->GetWidth();
|
||||||
if ( !m_pen.IsNull() )
|
|
||||||
{
|
// always offset for 1-pixel width
|
||||||
penwidth = (int)((wxMacCoreGraphicsPenData*)m_pen.GetRefData())->GetWidth();
|
if (width <= 0)
|
||||||
if ( penwidth == 0 )
|
return true;
|
||||||
penwidth = 1;
|
|
||||||
}
|
// no offset if overall scale is not odd integer
|
||||||
return ( penwidth % 2 ) == 1;
|
const double scaleFactor = GetContentScaleFactor();
|
||||||
|
CGSize s = { scaleFactor, scaleFactor };
|
||||||
|
s = CGContextConvertSizeToUserSpace(m_cgContext, s);
|
||||||
|
if (!wxIsSameDouble(fmod(wxMin(fabs(s.width), fabs(s.height)), 2.0), 1.0))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
// offset if pen width is odd integer
|
||||||
|
return wxIsSameDouble(fmod(width, 2.0), 1.0);
|
||||||
}
|
}
|
||||||
//
|
//
|
||||||
// text
|
// text
|
||||||
@@ -1555,13 +1562,16 @@ private:
|
|||||||
class wxQuartzOffsetHelper
|
class wxQuartzOffsetHelper
|
||||||
{
|
{
|
||||||
public :
|
public :
|
||||||
wxQuartzOffsetHelper( CGContextRef cg , bool offset )
|
wxQuartzOffsetHelper( CGContextRef cg, double scaleFactor, bool offset )
|
||||||
{
|
{
|
||||||
m_cg = cg;
|
m_cg = cg;
|
||||||
m_offset = offset;
|
m_offset = offset;
|
||||||
if ( m_offset )
|
if ( m_offset )
|
||||||
{
|
{
|
||||||
m_userOffset = CGContextConvertSizeToUserSpace( m_cg, CGSizeMake( 0.5 , 0.5 ) );
|
const CGSize s = { scaleFactor, scaleFactor };
|
||||||
|
m_userOffset = CGContextConvertSizeToUserSpace(m_cg, s);
|
||||||
|
m_userOffset.width = 0.5 / m_userOffset.width;
|
||||||
|
m_userOffset.height = 0.5 / m_userOffset.height;
|
||||||
CGContextTranslateCTM( m_cg, m_userOffset.width , m_userOffset.height );
|
CGContextTranslateCTM( m_cg, m_userOffset.width , m_userOffset.height );
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@@ -1615,7 +1625,7 @@ wxMacCoreGraphicsContext::wxMacCoreGraphicsContext( wxGraphicsRenderer* renderer
|
|||||||
{
|
{
|
||||||
Init();
|
Init();
|
||||||
|
|
||||||
SetEnableOffsetFromScaleFactor(window->GetContentScaleFactor());
|
EnableOffset();
|
||||||
wxSize sz = window->GetSize();
|
wxSize sz = window->GetSize();
|
||||||
m_width = sz.x;
|
m_width = sz.x;
|
||||||
m_height = sz.y;
|
m_height = sz.y;
|
||||||
@@ -2136,7 +2146,7 @@ void wxMacCoreGraphicsContext::StrokePath( const wxGraphicsPath &path )
|
|||||||
if (m_composition == wxCOMPOSITION_DEST)
|
if (m_composition == wxCOMPOSITION_DEST)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
wxQuartzOffsetHelper helper( m_cgContext , ShouldOffset() );
|
wxQuartzOffsetHelper helper( m_cgContext, GetContentScaleFactor(), ShouldOffset() );
|
||||||
wxMacCoreGraphicsPenData* penData = (wxMacCoreGraphicsPenData*)m_pen.GetRefData();
|
wxMacCoreGraphicsPenData* penData = (wxMacCoreGraphicsPenData*)m_pen.GetRefData();
|
||||||
|
|
||||||
penData->Apply(this);
|
penData->Apply(this);
|
||||||
@@ -2216,7 +2226,7 @@ void wxMacCoreGraphicsContext::DrawPath( const wxGraphicsPath &path , wxPolygonF
|
|||||||
if ( !m_pen.IsNull() )
|
if ( !m_pen.IsNull() )
|
||||||
((wxMacCoreGraphicsPenData*)m_pen.GetRefData())->Apply(this);
|
((wxMacCoreGraphicsPenData*)m_pen.GetRefData())->Apply(this);
|
||||||
|
|
||||||
wxQuartzOffsetHelper helper( m_cgContext , ShouldOffset() );
|
wxQuartzOffsetHelper helper( m_cgContext, GetContentScaleFactor(), ShouldOffset() );
|
||||||
|
|
||||||
CGContextAddPath( m_cgContext , (CGPathRef) path.GetNativePath() );
|
CGContextAddPath( m_cgContext , (CGPathRef) path.GetNativePath() );
|
||||||
CGContextDrawPath( m_cgContext , mode );
|
CGContextDrawPath( m_cgContext , mode );
|
||||||
@@ -2624,9 +2634,9 @@ void wxMacCoreGraphicsContext::DrawRectangle( wxDouble x, wxDouble y, wxDouble w
|
|||||||
CGContextFillRect(m_cgContext, rect);
|
CGContextFillRect(m_cgContext, rect);
|
||||||
}
|
}
|
||||||
|
|
||||||
wxQuartzOffsetHelper helper( m_cgContext , ShouldOffset() );
|
|
||||||
if ( !m_pen.IsNull() )
|
if ( !m_pen.IsNull() )
|
||||||
{
|
{
|
||||||
|
wxQuartzOffsetHelper helper( m_cgContext, GetContentScaleFactor(), ShouldOffset() );
|
||||||
((wxMacCoreGraphicsPenData*)m_pen.GetRefData())->Apply(this);
|
((wxMacCoreGraphicsPenData*)m_pen.GetRefData())->Apply(this);
|
||||||
CGContextStrokeRect(m_cgContext, rect);
|
CGContextStrokeRect(m_cgContext, rect);
|
||||||
}
|
}
|
||||||
@@ -2850,7 +2860,7 @@ wxGraphicsContext * wxMacCoreGraphicsRenderer::CreateContext( const wxWindowDC&
|
|||||||
CGContextRef cgctx = (CGContextRef)(win->MacGetCGContextRef());
|
CGContextRef cgctx = (CGContextRef)(win->MacGetCGContextRef());
|
||||||
wxMacCoreGraphicsContext *context =
|
wxMacCoreGraphicsContext *context =
|
||||||
new wxMacCoreGraphicsContext( this, cgctx, sz.x, sz.y, win );
|
new wxMacCoreGraphicsContext( this, cgctx, sz.x, sz.y, win );
|
||||||
context->SetEnableOffsetFromScaleFactor(dc.GetContentScaleFactor());
|
context->SetContentScaleFactor(dc.GetContentScaleFactor());
|
||||||
return context;
|
return context;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -2865,7 +2875,7 @@ wxGraphicsContext * wxMacCoreGraphicsRenderer::CreateContext( const wxMemoryDC&
|
|||||||
mem_impl->GetSize( &w, &h );
|
mem_impl->GetSize( &w, &h );
|
||||||
wxMacCoreGraphicsContext* context = new wxMacCoreGraphicsContext( this,
|
wxMacCoreGraphicsContext* context = new wxMacCoreGraphicsContext( this,
|
||||||
(CGContextRef)(mem_impl->GetGraphicsContext()->GetNativeContext()), (wxDouble) w, (wxDouble) h );
|
(CGContextRef)(mem_impl->GetGraphicsContext()->GetNativeContext()), (wxDouble) w, (wxDouble) h );
|
||||||
context->SetEnableOffsetFromScaleFactor(dc.GetContentScaleFactor());
|
context->SetContentScaleFactor(dc.GetContentScaleFactor());
|
||||||
return context;
|
return context;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
@@ -89,7 +89,9 @@ void wxMemoryDCImpl::DoSelect( const wxBitmap& bitmap )
|
|||||||
CGContextSetStrokeColorSpace( bmCtx, genericColorSpace );
|
CGContextSetStrokeColorSpace( bmCtx, genericColorSpace );
|
||||||
SetGraphicsContext( wxGraphicsContext::CreateFromNative( bmCtx ) );
|
SetGraphicsContext( wxGraphicsContext::CreateFromNative( bmCtx ) );
|
||||||
if (m_graphicContext)
|
if (m_graphicContext)
|
||||||
m_graphicContext->EnableOffset(m_contentScaleFactor <= 1);
|
{
|
||||||
|
m_graphicContext->SetContentScaleFactor(m_contentScaleFactor);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
m_ok = (m_graphicContext != NULL) ;
|
m_ok = (m_graphicContext != NULL) ;
|
||||||
}
|
}
|
||||||
|
Reference in New Issue
Block a user