Ejemplo n.º 1
0
 def __init__(self, enum,*args):
     if isSeq(enum):
         if args!=():
             raise ValueError("Either all singleton args or a single sequence argument")
         self._enum = tuple(enum)+args
     else:
         self._enum = (enum,)+args
Ejemplo n.º 2
0
def addProxyAttribute(src,name,validate=None,desc=None,initial=None,dst=None):
    '''
    Add a proxy attribute 'name' to src with targets dst
    '''
    #sanity
    assert hasattr(src,'_attrMap'), 'src object has no _attrMap'
    A, oA = _privateAttrMap(src,1)
    if not isSeq(dst): dst = dst,
    D = []
    DV = []
    for d in dst:
        if isSeq(d):
            d, e = d[0], d[1:]
        obj, attr = _findObjectAndAttr(src,d)
        if obj:
            dA = getattr(obj,'_attrMap',None)
Ejemplo n.º 3
0
 def __init__(
     self,
     id=None,
     frames=[],
     onPage=_doNothing,
     onPageEnd=_doNothing,
     pagesize=None,
     autoNextPageTemplate=None,
     cropBox=None,
     artBox=None,
     trimBox=None,
     bleedBox=None,
 ):
     frames = frames or []
     if not isSeq(frames):
         frames = [frames]
     assert [x for x in frames if not isinstance(x, Frame)] == [], "frames argument error"
     self.id = id
     self.frames = frames
     self.onPage = onPage
     self.onPageEnd = onPageEnd
     self.pagesize = pagesize
     self.autoNextPageTemplate = autoNextPageTemplate
     self.cropBox = cropBox
     self.artBox = artBox
     self.trimBox = trimBox
     self.bleedBox = bleedBox
Ejemplo n.º 4
0
    def _expandWidths(self, compactWidthArray):
        """Expands Adobe nested list structure to get a dictionary of widths.

        Here is an example of such a structure.::
        
            (
            # starting at character ID 1, next n  characters have the widths given.
            1,  (277,305,500,668,668,906,727,305,445,445,508,668,305,379,305,539),
            # all Characters from ID 17 to 26 are 668 em units wide
            17, 26, 668,
            27, (305, 305, 668, 668, 668, 566, 871, 727, 637, 652, 699, 574, 555,
                 676, 687, 242, 492, 664, 582, 789, 707, 734, 582, 734, 605, 605,
                 641, 668, 727, 945, 609, 609, 574, 445, 668, 445, 668, 668, 590,
                 555, 609, 547, 602, 574, 391, 609, 582, 234, 277, 539, 234, 895,
                 582, 605, 602, 602, 387, 508, 441, 582, 562, 781, 531, 570, 555,
                 449, 246, 449, 668),
            # these must be half width katakana and the like.
            231, 632, 500
            )
        
        """
        data = compactWidthArray[:]
        widths = {}
        while data:
            start, data = data[0], data[1:]
            if isSeq(data[0]):
                items, data = data[0], data[1:]
                for offset in range(len(items)):
                    widths[start + offset] = items[offset]
            else:
                end, width, data = data[0], data[1], data[2:]
                for idx in range(start, end+1):
                    widths[idx] = width
        return widths
Ejemplo n.º 5
0
 def __init__(self,action=()):
     #must call super init to ensure it has a width and height (of zero),
     #as in some cases the packer might get called on it...
     Flowable.__init__(self)
     if not isSeq(action):
         action = (action,)
     self.action = tuple(action)
Ejemplo n.º 6
0
 def addPageTemplates(self,pageTemplates):
     'add one or a sequence of pageTemplates'
     if not isSeq(pageTemplates):
         pageTemplates = [pageTemplates]
     #this test below fails due to inconsistent imports!
     #assert filter(lambda x: not isinstance(x,PageTemplate), pageTemplates)==[], "pageTemplates argument error"
     for t in pageTemplates:
         self.pageTemplates.append(t)
Ejemplo n.º 7
0
def _evalMeasurement(n):
    if isinstance(n, str):
        from reportlab.platypus.paraparser import _num

        n = _num(n)
        if isSeq(n):
            n = n[1]
    return n
Ejemplo n.º 8
0
 def _samePT(self,npt):
     if isSeq(npt):
         return getattr(self,'_nextPageTemplateCycle',[])
     if isinstance(npt,strTypes):
         return npt == (self.pageTemplates[self._nextPageTemplateIndex].id if hasattr(self,'_nextPageTemplateIndex') else self.pageTemplate.id)
     if isinstance(npt,int) and 0<=npt<len(self.pageTemplates):
         if hasattr(self,'_nextPageTemplateIndex'):
             return npt==self._nextPageTemplateIndex
         return npt==self.pageTemplates.find(self.pageTemplate)
Ejemplo n.º 9
0
 def test(self, x):
     if not isSeq(x):
         if x is None: return self._NoneOK
         return False
     if x==[] or x==():
         return self._emptyOK
     elif not self._lo<=len(x)<=self._hi: return False
     for e in x:
         if not self._elemTest(e): return False
     return True
Ejemplo n.º 10
0
 def test(self, x):
     from reportlab.graphics.shapes import Shape
     if isSeq(x):
         answer = 1
         for e in x:
             if not isinstance(e, Shape):
                 answer = 0
         return answer
     else:
         return False
Ejemplo n.º 11
0
 def test(self, x):
     if isSeq(x):
         if len(x) == 6:
             for element in x:
                 if not isNumber(element):
                     return False
             return True
         else:
             return False
     else:
         return False
Ejemplo n.º 12
0
    def getContext(self, tag):
        """Return main context for tag

        >>> g = Cleaner()
        >>> eqCheck(g.getContext('i'),'inline')
        >>> eqCheck(g.getContext('li'),'list')
        """
        context = self._tagDict[tag]['context']
        if isSeq(context):
            return context[0]
        return context
Ejemplo n.º 13
0
def structToPDF(structure):
    "Converts deeply nested structure to PDFdoc dictionary/array objects"
    if isinstance(structure,dict):
        newDict = {}
        for k, v in structure.items():
            newDict[k] = structToPDF(v)
        return pdfdoc.PDFDictionary(newDict)
    elif isSeq(structure):
        newList = []
        for elem in structure:
            newList.append(structToPDF(elem))
        return pdfdoc.PDFArray(newList)
    else:
        return structure
Ejemplo n.º 14
0
    def __init__(self,BASE=None,UNWANTED=[],**kw):
        data = {}
        if BASE:
            if isinstance(BASE,AttrMap):
                data = BASE
            else:
                if not isSeq(BASE): BASE = (BASE,)
                for B in BASE:
                    am = getattr(B,'_attrMap',self)
                    if am is not self:
                        if am: data.update(am)
                    else:
                        raise ValueError('BASE=%s has wrong kind of value' % ascii(B))

        dict.__init__(self,data)
        self.remove(UNWANTED)
        self.update(kw)
Ejemplo n.º 15
0
    def __init__(self,BASE=None,UNWANTED=[],**kw):
        data = {}
        if BASE:
            if isinstance(BASE,AttrMap):
                data = BASE
            else:
                if not isSeq(BASE): BASE = (BASE,)
                for B in BASE:
                    am = getattr(B,'_attrMap',self)
                    if am is not self:
                        if am: data.update(am)
                    else:
                        raise ValueError('BASE=%s has wrong kind of value' % ascii(B))

        dict.__init__(self,data)
        self.remove(UNWANTED)
        self.update(kw)
Ejemplo n.º 16
0
 def __init__(self,
              id=None,
              frames=[],
              onPage=_doNothing,
              onPageEnd=_doNothing,
              pagesize=None,
              autoNextPageTemplate=None):
     frames = frames or []
     if not isSeq(frames): frames = [frames]
     assert [x for x in frames
             if not isinstance(x, Frame)] == [], "frames argument error"
     self.id = id
     self.frames = frames
     self.onPage = onPage
     self.onPageEnd = onPageEnd
     self.pagesize = pagesize
     self.autoNextPageTemplate = autoNextPageTemplate
Ejemplo n.º 17
0
    def start_stylesheet(self, args):
        #makes it the current style sheet.
        path = self._arg('stylesheet',args,'path')
        if path=='None': path = []
        if not isSeq(path): path = [path]
        path.append('styles')
        path.append(os.getcwd())
        modulename = self._arg('stylesheet', args, 'module')
        funcname = self._arg('stylesheet', args, 'function')
        try:
            found = imp.find_module(modulename, path)
            (file, pathname, description) = found
            mod = imp.load_module(modulename, file, pathname, description)
        except ImportError:
            #last gasp
            mod = getModule(modulename)

        #now get the function
        func = getattr(mod, funcname)
        pythonpoint.setStyles(func())
Ejemplo n.º 18
0
def _getWidths(i,s, fontName, fontSize, subCols):
    S = []
    aS = S.append
    if isSeq(s):
        for j,t in enumerate(s):
            sc = subCols[j,i]
            fN = getattr(sc,'fontName',fontName)
            fS = getattr(sc,'fontSize',fontSize)
            m = [stringWidth(x, fN, fS) for x in t.split('\n')]
            m = max(sc.minWidth,m and max(m) or 0)
            aS(m)
            aS(sc.rpad)
        del S[-1]
    else:
        sc = subCols[0,i]
        fN = getattr(sc,'fontName',fontName)
        fS = getattr(sc,'fontSize',fontSize)
        m = [stringWidth(x, fN, fS) for x in s.split('\n')]
        aS(max(sc.minWidth,m and max(m) or 0))
    return S
Ejemplo n.º 19
0
def _getWidths(i,s, fontName, fontSize, subCols):
    S = []
    aS = S.append
    if isSeq(s):
        for j,t in enumerate(s):
            sc = subCols[j,i]
            fN = getattr(sc,'fontName',fontName)
            fS = getattr(sc,'fontSize',fontSize)
            m = [stringWidth(x, fN, fS) for x in t.split('\n')]
            m = max(sc.minWidth,m and max(m) or 0)
            aS(m)
            aS(sc.rpad)
        del S[-1]
    else:
        sc = subCols[0,i]
        fN = getattr(sc,'fontName',fontName)
        fS = getattr(sc,'fontSize',fontSize)
        m = [stringWidth(x, fN, fS) for x in s.split('\n')]
        aS(max(sc.minWidth,m and max(m) or 0))
    return S
Ejemplo n.º 20
0
    def start_stylesheet(self, args):
        #makes it the current style sheet.
        path = self._arg('stylesheet', args, 'path')
        if path == 'None': path = []
        if not isSeq(path): path = [path]
        path.append('styles')
        path.append(os.getcwd())
        modulename = self._arg('stylesheet', args, 'module')
        funcname = self._arg('stylesheet', args, 'function')
        try:
            found = imp.find_module(modulename, path)
            (file, pathname, description) = found
            mod = imp.load_module(modulename, file, pathname, description)
        except ImportError:
            #last gasp
            mod = getModule(modulename)

        #now get the function
        func = getattr(mod, funcname)
        pythonpoint.setStyles(func())
Ejemplo n.º 21
0
 def fp_str(*a):
     '''convert separate arguments (or single sequence arg) into space separated numeric strings'''
     if len(a) == 1 and isSeq(a[0]): a = a[0]
     s = []
     A = s.append
     for i in a:
         sa = abs(i)
         if sa <= 1e-7: A('0')
         else:
             l = sa <= 1 and 6 or min(max(0, (6 - int(_log_10(sa)))), 6)
             n = _fp_fmts[l] % i
             if l:
                 j = len(n)
                 while j:
                     j -= 1
                     if n[j] != '0':
                         if n[j] != '.': j += 1
                         break
                 n = n[:j]
             A((n[0] != '0' or len(n) == 1) and n or n[1:])
     return ' '.join(s)
Ejemplo n.º 22
0
 def fp_str(*a):
     '''convert separate arguments (or single sequence arg) into space separated numeric strings'''
     if len(a)==1 and isSeq(a[0]): a = a[0]
     s = []
     A = s.append
     for i in a:
         sa =abs(i)
         if sa<=1e-7: A('0')
         else:
             l = sa<=1 and 6 or min(max(0,(6-int(_log_10(sa)))),6)
             n = _fp_fmts[l]%i
             if l:
                 j = len(n)
                 while j:
                     j -= 1
                     if n[j]!='0':
                         if n[j]!='.': j += 1
                         break
                 n = n[:j]
             A((n[0]!='0' or len(n)==1) and n or n[1:])
     return ' '.join(s)
Ejemplo n.º 23
0
    def handle_nextPageTemplate(self, pt):
        '''On endPage change to the page template with name or index pt'''
        if isinstance(pt, strTypes):
            if hasattr(self, '_nextPageTemplateCycle'):
                del self._nextPageTemplateCycle
            for t in self.pageTemplates:
                if t.id == pt:
                    self._nextPageTemplateIndex = self.pageTemplates.index(t)
                    return
            raise ValueError("can't find template('%s')" % pt)
        elif isinstance(pt, int):
            if hasattr(self, '_nextPageTemplateCycle'):
                del self._nextPageTemplateCycle
            self._nextPageTemplateIndex = pt
        elif isSeq(pt):
            #used for alternating left/right pages
            #collect the refs to the template objects, complain if any are bad
            c = PTCycle()
            for ptn in pt:
                found = 0
                if ptn == '*':  #special case name used to short circuit the iteration
                    c._restart = len(c)
                    continue
                for t in self.pageTemplates:
                    if t.id == ptn:
                        c.append(t)
                        found = 1
                if not found:
                    raise ValueError("Cannot find page template called %s" %
                                     ptn)
            if not c:
                raise ValueError("No valid page templates in cycle")
            elif c._restart > len(c):
                raise ValueError("Invalid cycle restart position")

            #ensure we start on the first one
            self._nextPageTemplateCycle = c.cyclicIterator()
        else:
            raise TypeError("argument pt should be string or integer or list")
 def __init__(self, name, base=None):
     self.name = name
     self.frozen = 0
     if name in standardEncodings:
         assert base is None, "Can't have a base encoding for a standard encoding"
         self.baseEncodingName = name
         self.vector = _fontdata.encodings[name]
     elif base == None:
         # assume based on the usual one
         self.baseEncodingName = defaultEncoding
         self.vector = _fontdata.encodings[defaultEncoding]
     elif isStr(base):
         baseEnc = getEncoding(base)
         self.baseEncodingName = baseEnc.name
         self.vector = baseEnc.vector[:]
     elif isSeq(base):
         self.baseEncodingName = defaultEncoding
         self.vector = base[:]
     elif isinstance(base, Encoding):
         # accept a vector
         self.baseEncodingName = base.name
         self.vector = base.vector[:]
Ejemplo n.º 25
0
    def handle_nextPageTemplate(self, pt):
        """On endPage change to the page template with name or index pt"""
        if isinstance(pt, strTypes):
            if hasattr(self, "_nextPageTemplateCycle"):
                del self._nextPageTemplateCycle
            for t in self.pageTemplates:
                if t.id == pt:
                    self._nextPageTemplateIndex = self.pageTemplates.index(t)
                    return
            raise ValueError("can't find template('%s')" % pt)
        elif isinstance(pt, int):
            if hasattr(self, "_nextPageTemplateCycle"):
                del self._nextPageTemplateCycle
            self._nextPageTemplateIndex = pt
        elif isSeq(pt):
            # used for alternating left/right pages
            # collect the refs to the template objects, complain if any are bad
            c = PTCycle()
            for ptn in pt:
                found = 0
                if ptn == "*":  # special case name used to short circuit the iteration
                    c._restart = len(c)
                    continue
                for t in self.pageTemplates:
                    if t.id == ptn:
                        c.append(t)
                        found = 1
                if not found:
                    raise ValueError("Cannot find page template called %s" % ptn)
            if not c:
                raise ValueError("No valid page templates in cycle")
            elif c._restart > len(c):
                raise ValueError("Invalid cycle restart position")

            # ensure we start on the first one
            self._nextPageTemplateCycle = c
        else:
            raise TypeError("argument pt should be string or integer or list")
Ejemplo n.º 26
0
    def draw(self):
        colorNamePairs = self.colorNamePairs
        autoCP = isAuto(colorNamePairs)
        if autoCP:
            chart = getattr(colorNamePairs,'chart',getattr(colorNamePairs,'obj',None))
            swatchMarker = None
            autoCP = Auto(obj=chart)
            n = chart._seriesCount
            chartTexts = self._getTexts(colorNamePairs)
        else:
            swatchMarker = getattr(self,'swatchMarker',None)
            if isAuto(swatchMarker):
                chart = getattr(swatchMarker,'chart',getattr(swatchMarker,'obj',None))
                swatchMarker = Auto(obj=chart)
            n = len(colorNamePairs)
        dx = self.dx
        dy = self.dy
        alignment = self.alignment
        columnMaximum = self.columnMaximum
        deltax = self.deltax
        deltay = self.deltay
        dxTextSpace = self.dxTextSpace
        fontName = self.fontName
        fontSize = self.fontSize
        fillColor = self.fillColor
        strokeWidth = self.strokeWidth
        strokeColor = self.strokeColor
        subCols = self.subCols
        leading = fontSize*1.2
        yGap = self.yGap
        if not deltay:
            deltay = max(dy,leading)+self.autoYPadding
        ba = self.boxAnchor
        maxWidth = self._calculateMaxBoundaries(colorNamePairs)
        nCols = int((n+columnMaximum-1)/(columnMaximum*1.0))
        xW = dx+dxTextSpace+self.autoXPadding
        variColumn = self.variColumn
        if variColumn:
            width = sum([m[-1] for m in maxWidth])+xW*nCols
        else:
            deltax = max(maxWidth[-1]+xW,deltax)
            width = nCols*deltax
            maxWidth = nCols*[maxWidth]

        thisx = self.x
        thisy = self.y - self.dy
        if ba not in ('ne','n','nw','autoy'):
            height = self._calcHeight()
            if ba in ('e','c','w'):
                thisy += height/2.
            else:
                thisy += height
        if ba not in ('nw','w','sw','autox'):
            if ba in ('n','c','s'):
                thisx -= width/2
            else:
                thisx -= width
        upperlefty = thisy

        g = Group()

        ascent=getFont(fontName).face.ascent/1000.
        if ascent==0: ascent=0.718 # default (from helvetica)
        ascent *= fontSize # normalize

        lim = columnMaximum - 1
        callout = getattr(self,'callout',None)
        scallout = getattr(self,'swatchCallout',None)
        dividerLines = self.dividerLines
        if dividerLines:
            dividerWidth = self.dividerWidth
            dividerColor = self.dividerColor
            dividerDashArray = self.dividerDashArray
            dividerOffsX = self.dividerOffsX
            dividerOffsY = self.dividerOffsY

        for i in xrange(n):
            if autoCP:
                col = autoCP
                col.index = i
                name = chartTexts[i]
            else:
                col, name = colorNamePairs[i]
                if isAuto(swatchMarker):
                    col = swatchMarker
                    col.index = i
                if isAuto(name):
                    name = getattr(swatchMarker,'chart',getattr(swatchMarker,'obj',None)).getSeriesName(i,'series %d' % i)
            T = _getLines(name)
            S = []
            aS = S.append
            j = int(i/(columnMaximum*1.0))
            jOffs = maxWidth[j]

            # thisy+dy/2 = y+leading/2
            y = y0 = thisy+(dy-ascent)*0.5

            if callout: callout(self,g,thisx,y,(col,name))
            if alignment == "left":
                x = thisx
                xn = thisx+jOffs[-1]+dxTextSpace
            elif alignment == "right":
                x = thisx+dx+dxTextSpace
                xn = thisx
            else:
                raise ValueError("bad alignment")
            if not isSeq(name):
                T = [T]
            yd = y
            for k,lines in enumerate(T):
                y = y0
                kk = k*2
                x1 = x+jOffs[kk]
                x2 = x+jOffs[kk+1]
                sc = subCols[k,i]
                anchor = sc.align
                scdx = sc.dx
                scdy = sc.dy
                fN = getattr(sc,'fontName',fontName)
                fS = getattr(sc,'fontSize',fontSize)
                fC = getattr(sc,'fillColor',fillColor)
                fL = getattr(sc,'leading',1.2*fontSize)
                if fN==fontName:
                    fA = (ascent*fS)/fontSize
                else:
                    fA = getFont(fontName).face.ascent/1000.
                    if fA==0: fA=0.718
                    fA *= fS
                if anchor=='left':
                    anchor = 'start'
                    xoffs = x1
                elif anchor=='right':
                    anchor = 'end'
                    xoffs = x2
                elif anchor=='numeric':
                    xoffs = x2
                else:
                    anchor = 'middle'
                    xoffs = 0.5*(x1+x2)
                for t in lines:
                    aS(String(xoffs+scdx,y+scdy,t,fontName=fN,fontSize=fS,fillColor=fC, textAnchor = anchor))
                    y -= fL
                yd = min(yd,y)
                y += fL
                for iy, a in ((y-max(fL-fA,0),'underlines'),(y+fA,'overlines')):
                    il = getattr(sc,a,None)
                    if il:
                        if not isinstance(il,(tuple,list)): il = (il,)
                        for l in il:
                            l = copy.copy(l)
                            l.y1 += iy
                            l.y2 += iy
                            l.x1 += x1
                            l.x2 += x2
                            aS(l)
            x = xn
            y = yd
            leadingMove = 2*y0-y-thisy

            if dividerLines:
                xd = thisx+dx+dxTextSpace+jOffs[-1]+dividerOffsX[1]
                yd = thisy+dy*0.5+dividerOffsY
                if ((dividerLines&1) and i%columnMaximum) or ((dividerLines&2) and not i%columnMaximum):
                    g.add(Line(thisx+dividerOffsX[0],yd,xd,yd,
                        strokeColor=dividerColor, strokeWidth=dividerWidth, strokeDashArray=dividerDashArray))

                if (dividerLines&4) and (i%columnMaximum==lim or i==(n-1)):
                    yd -= max(deltay,leadingMove)+yGap
                    g.add(Line(thisx+dividerOffsX[0],yd,xd,yd,
                        strokeColor=dividerColor, strokeWidth=dividerWidth, strokeDashArray=dividerDashArray))

            # Make a 'normal' color swatch...
            swatchX = x + getattr(self,'swdx',0)
            swatchY = thisy + getattr(self,'swdy',0)

            if isAuto(col):
                chart = getattr(col,'chart',getattr(col,'obj',None))
                c = chart.makeSwatchSample(getattr(col,'index',i),swatchX,swatchY,dx,dy)
            elif isinstance(col, colors.Color):
                if isSymbol(swatchMarker):
                    c = uSymbol2Symbol(swatchMarker,swatchX+dx/2.,swatchY+dy/2.,col)
                else:
                    c = self._defaultSwatch(swatchX,swatchY,dx,dy,fillColor=col,strokeWidth=strokeWidth,strokeColor=strokeColor)
            elif col is not None:
                try:
                    c = copy.deepcopy(col)
                    c.x = swatchX
                    c.y = swatchY
                    c.width = dx
                    c.height = dy
                except:
                    c = None
            else:
                c = None

            if c:
                g.add(c)
                if scallout: scallout(self,g,thisx,y0,i,(col,name),c)

            for s in S: g.add(s)
            if self.colEndCallout and (i%columnMaximum==lim or i==(n-1)):
                if alignment == "left":
                    xt = thisx
                else:
                    xt = thisx+dx+dxTextSpace
                yd = thisy+dy*0.5+dividerOffsY - (max(deltay,leadingMove)+yGap)
                self.colEndCallout(self, g, thisx, xt, yd, jOffs[-1], jOffs[-1]+dx+dxTextSpace)

            if i%columnMaximum==lim:
                if variColumn:
                    thisx += jOffs[-1]+xW
                else:
                    thisx = thisx+deltax
                thisy = upperlefty
            else:
                thisy = thisy-max(deltay,leadingMove)-yGap

        return g
Ejemplo n.º 27
0
def _getLines(s):
    if isSeq(s):
        return tuple([(x or '').split('\n') for x in s])
    else:
        return (s or '').split('\n')
Ejemplo n.º 28
0
def _getLineCount(s):
    T = _getLines(s)
    if isSeq(s):
        return max([len(x) for x in T])
    else:
        return len(T)
Ejemplo n.º 29
0
    def draw(self):
        colorNamePairs = self.colorNamePairs
        autoCP = isAuto(colorNamePairs)
        if autoCP:
            chart = getattr(colorNamePairs,'chart',getattr(colorNamePairs,'obj',None))
            swatchMarker = None
            autoCP = Auto(obj=chart)
            n = chart._seriesCount
            chartTexts = self._getTexts(colorNamePairs)
        else:
            swatchMarker = getattr(self,'swatchMarker',None)
            if isAuto(swatchMarker):
                chart = getattr(swatchMarker,'chart',getattr(swatchMarker,'obj',None))
                swatchMarker = Auto(obj=chart)
            n = len(colorNamePairs)
        dx = self.dx
        dy = self.dy
        alignment = self.alignment
        columnMaximum = self.columnMaximum
        deltax = self.deltax
        deltay = self.deltay
        dxTextSpace = self.dxTextSpace
        fontName = self.fontName
        fontSize = self.fontSize
        fillColor = self.fillColor
        strokeWidth = self.strokeWidth
        strokeColor = self.strokeColor
        subCols = self.subCols
        leading = fontSize*1.2
        yGap = self.yGap
        if not deltay:
            deltay = max(dy,leading)+self.autoYPadding
        ba = self.boxAnchor
        maxWidth = self._calculateMaxBoundaries(colorNamePairs)
        nCols = int((n+columnMaximum-1)/(columnMaximum*1.0))
        xW = dx+dxTextSpace+self.autoXPadding
        variColumn = self.variColumn
        if variColumn:
            width = sum([m[-1] for m in maxWidth])+xW*nCols
        else:
            deltax = max(maxWidth[-1]+xW,deltax)
            width = nCols*deltax
            maxWidth = nCols*[maxWidth]

        thisx = self.x
        thisy = self.y - self.dy
        if ba not in ('ne','n','nw','autoy'):
            height = self._calcHeight()
            if ba in ('e','c','w'):
                thisy += height/2.
            else:
                thisy += height
        if ba not in ('nw','w','sw','autox'):
            if ba in ('n','c','s'):
                thisx -= width/2
            else:
                thisx -= width
        upperlefty = thisy

        g = Group()

        ascent=getFont(fontName).face.ascent/1000.
        if ascent==0: ascent=0.718 # default (from helvetica)
        ascent *= fontSize # normalize

        lim = columnMaximum - 1
        callout = getattr(self,'callout',None)
        scallout = getattr(self,'swatchCallout',None)
        dividerLines = self.dividerLines
        if dividerLines:
            dividerWidth = self.dividerWidth
            dividerColor = self.dividerColor
            dividerDashArray = self.dividerDashArray
            dividerOffsX = self.dividerOffsX
            dividerOffsY = self.dividerOffsY

        for i in xrange(n):
            if autoCP:
                col = autoCP
                col.index = i
                name = chartTexts[i]
            else:
                col, name = colorNamePairs[i]
                if isAuto(swatchMarker):
                    col = swatchMarker
                    col.index = i
                if isAuto(name):
                    name = getattr(swatchMarker,'chart',getattr(swatchMarker,'obj',None)).getSeriesName(i,'series %d' % i)
            T = _getLines(name)
            S = []
            aS = S.append
            j = int(i/(columnMaximum*1.0))
            jOffs = maxWidth[j]

            # thisy+dy/2 = y+leading/2
            y = y0 = thisy+(dy-ascent)*0.5

            if callout: callout(self,g,thisx,y,(col,name))
            if alignment == "left":
                x = thisx
                xn = thisx+jOffs[-1]+dxTextSpace
            elif alignment == "right":
                x = thisx+dx+dxTextSpace
                xn = thisx
            else:
                raise ValueError("bad alignment")
            if not isSeq(name):
                T = [T]
            yd = y
            for k,lines in enumerate(T):
                y = y0
                kk = k*2
                x1 = x+jOffs[kk]
                x2 = x+jOffs[kk+1]
                sc = subCols[k,i]
                anchor = sc.align
                scdx = sc.dx
                scdy = sc.dy
                fN = getattr(sc,'fontName',fontName)
                fS = getattr(sc,'fontSize',fontSize)
                fC = getattr(sc,'fillColor',fillColor)
                fL = getattr(sc,'leading',1.2*fontSize)
                if fN==fontName:
                    fA = (ascent*fS)/fontSize
                else:
                    fA = getFont(fontName).face.ascent/1000.
                    if fA==0: fA=0.718
                    fA *= fS
                if anchor=='left':
                    anchor = 'start'
                    xoffs = x1
                elif anchor=='right':
                    anchor = 'end'
                    xoffs = x2
                elif anchor=='numeric':
                    xoffs = x2
                else:
                    anchor = 'middle'
                    xoffs = 0.5*(x1+x2)
                for t in lines:
                    aS(String(xoffs+scdx,y+scdy,t,fontName=fN,fontSize=fS,fillColor=fC, textAnchor = anchor))
                    y -= fL
                yd = min(yd,y)
                y += fL
                for iy, a in ((y-max(fL-fA,0),'underlines'),(y+fA,'overlines')):
                    il = getattr(sc,a,None)
                    if il:
                        if not isinstance(il,(tuple,list)): il = (il,)
                        for l in il:
                            l = copy.copy(l)
                            l.y1 += iy
                            l.y2 += iy
                            l.x1 += x1
                            l.x2 += x2
                            aS(l)
            x = xn
            y = yd
            leadingMove = 2*y0-y-thisy

            if dividerLines:
                xd = thisx+dx+dxTextSpace+jOffs[-1]+dividerOffsX[1]
                yd = thisy+dy*0.5+dividerOffsY
                if ((dividerLines&1) and i%columnMaximum) or ((dividerLines&2) and not i%columnMaximum):
                    g.add(Line(thisx+dividerOffsX[0],yd,xd,yd,
                        strokeColor=dividerColor, strokeWidth=dividerWidth, strokeDashArray=dividerDashArray))

                if (dividerLines&4) and (i%columnMaximum==lim or i==(n-1)):
                    yd -= max(deltay,leadingMove)+yGap
                    g.add(Line(thisx+dividerOffsX[0],yd,xd,yd,
                        strokeColor=dividerColor, strokeWidth=dividerWidth, strokeDashArray=dividerDashArray))

            # Make a 'normal' color swatch...
            swatchX = x + getattr(self,'swdx',0)
            swatchY = thisy + getattr(self,'swdy',0)

            if isAuto(col):
                chart = getattr(col,'chart',getattr(col,'obj',None))
                c = chart.makeSwatchSample(getattr(col,'index',i),swatchX,swatchY,dx,dy)
            elif isinstance(col, colors.Color):
                if isSymbol(swatchMarker):
                    c = uSymbol2Symbol(swatchMarker,swatchX+dx/2.,swatchY+dy/2.,col)
                else:
                    c = self._defaultSwatch(swatchX,swatchY,dx,dy,fillColor=col,strokeWidth=strokeWidth,strokeColor=strokeColor)
            elif col is not None:
                try:
                    c = copy.deepcopy(col)
                    c.x = swatchX
                    c.y = swatchY
                    c.width = dx
                    c.height = dy
                except:
                    c = None
            else:
                c = None

            if c:
                g.add(c)
                if scallout: scallout(self,g,thisx,y0,i,(col,name),c)

            for s in S: g.add(s)
            if self.colEndCallout and (i%columnMaximum==lim or i==(n-1)):
                if alignment == "left":
                    xt = thisx
                else:
                    xt = thisx+dx+dxTextSpace
                yd = thisy+dy*0.5+dividerOffsY - (max(deltay,leadingMove)+yGap)
                self.colEndCallout(self, g, thisx, xt, yd, jOffs[-1], jOffs[-1]+dx+dxTextSpace)

            if i%columnMaximum==lim:
                if variColumn:
                    thisx += jOffs[-1]+xW
                else:
                    thisx = thisx+deltax
                thisy = upperlefty
            else:
                thisy = thisy-max(deltay,leadingMove)-yGap

        return g
Ejemplo n.º 30
0
def _getStr(s):
    if isSeq(s):
        return list(map(_getStr,s))
    else:
        return _objStr(s)
Ejemplo n.º 31
0
 def __init__(self,tests,name=None):
     if not isSeq(tests): tests = (tests,)
     self._tests = tests
     if name: self._str = name
Ejemplo n.º 32
0
def _getStr(s):
    if isSeq(s):
        return list(map(_getStr,s))
    else:
        return _objStr(s)
Ejemplo n.º 33
0
def _evalMeasurement(n):
    if isinstance(n,str):
        from reportlab.platypus.paraparser import _num
        n = _num(n)
        if isSeq(n): n = n[1]
    return n
Ejemplo n.º 34
0
    def breakLines(self, width):
        """
        Returns a broken line structure. There are two cases

        A) For the simple case of a single formatting input fragment the output is
            A fragment specifier with
                - kind = 0
                - fontName, fontSize, leading, textColor
                - lines=  A list of lines
                
                    Each line has two items:
                    
                    1. unused width in points
                    2. a list of words

        B) When there is more than one input formatting fragment the out put is
            A fragment specifier with
                - kind = 1
                - lines =  A list of fragments each having fields:
                
                    - extraspace (needed for justified)
                    - fontSize
                    - words=word list
                    - each word is itself a fragment with
                    - various settings

        This structure can be used to easily draw paragraphs with the various alignments.
        You can supply either a single width or a list of widths; the latter will have its
        last item repeated until necessary. A 2-element list is useful when there is a
        different first line indent; a longer list could be created to facilitate custom wraps
        around irregular objects."""

        if not isSeq(width): maxWidths = [width]
        else: maxWidths = width
        lines = []
        lineno = 0
        maxWidth = maxWidths[lineno]
        style = self.style
        fFontSize = float(style.fontSize)
        requiredWidth = 0

        #for bullets, work out width and ensure we wrap the right amount onto line one
        _handleBulletWidth(self.bulletText,style,maxWidths)

        self.height = 0
        autoLeading = getattr(self,'autoLeading',getattr(style,'autoLeading',''))
        calcBounds = autoLeading not in ('','off')
        frags = self.frags
        nFrags= len(frags)
        if nFrags==1:
            f = frags[0]
            if hasattr(f,'text'):
                fontSize = f.fontSize
                fontName = f.fontName
                ascent, descent = getAscentDescent(fontName,fontSize)
                kind = 0
                L=f.text.split('\n')
                for l in L:
                    currentWidth = stringWidth(l,fontName,fontSize)
                    requiredWidth = max(currentWidth,requiredWidth)
                    extraSpace = maxWidth-currentWidth
                    lines.append((extraSpace,l.split(' '),currentWidth))
                    lineno = lineno+1
                    maxWidth = lineno<len(maxWidths) and maxWidths[lineno] or maxWidths[-1]
                blPara = f.clone(kind=kind, lines=lines,ascent=ascent,descent=descent,fontSize=fontSize)
            else:
                kind = f.kind
                lines = f.lines
                for L in lines:
                    if kind==0:
                        currentWidth = L[2]
                    else:
                        currentWidth = L.currentWidth
                    requiredWidth = max(currentWidth,requiredWidth)
                blPara = f.clone(kind=kind, lines=lines)

            self.width = max(self.width,requiredWidth)
            return blPara
        elif nFrags<=0:
            return ParaLines(kind=0, fontSize=style.fontSize, fontName=style.fontName,
                            textColor=style.textColor, ascent=style.fontSize,descent=-0.2*style.fontSize,
                            lines=[])
        else:
            for L in _getFragLines(frags):
                currentWidth, n, w = _getFragWord(L,maxWidth)
                f = w[0][0]
                maxSize = f.fontSize
                maxAscent, minDescent = getAscentDescent(f.fontName,maxSize)
                words = [f.clone()]
                words[-1].text = w[0][1]
                for i in w[1:]:
                    f = i[0].clone()
                    f.text=i[1]
                    words.append(f)
                    fontSize = f.fontSize
                    fontName = f.fontName
                    if calcBounds:
                        cbDefn = getattr(f,'cbDefn',None)
                        if getattr(cbDefn,'width',0):
                            descent,ascent = imgVRange(imgNormV(cbDefn.height,fontSize),cbDefn.valign,fontSize)
                        else:
                            ascent, descent = getAscentDescent(fontName,fontSize)
                    else:
                        ascent, descent = getAscentDescent(fontName,fontSize)
                    maxSize = max(maxSize,fontSize)
                    maxAscent = max(maxAscent,ascent)
                    minDescent = min(minDescent,descent)

                lineno += 1
                maxWidth = lineno<len(maxWidths) and maxWidths[lineno] or maxWidths[-1]
                requiredWidth = max(currentWidth,requiredWidth)
                extraSpace = maxWidth - currentWidth
                lines.append(ParaLines(extraSpace=extraSpace,wordCount=n, words=words, fontSize=maxSize, ascent=maxAscent,descent=minDescent,currentWidth=currentWidth))

            self.width = max(self.width,requiredWidth)
            return ParaLines(kind=1, lines=lines)

        return lines
Ejemplo n.º 35
0
def _getLines(s):
    if isSeq(s):
        return tuple([(x or '').split('\n') for x in s])
    else:
        return (s or '').split('\n')
Ejemplo n.º 36
0
    def _setupGrammar(self):

        self.DEFAULT_BLOCK_TAG = 'p'    #used to close blocks if nothing else given
        def uniDict(d):
            r = {}
            for k in d:
                r[asUnicode(k)] = d[k]
            return r

        def byName(listOfDicts):
            out = {}
            for d in listOfDicts:
                d = uniDict(d)
                out[d['name']] = d
            return out

        #situations in which a tag can appear.
        self._contextDict = byName([
            dict(name='block', allowedIn=None),  #None=top-level
            dict(name='inline', allowedIn='block'),
            dict(name='table', allowedIn='block'),
            dict(name='list', allowedIn='block'),
            dict(name='li', allowedIn='list'),
            dict(name='tr', allowedIn='table'),
            dict(name='td', allowedIn='tr'),    #no contents for now
            ])
#        if not self.allowTables:
#            del self._contextDict['table']

        for context in self._contextDict.values():
            context['canContain'] = set()

        allowParaAttrs = []
        if self.allowStyleAttr: allowParaAttrs.append('style')
        if self.allowAlignAttr: allowParaAttrs.append('align')

        self._tagDict = byName([
            dict(name='p',context='block', attrs=allowParaAttrs),
            dict(name='h1',context='block', attrs=allowParaAttrs),
            dict(name='h2',context='block', attrs=allowParaAttrs),
            dict(name='h3',context='block', attrs=allowParaAttrs),
            dict(name='h4',context='block', attrs=allowParaAttrs),
            dict(name='h5',context='block', attrs=allowParaAttrs),
            dict(name='h6',context='block', attrs=allowParaAttrs),

            dict(name='strong',context=('inline', 'li', 'td'), attrs=[]),
            dict(name='em',context=('inline', 'li', 'td'), attrs=[]),
            dict(name='i',context=('inline', 'li', 'td'), attrs=[]),
            dict(name='b',context=('inline', 'li', 'td'), attrs=[]),
            dict(name='',context=('inline', 'li', 'td'), attrs=[]),
            dict(name='sup',context=('inline', 'li', 'td'), attrs=[]),
            dict(name='sub',context=('inline', 'li', 'td'), attrs=[]),
            dict(name='br',context=('inline', 'li', 'td'), attrs=[], selfClosing=True),
            dict(name='a',context=('inline', 'li', 'td'), attrs=['href']),

            # force_attrs. These attributes will be added to make sure xhtml validation passes.
            dict(name='img',context=('inline', 'li'), attrs=['src','width','height','alt'], force_attrs=['alt'], selfClosing=True),

            dict(name='table',context='block', attrs=[]),
            dict(name='tr',context='table', attrs=[]),
            dict(name='td',context='tr', attrs=[]),
            dict(name='th',context='tr', attrs=[]),

            dict(name='ul',context='block', attrs=[]),
            dict(name='ol',context='block', attrs=[]),
            dict(name='li',context='list', attrs=[]),
            ])

        # Tags to use to cover naked text up with in the given context
        self._dataCover = uniDict(dict(
            block=(self.DEFAULT_BLOCK_TAG,),
            table=('tr', 'td'),
            tr=('td',),
            list=('li',),
            ))

#        if not self.allowTables:
#            del self._tagDict['table']
#            del self._tagDict['tr']
#            del self._tagDict['td']

        if not self.allowImages:
            del self._tagDict['img']
        if not self.allowAtags:
            del self._tagDict['a']

        #work out in-place the set of tags allowed in each context.

        for tagName,tag in self._tagDict.items():
            if 'selfClosing' not in tag:
                tag['selfClosing'] = False

            contexts = tag['context']
            if not isSeq(contexts):
                contexts = contexts,
            for ctxName in contexts:
                context = self._contextDict.get(ctxName)
                context['canContain'].add(tagName)

        #work out certain useful attributes
        self.valid_tags = set(self._tagDict.keys())
        self.valid_block_tags = self.tagsAllowedInContext('block')
        self.valid_inline_tags = self.tagsAllowedInContext('inline')
        self.valid_other_tags = self.valid_tags - self.valid_block_tags - self.valid_inline_tags
Ejemplo n.º 37
0
    def breakLines(self, width):
        """
        Returns a broken line structure. There are two cases

        A) For the simple case of a single formatting input fragment the output is
            A fragment specifier with
                - kind = 0
                - fontName, fontSize, leading, textColor
                - lines=  A list of lines
                
                    Each line has two items:
                    
                    1. unused width in points
                    2. a list of words

        B) When there is more than one input formatting fragment the out put is
            A fragment specifier with
                - kind = 1
                - lines =  A list of fragments each having fields:
                
                    - extraspace (needed for justified)
                    - fontSize
                    - words=word list
                    - each word is itself a fragment with
                    - various settings

        This structure can be used to easily draw paragraphs with the various alignments.
        You can supply either a single width or a list of widths; the latter will have its
        last item repeated until necessary. A 2-element list is useful when there is a
        different first line indent; a longer list could be created to facilitate custom wraps
        around irregular objects."""

        self._width_max = 0
        if not isSeq(width): maxWidths = [width]
        else: maxWidths = width
        lines = []
        lineno = 0
        maxWidth = maxWidths[lineno]
        style = self.style
        fFontSize = float(style.fontSize)
        requiredWidth = 0

        #for bullets, work out width and ensure we wrap the right amount onto line one
        _handleBulletWidth(self.bulletText, style, maxWidths)

        self.height = 0
        autoLeading = getattr(self, 'autoLeading',
                              getattr(style, 'autoLeading', ''))
        calcBounds = autoLeading not in ('', 'off')
        frags = self.frags
        nFrags = len(frags)
        if nFrags == 1:
            f = frags[0]
            if hasattr(f, 'text'):
                fontSize = f.fontSize
                fontName = f.fontName
                ascent, descent = getAscentDescent(fontName, fontSize)
                kind = 0
                L = f.text.split('\n')
                for l in L:
                    currentWidth = stringWidth(l, fontName, fontSize)
                    if currentWidth > self._width_max:
                        self._width_max = currentWidth
                    requiredWidth = max(currentWidth, requiredWidth)
                    extraSpace = maxWidth - currentWidth
                    lines.append((extraSpace, l.split(' '), currentWidth))
                    lineno = lineno + 1
                    maxWidth = lineno < len(
                        maxWidths) and maxWidths[lineno] or maxWidths[-1]
                blPara = f.clone(kind=kind,
                                 lines=lines,
                                 ascent=ascent,
                                 descent=descent,
                                 fontSize=fontSize)
            else:
                kind = f.kind
                lines = f.lines
                for L in lines:
                    if kind == 0:
                        currentWidth = L[2]
                    else:
                        currentWidth = L.currentWidth
                    requiredWidth = max(currentWidth, requiredWidth)
                blPara = f.clone(kind=kind, lines=lines)

            self.width = max(self.width, requiredWidth)
            return blPara
        elif nFrags <= 0:
            return ParaLines(kind=0,
                             fontSize=style.fontSize,
                             fontName=style.fontName,
                             textColor=style.textColor,
                             ascent=style.fontSize,
                             descent=-0.2 * style.fontSize,
                             lines=[])
        else:
            for L in _getFragLines(frags):
                currentWidth, n, w = _getFragWord(L, maxWidth)
                f = w[0][0]
                maxSize = f.fontSize
                maxAscent, minDescent = getAscentDescent(f.fontName, maxSize)
                words = [f.clone()]
                words[-1].text = w[0][1]
                for i in w[1:]:
                    f = i[0].clone()
                    f.text = i[1]
                    words.append(f)
                    fontSize = f.fontSize
                    fontName = f.fontName
                    if calcBounds:
                        cbDefn = getattr(f, 'cbDefn', None)
                        if getattr(cbDefn, 'width', 0):
                            descent, ascent = imgVRange(
                                imgNormV(cbDefn.height, fontSize),
                                cbDefn.valign, fontSize)
                        else:
                            ascent, descent = getAscentDescent(
                                fontName, fontSize)
                    else:
                        ascent, descent = getAscentDescent(fontName, fontSize)
                    maxSize = max(maxSize, fontSize)
                    maxAscent = max(maxAscent, ascent)
                    minDescent = min(minDescent, descent)

                lineno += 1
                maxWidth = lineno < len(
                    maxWidths) and maxWidths[lineno] or maxWidths[-1]
                requiredWidth = max(currentWidth, requiredWidth)
                extraSpace = maxWidth - currentWidth
                if currentWidth > self._width_max:
                    self._width_max = currentWidth
                lines.append(
                    ParaLines(extraSpace=extraSpace,
                              wordCount=n,
                              words=words,
                              fontSize=maxSize,
                              ascent=maxAscent,
                              descent=minDescent,
                              currentWidth=currentWidth,
                              preformatted=True))

            self.width = max(self.width, requiredWidth)
            return ParaLines(kind=1, lines=lines)

        return lines
Ejemplo n.º 38
0
 def __init__(self, tests, name=None):
     if not isSeq(tests): tests = (tests, )
     self._tests = tests
     if name: self._str = name
Ejemplo n.º 39
0
def _getLineCount(s):
    T = _getLines(s)
    if isSeq(s):
        return max([len(x) for x in T])
    else:
        return len(T)