[reportlab-users] TileFrame

Spruce Weber timberdig at gmail.com
Fri Dec 9 17:02:33 EST 2005


To accommodate label printing, I subclassed Frame to allow for tiling
of flowables. I'm just starting to get familiar with Reportlab. Feel
free to package this with Reportlab or to use it or modify it however
you will...

class TileFrame(Frame):
    """
    Extends Frame to allow tiling (across-then-down or
down-then-across) of flowables.

    Assumes all flowables have equal dimensions. Ignores
flowable.getSpaceBefore()
    and flowable.getSpaceAfter(). Maybe flowables should have a
concept of right,
    left, above and below instead of before and after?
    """
    def __init__(self, x1, y1, width,height, leftPadding=6, bottomPadding=6,
            rightPadding=6, topPadding=6, id=None, showBoundary=0,
            overlapAttachedSpace=None, direction=None):
        Frame.__init__(self, x1, y1, width,height, leftPadding, bottomPadding,
            rightPadding, topPadding, id, showBoundary, overlapAttachedSpace)

        self._direction = direction

    def _getSpaceToRight(self):
        return self._x2 - self._rightPadding - self._x

    def _getSpaceBelow(self):
        return self._y - self._y1 - self._bottomPadding

    def _nextPosition(self, w, h, wrap=False):
        if wrap:
            if self._direction == "ACROSS":
                self._x = self._x1 + self._leftPadding
                self._y -= h
            else:
                self._x += w
                self._y = self._y2 - self._topPadding
        else:
            if self._direction == "ACROSS":
                self._x += w
            else: #elif self._direction == "DOWN":
                self._y -= h
        return (self._x, self._y)

    def add(self, flowable, canv, trySplit=0):
        y = self._y
        x = self._x
        p = self._y1p
        aW = self._getAvailableWidth()
        spaceBelow = self._getSpaceBelow()
        spaceRight = self._getSpaceToRight()
        retry = False

        if self._direction and spaceBelow>0-_FUZZ and
spaceRight>0-_FUZZ: #space exists
            w, h = flowable.wrap(spaceRight, spaceBelow)
            if w>spaceRight or h>spaceBelow: #space is too small, try
again after wrapping
                x, y = self._nextPosition(w,h,True)
                retry = True
        else:
            retry = True
        if retry:
            spaceBelow = self._getSpaceBelow()
            spaceRight = self._getSpaceToRight()
            if spaceBelow>0-_FUZZ and spaceRight>0-_FUZZ: #space exists
                w, h = flowable.wrap(spaceRight, spaceBelow)
                if w>spaceRight or h>spaceBelow: #space is too small,
even after wrapping: next page/frame
                    return 0
            else:
                return 0
        flowable.drawOn(canv, x + self._leftExtraIndent, y-h, _sW=aW-w)
        self._nextPosition(w,h)
        return 1


More information about the reportlab-users mailing list