[cairo] A patch to detect CTFont API availability (Re: [PATCH 2/3] Update README with new minimum MacOSX requirements)

Andrea Canciani ranma42 at gmail.com
Tue Mar 10 11:02:24 PDT 2015


On Tue, Mar 10, 2015 at 5:23 PM, suzuki toshiya <mpsuzuki at hiroshima-u.ac.jp>
wrote:

> Hi,
>
> Andrea Canciani wrote:
> > On Tue, Mar 10, 2015 at 12:17 PM, suzuki toshiya <
> mpsuzuki at hiroshima-u.ac.jp
> >> I don't think the change is too complex to drop Mac OS X 10.4
> >> support... How do you think of?
> >
> > The change itself is not very complex, but maintaining 10.4 is becoming
> > unfeasible, given that testing is very hard.
> > This is confirmed by the bug you have in your patch :P (see comment
> inline).
>
> Oops. However, my bug seems to appear in the newest environment
> which lacks old API (and I don't have such environment yet X-O,
> so it does not show the difficulty to test 10.4 (I can do that,
> if somebody could give the collection of the expected results).
>

Sorry, you're right. That typo does not show the difficulty to test 10.4
specifically, but it suggests that relying on conditional compilation and
dynamic linking is more error prone. If you used the function directly, the
compiler would have warned about a missing declaration and the linker about
an unresolved symbol.


> > Another option, which at least to me sounds very appealing, is to let
> 10.4
> > die (from Apple's point of view, it's unsupported since September 2009)
> and
> > cleanup cairo-quartz as in
> >
> http://cgit.freedesktop.org/~ranma42/cairo/commit/?h=wip/remove-10.4&id=66b5419704aa1971c77de764fd94b2f7d2a05b76
> > This would remove most of the weirdness in the quartz backend (the two
> > bigger culprits are currently blend modes and font metrics).
>
> > Of course, if the remove-10.4 branch was merged, the patch to restore
> 10.4
> > would be much more complex, so we could say that supporting 10.4
> requires a
> > significant complexity in cairo-quartz.
>
> Hmm. I found that you are planning to remove runtime resolving by
> dlsym() completely. One of my concern is that Apple's font framework
> would never be stable (QuickDraw, AppleTypeService, CoreGraphics,
> CoreText,...). Even if cairo concentrates to CoreText font API, cairo
> might be asked to support new/better font framework within several
> years - then, the maintainer should choose again; the simplicity or
> multiple framework support. Is it a time to start simplicity?
>

I do not believe that we will be able to completely get rid of it in the
short term, but as you have probably noticed if we remove support for 10.4
there are only a couple of remaining dlsym-ed functions.

Ideally I would expect a new font/surface backend to be written when a new
framework is released.
I am not sure why this was not the case for the pre-CoreText age (I was not
yet working on cairo-quartz at that time), but my guess is that quite a lot
of it relied on private functions, that were needed to access the features
which Cairo relied upon.
I would be somewhat surprised if, upon the release of a new framework, font
metric computation, blend modes or any currently available functions was
completely removed.
Nonetheless I expect code to worsen when transitioning to a new framework
(even if we try to keep it clean by making separate backends), but I would
definitely aim for supporting a limited time span. For example, I think it
would be a very bad idea to inflate cairo-quartz with support for
QuickDraw. If anybody wanted it inside cairo, I would definitely suggest a
separate backend (possibly with utility functions for
CoreGraphics/QuickDraw interaction).

This reminds me that I started working towards a CoreText font backend...
I should probably take some time to figure out if it makes sense to
continue working on it, as it might now be an interesting alternative to
the CoreGraphics font API.

Andrea


> Regards,
> mpsuzuki
>
> > Andrea
> >
> >
> >> Regards,
> >> mpsuzuki
> >>
> >>
> >> Andrea Canciani wrote:
> >>> From: Andrea Canciani <ranma42 at tartaros.local>
> >>>
> >>> Since 70cc8f250b5669e757b4f044571ba0f71e3dea9e the quartz backend is
> >>> using some APIs that are not available on MacOSX 10.4 directly
> >>> (i.e. without detecting their availability through dynamic linking).
> >>> This means that the quartz backend does not work anymore on MacOSX
> >>> 10.4 and that the 10.5 SDK (or newer) is needed to build.
> >>> ---
> >>>  README | 2 +-
> >>>  1 file changed, 1 insertion(+), 1 deletion(-)
> >>>
> >>> diff --git a/README b/README
> >>> index 5926430..0be9947 100644
> >>> --- a/README
> >>> +++ b/README
> >>> @@ -121,7 +121,7 @@ Supported, "platform" surface backends
> >>>
> >>>       quartz backend
> >>>       --------------
> >>> -     MacOS X >= 10.4 with Xcode >= 2.4
> >>> +     MacOS X >= 10.5 with Xcode >= 3.0
> >>>
> >>>       win32 backend
> >>>       -------------
> >
> > diff --git a/configure.ac b/configure.ac
> >
> > index 2ce1959..23216c2 100644
> >> --- a/configure.ac
> >> +++ b/configure.ac
> >> @@ -210,8 +210,43 @@ CAIRO_ENABLE_SURFACE_BACKEND(quartz, Quartz, auto,
> [
> >>
> >>  CAIRO_ENABLE_FONT_BACKEND(quartz_font, Quartz, auto, [
> >>    use_quartz_font=$use_quartz
> >> +  if test "x$use_quartz_font" = "xyes" ; then
> >> +    dnl include Quartz header to check CTFontRef declaration
> >> +    header_for_CTFontRef=""
> >> +    if test
> "x${ac_cv_header_ApplicationServices_ApplicationServices_h}"
> >> = "xyes" ; then
> >> +      header_for_CTFontRef=ApplicationServices/ApplicationServices.h
> >> +    else
> >> +      AC_CHECK_HEADER(CoreText/CoreText.h,[
> >> +        header_for_CTFontRef=CoreText/CoreText.h
> >> +      ],[])
> >> +    fi
> >> +
> >> +    if test "x${header_for_CTFontRef}" != "x" ; then
> >> +      AC_CHECK_TYPE(CTFontRef,[
> >> +          AC_DEFINE([QUARTZ_HAS_CTFONTREF_T], 1, [Define to 1 if
> >> CTFontRef type is defined in CTFont.h])
> >> +        ],[],[#include "${header_for_CTFontRef}"]
> >> +      )
> >> +    fi
> >> +  fi
> >>  ])
> >>
> >> +if test "x$use_quartz" = "xyes" ; then
> >> +  dnl include Quartz header to check CGDataProviderReleaseDataCallback
> >> declaration
> >> +  header_for_CGDataProviderReleaseDataCallback=""
> >> +  if test "x${ac_cv_header_ApplicationServices_ApplicationServices_h}"
> =
> >> "xyes" ; then
> >> +
> >>
> header_for_CGDataProviderReleaseDataCallback=ApplicationServices/ApplicationServices.h
> >> +  elif test "x${ac_cv_header_CoreGraphics_CoreGraphics_h}" = "xyes" ;
> then
> >> +
> >> header_for_CGDataProviderReleaseDataCallback=CoreGraphics/CoreGraphics.h
> >> +  fi
> >> +
> >> +  if test "x${header_for_CGDataProviderReleaseDataCallback}" != "x" ;
> then
> >> +    AC_CHECK_TYPE(CGDataProviderReleaseDataCallback,[
> >> +        AC_DEFINE([QUARTZ_HAS_CGDATAPROVIDERRELEASEDATACALLBACK_T], 1,
> >> [Define to 1 if CGDataProviderReleaseDataCallback type is defined in
> >> CGDataProvider.h])
> >> +      ],[],[#include "${header_for_CGDataProviderReleaseDataCallback}"]
> >> +    )
> >> +  fi
> >> +fi
> >> +
> >>  CAIRO_ENABLE_SURFACE_BACKEND(quartz_image, Quartz Image, no, [
> >>    use_quartz_image=$use_quartz
> >>  ])
> >> diff --git a/src/cairo-quartz-font.c b/src/cairo-quartz-font.c
> >> index 02f3426..35fe24d 100644
> >> --- a/src/cairo-quartz-font.c
> >> +++ b/src/cairo-quartz-font.c
> >> @@ -81,6 +81,18 @@ static void (*CGFontGetGlyphsForUnicharsPtr)
> >> (CGFontRef, const UniChar[], const
> >>  static void (*CGContextSetAllowsFontSmoothingPtr) (CGContextRef, bool)
> =
> >> NULL;
> >>  static bool (*CGContextGetAllowsFontSmoothingPtr) (CGContextRef) =
> NULL;
> >>
> >> +/* Not public in the least bit */
> >> +static CGPathRef (*CGFontGetGlyphPathPtr) (CGFontRef fontRef,
> >> CGAffineTransform *textTransform, int unknown, CGGlyph glyph) = NULL;
> >> +
> >> +/* CoreText Replacement of CGFontGetGlyphPathPtr */
> >> +#ifdef QUARTZ_HAS_CTFONTREF_T
> >
> > +static CTFontRef (*CTFontCreateWithGraphicsFontPtr) (CGFontRef , CGFloat
> >> size, const CGAffineTransform*, CTFontDescriptorRef) = NULL;
> >
> > +static CGPathRef (*CTFontCreatePathForGlyphPtr) (CTFontRef, CGGlyph,
> >> CGAffineTransform *) = NULL;
> >> +#else
> >> +static void* CTFontCreateWithGraphicsFontPtr = NULL;
> >> +static void* CTFontCreatePathForGlyphPtr = NULL;
> >> +#endif
> >> +
> >>  /* CGFontGetHMetrics isn't public, but the other functions are
> >> public/present in 10.5 */
> >>  typedef struct {
> >>      int ascent;
> >> @@ -125,6 +137,13 @@ quartz_font_ensure_symbols(void)
> >>      CGFontGetUnitsPerEmPtr = dlsym(RTLD_DEFAULT,
> "CGFontGetUnitsPerEm");
> >>      CGFontGetGlyphAdvancesPtr = dlsym(RTLD_DEFAULT,
> >> "CGFontGetGlyphAdvances");
> >>
> >> +#ifdef QUARTZ_HAS_CTFONTREF_T
> >> +    CTFontCreateWithGraphicsFontPtr = dlsym(RTLD_DEFAULT,
> >> "CTFontCreateWithGraphicsFont");
> >> +    CTFontCreatePathForGlyphPtr = dlsym(RTLD_DEFAULT,
> >> "CTFontCreatePathForGlyphPtr");
> >>
> >
> > Hidden bug!
> > CTFontCreatePathForGlyphPtr = dlsym(RTLD_DEFAULT,
> > "CTFontCreatePathForGlyphPtr");
> > should be
> > CTFontCreatePathForGlyphPtr = dlsym(RTLD_DEFAULT,
> > "CTFontCreatePathForGlyph");
> >
> >
> >> +    if (!CTFontCreateWithGraphicsFontPtr ||
> !CTFontCreatePathForGlyphPtr)
> >> +#endif
> >> +       CGFontGetGlyphPathPtr = dlsym(RTLD_DEFAULT,
> "CGFontGetGlyphPath");
> >> +
> >>      CGFontGetHMetricsPtr = dlsym(RTLD_DEFAULT, "CGFontGetHMetrics");
> >>      CGFontGetAscentPtr = dlsym(RTLD_DEFAULT, "CGFontGetAscent");
> >>      CGFontGetDescentPtr = dlsym(RTLD_DEFAULT, "CGFontGetDescent");
> >> @@ -140,6 +159,7 @@ quartz_font_ensure_symbols(void)
> >>         CGFontGetGlyphsForUnicharsPtr &&
> >>         CGFontGetUnitsPerEmPtr &&
> >>         CGFontGetGlyphAdvancesPtr &&
> >> +       ((CTFontCreateWithGraphicsFontPtr &&
> CTFontCreatePathForGlyphPtr)
> >> || CGFontGetGlyphPathPtr) &&
> >>         (CGFontGetHMetricsPtr || (CGFontGetAscentPtr &&
> >> CGFontGetDescentPtr && CGFontGetLeadingPtr)))
> >>         _cairo_quartz_font_symbols_present = TRUE;
> >>
> >> @@ -545,7 +565,6 @@ _cairo_quartz_init_glyph_path
> >> (cairo_quartz_scaled_font_t *font,
> >>      CGGlyph glyph = _cairo_quartz_scaled_glyph_index (scaled_glyph);
> >>      CGAffineTransform textMatrix;
> >>      CGPathRef glyphPath;
> >> -    CTFontRef ctFont;
> >>      cairo_path_fixed_t *path;
> >>
> >>      if (glyph == INVALID_GLYPH) {
> >> @@ -560,9 +579,14 @@ _cairo_quartz_init_glyph_path
> >> (cairo_quartz_scaled_font_t *font,
> >>                                         -font->base.scale.yy,
> >>                                         0, 0);
> >>
> >> -    ctFont = CTFontCreateWithGraphicsFont (font_face->cgFont, 0.0,
> NULL,
> >> NULL);
> >> -    glyphPath = CTFontCreatePathForGlyph (ctFont, glyph, &textMatrix);
> >> -    CFRelease (ctFont);
> >> +#ifdef QUARTZ_HAS_CTFONTREF_T
> >> +    if (CTFontCreateWithGraphicsFontPtr &&
> CTFontCreatePathForGlyphPtr) {
> >> +        CTFontRef ctFont = CTFontCreateWithGraphicsFontPtr
> >> (font_face->cgFont, 0.0, NULL, NULL);
> >> +        glyphPath = CTFontCreatePathForGlyphPtr (ctFont, glyph,
> >> &textMatrix);
> >> +        CFRelease (ctFont);
> >> +    } else
> >> +#endif
> >> +       glyphPath = CGFontGetGlyphPathPtr (font_face->cgFont,
> &textMatrix,
> >> 0, glyph);
> >>      if (!glyphPath)
> >>         return CAIRO_INT_STATUS_UNSUPPORTED;
> >>
> >>
> >>
> >
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.cairographics.org/archives/cairo/attachments/20150310/6da6a2cf/attachment-0001.html>


More information about the cairo mailing list