Blame lib/dbtexmf/dblatex/xetex/fcfallback.py

Packit Service f3de8e
from __future__ import print_function
Packit Service f3de8e
Packit Service f3de8e
from dbtexmf.dblatex.xetex.fontspec import FontSpec
Packit Service f3de8e
from dbtexmf.dblatex.xetex.fcmanager import FcManager
Packit 0f19cf
Packit 0f19cf
Packit 0f19cf
class DefaultFontSpec(FontSpec):
Packit 0f19cf
    """
Packit 0f19cf
    The default fontspec gives priority to its children, and 
Packit 0f19cf
    contains any character.
Packit 0f19cf
    """
Packit 0f19cf
    def __init__(self):
Packit 0f19cf
        FontSpec.__init__(self, subfont_first=True)
Packit 0f19cf
    
Packit 0f19cf
    def contains(self, char):
Packit 0f19cf
        return True
Packit 0f19cf
Packit 0f19cf
Packit 0f19cf
class FcFallbackFontSpec(DefaultFontSpec):
Packit 0f19cf
    """
Packit 0f19cf
    Default fontspec that finds fonts from fontconfig 
Packit 0f19cf
    if the preexisting fontspecs don't match.
Packit 0f19cf
Packit 0f19cf
    Currently this class is the only interface between the
Packit 0f19cf
    two worlds (fontspec and fontconfig).
Packit 0f19cf
    """
Packit 0f19cf
    def __init__(self):
Packit 0f19cf
        DefaultFontSpec.__init__(self)
Packit 0f19cf
        self.fcmanager = FcManager()
Packit 0f19cf
        self.fccache = {}
Packit 0f19cf
        self.fcmissed = []
Packit 0f19cf
        try:
Packit 0f19cf
            self.fcmanager.build_fonts(partial=True)
Packit 0f19cf
        except:
Packit 0f19cf
            self.fcmanager = None
Packit 0f19cf
    
Packit 0f19cf
    def _loghas(self, id, char):
Packit 0f19cf
        pass 
Packit 0f19cf
Packit 0f19cf
    def _loghas2(self, id, char):
Packit 0f19cf
        DefaultFontSpec._loghas(self, id, char)
Packit 0f19cf
Packit 0f19cf
    def match(self, char, excluded=None):
Packit 0f19cf
        fontspec = DefaultFontSpec.match(self, char, excluded)
Packit 0f19cf
        if fontspec != self or not(self.fcmanager):
Packit 0f19cf
            self._loghas2(fontspec.id, char)
Packit 0f19cf
            return fontspec
Packit 0f19cf
Packit 0f19cf
        if self.isignored(char):
Packit 0f19cf
            self._loghas2(self.id, char)
Packit 0f19cf
            return self
Packit 0f19cf
Packit 0f19cf
        # Scan again the predefined fontspecs and check with fontconfig
Packit 0f19cf
        # if their charset can be extended
Packit 0f19cf
Packit 0f19cf
        for fontspec in self.fontspecs:
Packit 0f19cf
Packit 0f19cf
            if fontspec in self.fcmissed:
Packit Service f3de8e
                print("Specified font '%s' is missing in the system!" % \
Packit Service f3de8e
                      (fontspec.mainfont()))
Packit 0f19cf
                continue
Packit 0f19cf
Packit 0f19cf
            fcfont = self.fccache.get(fontspec.mainfont()) or \
Packit 0f19cf
                     self.fcmanager.get_font(fontspec.mainfont())
Packit 0f19cf
Packit 0f19cf
            if not(fcfont):
Packit 0f19cf
                self.fcmissed.append(fontspec)
Packit 0f19cf
                continue
Packit 0f19cf
Packit 0f19cf
            if fcfont.has_char(char):
Packit 0f19cf
                fontspec.add_char(char)
Packit 0f19cf
                self._loghas2(fontspec.id + "[fc]", char)
Packit 0f19cf
                return fontspec
Packit 0f19cf
Packit 0f19cf
        # Find the first fcfont that has this char in its charset
Packit 0f19cf
        fcfonts = {}
Packit 0f19cf
        for font_type in ("serif", "sans-serif", "monospace"):
Packit 0f19cf
            fcfonts[font_type] = self.fcmanager.get_font_handling(char,
Packit 0f19cf
                                                         family_type=font_type)
Packit 0f19cf
        # FIXME: attribuer les autres fonts si font nexiste pas dans le type
Packit 0f19cf
        if not(fcfont):
Packit 0f19cf
            self._loghas2(self.id + "[?fc]", char)
Packit 0f19cf
            return self
Packit 0f19cf
Packit 0f19cf
        # Extend the fontspec group
Packit 0f19cf
        fontspec = self.spawn_fontspec_from_fcfonts(fcfonts, char)
Packit 0f19cf
        self._loghas2(fontspec.id + "[A fc]", char)
Packit 0f19cf
        return fontspec
Packit 0f19cf
Packit 0f19cf
    def spawn_fontspec_from_fcfonts(self, fcfonts, char):
Packit 0f19cf
        self.log.info("New fontspec '%s' matching U%X from fontconfig"\
Packit 0f19cf
              % (fcfonts["serif"].family, ord(char)))
Packit 0f19cf
        # Create a new font
Packit 0f19cf
        fontspec = FontSpec()
Packit 0f19cf
        fontspec.id = fcfont.family
Packit 0f19cf
        fontspec.transitions["enter"]["main"] = fcfonts["serif"].family
Packit 0f19cf
        fontspec.transitions["enter"]["sans"] = fcfonts["sans-serif"].family
Packit 0f19cf
        fontspec.transitions["enter"]["mono"] = fcfonts["monospace"].family
Packit 0f19cf
        fontspec.add_char(char)
Packit 0f19cf
        fontspec.add_ignored(self._ignored)
Packit 0f19cf
        # Register the font and its related fontconfig object
Packit 0f19cf
        for fcfont in fcfonts.values():
Packit 0f19cf
            self.fccache[fcfont.name] = fcfont
Packit 0f19cf
        self.add_subfont(fontspec)
Packit 0f19cf
        return fontspec
Packit 0f19cf