From a9fcfe108568906dbd9dc8dfddcc10250b952e3a Mon Sep 17 00:00:00 2001 From: Artur Wieczorek Date: Sun, 2 Jul 2017 14:31:00 +0200 Subject: [PATCH] Fix getting/setting transformation matrix (wxOSX) Transformation settings already applied to the source objects (CGContext, wxWindow) and inherited by wxGraphicsContext should be considered as a baseline transformation matrix for wxGC and shouldn't be exposed through e.g. GetTransform() function (like it's done in Cairo or Direct2D). To report only transformations explicitly applied to wxGC by calls to the corresponding wxGC functions, we need to store initial CTM (in a dedicated variable) and "subtract" it from the actual transformation settings. See #17609. --- docs/changes.txt | 1 + src/osx/carbon/graphics.cpp | 26 ++++++++++++++++++++++---- 2 files changed, 23 insertions(+), 4 deletions(-) diff --git a/docs/changes.txt b/docs/changes.txt index be5dfb7794..085308bb49 100644 --- a/docs/changes.txt +++ b/docs/changes.txt @@ -211,6 +211,7 @@ wxOSX: - Update font code to use toll-free bridges from CTFontRef to NSFont or UIFont - Add a native implementation for clearing bitmap/window wxGraphicsContexts - wxiOS now needs a minimum of iOS 9 for deployment +- Fix handling CTM in wxGraphicsContext::SeTransform and GetTransform(). Unix: diff --git a/src/osx/carbon/graphics.cpp b/src/osx/carbon/graphics.cpp index a69f1370ac..bc3ef2562e 100644 --- a/src/osx/carbon/graphics.cpp +++ b/src/osx/carbon/graphics.cpp @@ -1393,6 +1393,7 @@ private: CGContextRef m_cgContext; WXWidget m_view; bool m_contextSynthesized; + CGAffineTransform m_initTransform; CGAffineTransform m_windowTransform; bool m_invisible; @@ -1466,6 +1467,7 @@ wxMacCoreGraphicsContext::wxMacCoreGraphicsContext( wxGraphicsRenderer* renderer SetNativeContext(cgcontext); m_width = width; m_height = height; + m_initTransform = CGContextGetCTM(m_cgContext); } wxMacCoreGraphicsContext::wxMacCoreGraphicsContext( wxGraphicsRenderer* renderer, wxWindow* window ): wxGraphicsContext(renderer) @@ -1502,6 +1504,7 @@ wxMacCoreGraphicsContext::wxMacCoreGraphicsContext( wxGraphicsRenderer* renderer m_windowTransform = CGAffineTransformScale( m_windowTransform , 1 , -1 ); m_windowTransform = CGAffineTransformTranslate( m_windowTransform, originX, originY ) ; #endif + m_initTransform = m_windowTransform; } wxMacCoreGraphicsContext::wxMacCoreGraphicsContext(wxGraphicsRenderer* renderer) : wxGraphicsContext(renderer) @@ -2401,16 +2404,18 @@ void wxMacCoreGraphicsContext::ConcatTransform( const wxGraphicsMatrix& matrix ) void wxMacCoreGraphicsContext::SetTransform( const wxGraphicsMatrix& matrix ) { CheckInvariants(); + CGAffineTransform t = *((CGAffineTransform*)matrix.GetNativeMatrix()); if ( m_cgContext ) { CGAffineTransform transform = CGContextGetCTM( m_cgContext ); transform = CGAffineTransformInvert( transform ) ; CGContextConcatCTM( m_cgContext, transform); - CGContextConcatCTM( m_cgContext, *(CGAffineTransform*) matrix.GetNativeMatrix()); + CGContextConcatCTM(m_cgContext, m_initTransform); + CGContextConcatCTM(m_cgContext, t); } else { - m_windowTransform = *(CGAffineTransform*) matrix.GetNativeMatrix(); + m_windowTransform = CGAffineTransformConcat(t, m_initTransform); } CheckInvariants(); } @@ -2419,8 +2424,21 @@ void wxMacCoreGraphicsContext::SetTransform( const wxGraphicsMatrix& matrix ) wxGraphicsMatrix wxMacCoreGraphicsContext::GetTransform() const { wxGraphicsMatrix m = CreateMatrix(); - *((CGAffineTransform*) m.GetNativeMatrix()) = ( m_cgContext == NULL ? m_windowTransform : - CGContextGetCTM( m_cgContext )); + CGAffineTransform* transformMatrix = (CGAffineTransform*)m.GetNativeMatrix(); + + if ( m_cgContext ) + { + *transformMatrix = CGContextGetCTM(m_cgContext); + } + else + { + *transformMatrix = m_windowTransform; + } + // Don't expose internal transformations. + CGAffineTransform initTransformInv = m_initTransform; + initTransformInv = CGAffineTransformInvert(initTransformInv); + *transformMatrix = CGAffineTransformConcat(*transformMatrix, initTransformInv); + return m; }