Script 'mail_helper' called by obssrc
Hello community,
here is the log from the commit of package python-reportlab for
openSUSE:Factory checked in at 2021-01-15 19:44:31
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/python-reportlab (Old)
and /work/SRC/openSUSE:Factory/.python-reportlab.new.28504 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "python-reportlab"
Fri Jan 15 19:44:31 2021 rev:29 rq:862304 version:3.5.59
Changes:
--------
--- /work/SRC/openSUSE:Factory/python-reportlab/python-reportlab.changes
2020-12-12 20:32:07.253836799 +0100
+++
/work/SRC/openSUSE:Factory/.python-reportlab.new.28504/python-reportlab.changes
2021-01-15 19:44:47.405893354 +0100
@@ -1,0 +2,17 @@
+Mon Jan 11 12:31:13 UTC 2021 - Antonio Larrosa <[email protected]>
+
+- Update to 3.5.59
+ * Allow variant corners in Canvas.roundRect
+ * Allow tables to have rounded corners
+- Update to 3.5.58
+ * added ddfStyle to Label
+ * allowed for embedded(and ordinary)Hyphenation to pre-empt splitting when
embeddedHyphenation>=2
+ * fix extension escapePDF so it can handle unicode
+ * fix poundsign in Ean5BarcodeWidget
+ * Table can use __styledWrap__ for sizing
+ * test fixes so 3.9 and 2.7 produce same pdf
+- Update to 3.5.57
+ * added .github action wheel.yml
+ * micro change to userguide doc
+
+-------------------------------------------------------------------
Old:
----
reportlab-3.5.56.tar.gz
New:
----
reportlab-3.5.59.tar.gz
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Other differences:
------------------
++++++ python-reportlab.spec ++++++
--- /var/tmp/diff_new_pack.vq6OvA/_old 2021-01-15 19:44:48.217894562 +0100
+++ /var/tmp/diff_new_pack.vq6OvA/_new 2021-01-15 19:44:48.221894568 +0100
@@ -1,7 +1,7 @@
#
# spec file for package python-reportlab
#
-# Copyright (c) 2020 SUSE LLC
+# Copyright (c) 2021 SUSE LLC
#
# All modifications and additions to the file contributed by third parties
# remain the property of their copyright owners, unless otherwise agreed
@@ -19,7 +19,7 @@
%{?!python_module:%define python_module() python-%{**} python3-%{**}}
%define oldpython python
Name: python-reportlab
-Version: 3.5.56
+Version: 3.5.59
Release: 0
Summary: The Reportlab Toolkit
License: BSD-3-Clause
++++++ reportlab-3.5.56.tar.gz -> reportlab-3.5.59.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/CHANGES.md
new/reportlab-3.5.59/CHANGES.md
--- old/reportlab-3.5.56/CHANGES.md 2020-12-01 17:29:04.000000000 +0100
+++ new/reportlab-3.5.59/CHANGES.md 2021-01-01 19:09:10.000000000 +0100
@@ -11,6 +11,25 @@
The contributors lists are in no order and apologies to those accidentally not
mentioned. If we missed you, please let us know!
+CHANGES 3.5.58 01/01/2021
+---------------------------
+ * Allow variant corners in Canvas.roundRect
+ * Allow tables to have rounded corners
+
+CHANGES 3.5.57 27/12/2020
+---------------------------
+ * added ddfStyle to Label
+ * allowed for embedded(and ordinary)Hyphenation to pre-empt splitting
when embeddedHyphenation>=2
+ * fix extension escapePDF so it can handle unicode
+ * fix poundsign in Ean5BarcodeWidget
+ * Table can use __styledWrap__ for sizing
+ * test fixes so 3.9 and 2.7 produce same pdf
+
+CHANGES 3.5.56 10/12/2020
+---------------------------
+ * added .github action wheel.yml
+ * micro change to userguide doc
+
RELEASE 3.5.56 01/12/2020
---------------------------
* micro changes for Big Sur in C extensions
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/PKG-INFO
new/reportlab-3.5.59/PKG-INFO
--- old/reportlab-3.5.56/PKG-INFO 2020-12-01 17:29:31.000000000 +0100
+++ new/reportlab-3.5.59/PKG-INFO 2021-01-04 15:52:21.000000000 +0100
@@ -1,6 +1,6 @@
Metadata-Version: 1.1
Name: reportlab
-Version: 3.5.56
+Version: 3.5.59
Summary: The Reportlab Toolkit
Home-page: http://www.reportlab.com/
Author: Andy Robinson, Robin Becker, the ReportLab team and the community
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/docs/userguide/ch5_paragraphs.py
new/reportlab-3.5.59/docs/userguide/ch5_paragraphs.py
--- old/reportlab-3.5.56/docs/userguide/ch5_paragraphs.py 2020-12-01
17:29:04.000000000 +0100
+++ new/reportlab-3.5.59/docs/userguide/ch5_paragraphs.py 2020-12-27
12:44:36.000000000 +0100
@@ -345,7 +345,7 @@
This <img/> <img src="../images/testimg.gif" width="10"/> has width
<b>10</b>.<br/><br/>
</para>""","Inline images")
disc("""The $src$ attribute can refer to a remote location eg
$src="https://www.reportlab.com/images/logo.gif"$. By default we set
$rl_config.trustedShemes$ to $['https','http', 'file', 'data', 'ftp']$ and
-$rl_config.trustedHosts=None$ the latter meaning no-restriction. You can
modify these variables using one of the override files eg
$reportlab_settings.py$ or $~/.reportlab_settings$. Or as comma seprated
strings in the
+$rl_config.trustedHosts=None$ the latter meaning no-restriction. You can
modify these variables using one of the override files eg
$reportlab_settings.py$ or $~/.reportlab_settings$. Or as comma separated
strings in the
environment variables $RL_trustedSchemes$ & $RL_trustedHosts$. Note that
the $trustedHosts$ values may contain <b>glob</b> wild cars so
<i>*.reportlab.com</i> will match the obvious domains.
<br/><span color="red"><b>*NB*</b></span> use of <i>trustedHosts</i> and or
<i>trustedSchemes</i> may not control behaviour & actions when $URI$
patterns
are detected by the viewer application.""")
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/docs/userguide/ch6_tables.py
new/reportlab-3.5.59/docs/userguide/ch6_tables.py
--- old/reportlab-3.5.56/docs/userguide/ch6_tables.py 2019-10-01
17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/docs/userguide/ch6_tables.py 2021-01-04
15:51:54.000000000 +0100
@@ -57,7 +57,7 @@
disc("""These are the main methods which are of interest to the client
programmer.""")
heading4("""$Table(data, colWidths=None, rowHeights=None, style=None,
splitByRow=1,
-repeatRows=0, repeatCols=0, rowSplitRange=None, spaceBefore=None,
spaceAfter=None)$""")
+repeatRows=0, repeatCols=0, rowSplitRange=None, spaceBefore=None,
spaceAfter=None, cornerRadii=None)$""")
disc("""The $data$ argument is a sequence of sequences of cell values each of
which
should be convertible to a string value using the $str$ function or should be
a Flowable instance (such as a $Paragraph$) or a list (or tuple) of such
instances.
@@ -91,8 +91,11 @@
that should be repeated when the $Table$ is asked to split itself. If it is a
tuple it should specify which of the leading rows should be repeated; this
allows
for cases where the first appearance of the table hsa more leading rows than
later split parts.
The $repeatCols$ argument is currently ignored as a $Table$ cannot be split by
column.""")
-disc("""The $spaceBefore$ & $spaceAfter$ arguments may be used to put
extra space before or after the table when renedered in a $platypus$ story.""")
disc("""The $rowSplitRange$ argument may be used to control the splitting of
the table to a subset of its rows; that can be to prevent splitting too close
to the beginning or end of the table.""")
+disc("""The $spaceBefore$ & $spaceAfter$ arguments may be used to put
extra space before or after the table when renedered in a $platypus$ story.""")
+disc("""The $style$ argument can be an initial style for the table.""")
+disc("""The $cornerRadii$ argument can be a list of the top left, top right,
bottom left and bottom right radii.
+A positive non-zero radius indicates that the corner should be rounded. This
argument will override any $ROUNDEDCORNERS$ command in the argument $style$
list (ie it has pririty).""")
heading4('$Table.setStyle(tblStyle)$')
disc("""
This method applies a particular instance of class $TableStyle$ (discussed
below)
@@ -340,6 +343,17 @@
""")
disc("""demands that the cells in columns $sc$ - $ec$ and rows $sr$ - $er$ may
not be split.""")
+eg("")
+eg("")
+disc("""To control $Table$ corner rounding the $ROUNDEDCORNERS$ command may be
used
+The style specification
+""")
+eg("""
+ROUNDEDCORNERS, [tl, tr, bl, br]
+""")
+disc("""specifies the radii of the top left, top right, bottom left and bottom
right. A value of $0$ indicates a square corner. replace the whole array by
$None$ to turn off all rounding.
+<br/>Borders at a rounded corner are curved by an octant.""")
+
heading3("""Special $TableStyle$ Indeces""")
disc("""In any style command the first row index may be set to one of the
special strings
$'splitlast'$ or $'splitfirst'$ to indicate that the style should be used only
for the last row of
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/src/reportlab/__init__.py
new/reportlab-3.5.59/src/reportlab/__init__.py
--- old/reportlab-3.5.56/src/reportlab/__init__.py 2020-12-01
17:29:04.000000000 +0100
+++ new/reportlab-3.5.59/src/reportlab/__init__.py 2021-01-04
15:51:54.000000000 +0100
@@ -1,9 +1,9 @@
#Copyright ReportLab Europe Ltd. 2000-2018
#see license.txt for license details
__doc__="""The Reportlab PDF generation library."""
-Version = "3.5.56"
+Version = "3.5.59"
__version__=Version
-__date__='20201201'
+__date__='20210104'
import sys, os
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/reportlab-3.5.56/src/reportlab/graphics/barcode/eanbc.py
new/reportlab-3.5.59/src/reportlab/graphics/barcode/eanbc.py
--- old/reportlab-3.5.56/src/reportlab/graphics/barcode/eanbc.py
2019-10-01 17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/src/reportlab/graphics/barcode/eanbc.py
2020-12-27 12:44:36.000000000 +0100
@@ -461,7 +461,7 @@
if s[0] in '3456':
price = '$'
elif s[0] in '01':
- price = '\xc2\xa3'
+ price = asNative(b'\xc2\xa3')
if price is None:
return
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/reportlab-3.5.56/src/reportlab/graphics/charts/textlabels.py
new/reportlab-3.5.59/src/reportlab/graphics/charts/textlabels.py
--- old/reportlab-3.5.56/src/reportlab/graphics/charts/textlabels.py
2020-01-22 15:40:54.000000000 +0100
+++ new/reportlab-3.5.59/src/reportlab/graphics/charts/textlabels.py
2020-12-27 12:44:36.000000000 +0100
@@ -16,7 +16,7 @@
from reportlab.graphics.widgetbase import Widget, PropHolder
from reportlab.graphics.shapes import _baseGFontName, DirectDraw
from reportlab.platypus import XPreformatted, Paragraph, Flowable
-from reportlab.lib.styles import ParagraphStyle
+from reportlab.lib.styles import ParagraphStyle, PropertySet
from reportlab.lib.enums import TA_LEFT, TA_RIGHT, TA_CENTER
_ta2al = dict(start=TA_LEFT,end=TA_RIGHT,middle=TA_CENTER)
@@ -153,6 +153,7 @@
customDrawChanger = AttrMapValue(isNoneOrCallable,desc="An instance of
CustomDrawChanger to modify the behavior at draw time", _advancedUsage=1),
ddf =
AttrMapValue(NoneOr(isSubclassOf(DirectDraw),'NoneOrDirectDraw'),desc="A
DirectDrawFlowable instance", _advancedUsage=1),
ddfKlass =
AttrMapValue(NoneOr(isSubclassOf(Flowable),'NoneOrDirectDraw'),desc="A
DirectDrawFlowable instance", _advancedUsage=1),
+ ddfStyle = AttrMapValue(NoneOr(isSubclassOf(PropertySet)),desc="A
style for a ddfKlass or None", _advancedUsage=1),
)
def __init__(self,**kw):
@@ -187,6 +188,7 @@
useAscentDescent = False,
ddf = DirectDrawFlowable,
ddfKlass = None,
+ ddfStyle = None,
)
def setText(self, text):
@@ -288,12 +290,14 @@
else:
if self.ddf is None:
raise RuntimeError('DirectDrawFlowable class is not available
you need the rlextra package as well as reportlab')
- sty = self._style = ParagraphStyle('xlabel-generated',
+ sty = dict(
+ name='xlabel-generated',
fontName=self.fontName,
fontSize=self.fontSize,
fillColor=self.fillColor,
strokeColor=self.strokeColor,
)
+ sty = self._style = (ddfStyle.clone if self.ddfStyle else
ParagraphStyle)(**sty)
self._getBaseLineRatio()
if self.useAscentDescent:
sty.autoLeading = True
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/src/reportlab/lib/utils.py
new/reportlab-3.5.59/src/reportlab/lib/utils.py
--- old/reportlab-3.5.56/src/reportlab/lib/utils.py 2020-10-29
13:35:05.000000000 +0100
+++ new/reportlab-3.5.59/src/reportlab/lib/utils.py 2021-01-04
15:51:54.000000000 +0100
@@ -16,6 +16,16 @@
from reportlab.lib.rltempfile import get_rl_tempfile, get_rl_tempdir,
_rl_getuid
from . rl_safe_eval import rl_safe_exec, rl_safe_eval, safer_globals
+class __UNSET__(object):
+ @staticmethod
+ def __bool__():
+ return False
+ @staticmethod
+ def __str__():
+ return '__UNSET__'
+ __repr__ = __str__
+__UNSET__ = __UNSET__()
+
try:
import cPickle as pickle
except ImportError:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/src/reportlab/pdfgen/canvas.py
new/reportlab-3.5.59/src/reportlab/pdfgen/canvas.py
--- old/reportlab-3.5.56/src/reportlab/pdfgen/canvas.py 2020-10-02
17:51:34.000000000 +0200
+++ new/reportlab-3.5.59/src/reportlab/pdfgen/canvas.py 2020-12-27
12:44:36.000000000 +0100
@@ -23,7 +23,7 @@
from reportlab.pdfgen import pdfgeom, pathobject
from reportlab.pdfgen.textobject import PDFTextObject, _PDFColorSetter
from reportlab.lib.colors import black, _chooseEnforceColorSpace, Color,
CMYKColor, toColor
-from reportlab.lib.utils import import_zlib, ImageReader, isSeq, isStr,
isUnicode, _digester
+from reportlab.lib.utils import import_zlib, ImageReader, isSeq, isStr,
isUnicode, _digester, asUnicode
from reportlab.lib.rl_accel import fp_str, escapePDF
from reportlab.lib.boxstuff import aspectRatioFix
@@ -1595,8 +1595,7 @@
def drawString(self, x, y, text, mode=None, charSpace=0, direction=None,
wordSpace=None):
"""Draws a string in the current text styles."""
- if sys.version_info[0] == 3 and not isinstance(text, str):
- text = text.decode('utf-8')
+ text = asUnicode(text)
#we could inline this for speed if needed
t = self.beginText(x, y, direction=direction)
if mode is not None: t.setTextRenderMode(mode)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/src/reportlab/pdfgen/pathobject.py
new/reportlab-3.5.59/src/reportlab/pdfgen/pathobject.py
--- old/reportlab-3.5.56/src/reportlab/pdfgen/pathobject.py 2019-10-01
17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/src/reportlab/pdfgen/pathobject.py 2021-01-01
19:09:10.000000000 +0100
@@ -25,7 +25,7 @@
Path objects are probably not long, so we pack onto one line
- the code argument allows a canvas to get the operatiosn appended directly
so
+ the code argument allows a canvas to get the operations appended directly
so
avoiding the final getCode
"""
def __init__(self,code=None):
@@ -95,31 +95,43 @@
#use a precomputed set of factors for the bezier approximation
#to a circle. There are six relevant points on the x axis and y axis.
#sketch them and it should all make sense!
- t = 0.4472 * radius
-
- x0 = x
- x1 = x0 + t
- x2 = x0 + radius
- x3 = x0 + width - radius
- x4 = x0 + width - t
- x5 = x0 + width
-
- y0 = y
- y1 = y0 + t
- y2 = y0 + radius
- y3 = y0 + height - radius
- y4 = y0 + height - t
- y5 = y0 + height
-
- self.moveTo(x2, y0)
- self.lineTo(x3, y0) #bottom row
- self.curveTo(x4, y0, x5, y1, x5, y2) #bottom right
- self.lineTo(x5, y3) #right edge
- self.curveTo(x5, y4, x4, y5, x3, y5) #top right
- self.lineTo(x2, y5) #top row
- self.curveTo(x1, y5, x0, y4, x0, y3) #top left
- self.lineTo(x0, y2) #left edge
- self.curveTo(x0, y1, x1, y0, x2, y0) #bottom left
+ m = 0.4472 #radius multiplier
+ xhi = x,x+width
+ xlo, xhi = min(xhi), max(xhi)
+ yhi = y,y+height
+ ylo, yhi = min(yhi), max(yhi)
+ if isinstance(radius,(list,tuple)):
+ r = [max(0,r) for r in radius]
+ if len(r)<4: r += (4-len(r))*[0]
+ self.moveTo(xlo + r[2], ylo) #start at bottom left
+ self.lineTo(xhi - r[3], ylo) #bottom row
+ if r[3]>0:
+ t = m*r[3]
+ self.curveTo(xhi - t, ylo, xhi, ylo + t, xhi, ylo + r[3])
#bottom right
+ self.lineTo(xhi, yhi - r[1]) #right edge
+ if r[1]>0:
+ t = m*r[1]
+ self.curveTo(xhi, yhi - t, xhi - t, yhi, xhi - r[1], yhi) #top
right
+ self.lineTo(xlo + r[0], yhi) #top row
+ if r[0]>0:
+ t = m*r[0]
+ self.curveTo(xlo + t, yhi, xlo, yhi - t, xlo, yhi - r[0]) #top
left
+ self.lineTo(xlo, ylo + r[2]) #left edge
+ if r[2]>0:
+ t = m*r[2]
+ self.curveTo(xlo, ylo + t, xlo + t, ylo, xlo + r[2], ylo)
#bottom left
+ # 4 radii top left top right bittom left bottom right
+ else:
+ t = m * radius
+ self.moveTo(xlo + radius, ylo)
+ self.lineTo(xhi - radius, ylo) #bottom row
+ self.curveTo(xhi - t, ylo, xhi, ylo + t, xhi, ylo + radius)
#bottom right
+ self.lineTo(xhi, yhi - radius) #right edge
+ self.curveTo(xhi, yhi - t, xhi - t, yhi, xhi - radius, yhi) #top
right
+ self.lineTo(xlo + radius, yhi) #top row
+ self.curveTo(xlo + t, yhi, xlo, yhi - t, xlo, yhi - radius) #top
left
+ self.lineTo(xlo, ylo + radius) #left edge
+ self.curveTo(xlo, ylo + t, xlo + t, ylo, xlo + radius, ylo)
#bottom left
self.close()
def close(self):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/src/reportlab/platypus/paragraph.py
new/reportlab-3.5.59/src/reportlab/platypus/paragraph.py
--- old/reportlab-3.5.56/src/reportlab/platypus/paragraph.py 2020-07-20
09:39:52.000000000 +0200
+++ new/reportlab-3.5.59/src/reportlab/platypus/paragraph.py 2020-12-27
12:44:36.000000000 +0100
@@ -2014,6 +2014,7 @@
hyphenator = None
uriWasteReduce = style.uriWasteReduce
embeddedHyphenation = style.embeddedHyphenation
+ hyphenation2 = embeddedHyphenation>1
spaceShrinkage = style.spaceShrinkage
splitLongWords = style.splitLongWords
attemptHyphenation = hyphenator or uriWasteReduce or
embeddedHyphenation
@@ -2078,6 +2079,17 @@
self._hyphenations += 1
forcedSplit = 1
continue
+ elif hyphenation2 and len(cLine):
+ hsw = word.__shysplit__(
+ fontName, fontSize,
+ 0 + hyw - 1e-8,
+ maxWidth,
+ encoding = self.encoding,
+ )
+ if hsw:
+ words[0:0] = [word]
+ forcedSplit = 1
+ word = None
elif attemptHyphenation:
hyOk = not getattr(f,'nobr',False)
hsw = _hyphenateWord(hyphenator if hyOk else None,
@@ -2089,7 +2101,16 @@
self._hyphenations += 1
forcedSplit = 1
continue
- if splitLongWords and not isinstance(word,_SplitWord):
+ elif hyphenation2 and len(cLine):
+ hsw = _hyphenateWord(hyphenator if hyOk else None,
+ fontName, fontSize, word, wordWidth,
wordWidth, maxWidth,
+ uriWasteReduce if hyOk else False,
+ embeddedHyphenation and hyOk, hymwl)
+ if hsw:
+ words[0:0] = [word]
+ forcedSplit = 1
+ word = None
+ if splitLongWords and not (isinstance(word,_SplitWord) or
forcedSplit):
nmw = min(lineno,maxlineno)
if wordWidth>max(maxWidths[nmw:nmw+1]):
#a long word
@@ -2099,7 +2120,7 @@
continue
if newWidth <= (maxWidth+spaceShrink) or not len(cLine) or
forcedSplit:
# fit one more on this line
- cLine.append(word)
+ if word: cLine.append(word)
if forcedSplit:
forcedSplit = 0
if newWidth > self._width_max: self._width_max =
newWidth
@@ -2170,6 +2191,13 @@
FW.pop(-1) #remove this as we are doing this one
again
self._hyphenations += 1
continue
+ elif hyphenation2 and len(FW)>1: #only if we are
not the first word on the line
+ hsw = w.shyphenate(wordWidth, maxWidth)
+ if hsw:
+ _words[0:0] =
[_InjectedFrag([0,(f.clone(_fkind=_FK_BREAK,text=''),'')]),w]
+ FW.pop(-1) #remove this as we are doing this
one again
+ continue
+ #else: try to split an overlong word
elif attemptHyphenation:
hyOk = not getattr(f,'nobr',False)
hsw = _hyphenateFragWord(hyphenator if hyOk else None,
@@ -2182,6 +2210,16 @@
FW.pop(-1) #remove this as we are doing this one
again
self._hyphenations += 1
continue
+ elif hyphenation2 and len(FW)>1:
+ hsw = _hyphenateFragWord(hyphenator if hyOk else
None,
+ w,wordWidth,maxWidth,
+ uriWasteReduce if hyOk else False,
+ embeddedHyphenation and hyOk, hymwl)
+ if hsw:
+ _words[0:0] =
[_InjectedFrag([0,(f.clone(_fkind=_FK_BREAK,text=''),'')]),w]
+ FW.pop(-1) #remove this as we are doing this
one again
+ continue
+ #else: try to split an overlong word
if splitLongWords and not isinstance(w,_SplitFrag):
nmw = min(lineno,maxlineno)
if wordWidth>max(maxWidths[nmw:nmw+1]):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/src/reportlab/platypus/tables.py
new/reportlab-3.5.59/src/reportlab/platypus/tables.py
--- old/reportlab-3.5.56/src/reportlab/platypus/tables.py 2020-08-07
09:31:22.000000000 +0200
+++ new/reportlab-3.5.59/src/reportlab/platypus/tables.py 2021-01-04
15:51:54.000000000 +0100
@@ -27,12 +27,14 @@
from reportlab import rl_config, xrange, ascii
from reportlab.lib.styles import PropertySet, ParagraphStyle, _baseFontName
from reportlab.lib import colors
-from reportlab.lib.utils import annotateException, IdentStr, flatten, isStr,
asNative, strTypes
+from reportlab.lib.utils import annotateException, IdentStr, flatten, isStr,
asNative, strTypes, __UNSET__
+from reportlab.lib.validators import isListOfNumbersOrNone
from reportlab.lib.rl_accel import fp_str
from reportlab.lib.abag import ABag as CellFrame
from reportlab.pdfbase.pdfmetrics import stringWidth
from reportlab.platypus.doctemplate import Indenter, NullActionFlowable
from reportlab.platypus.flowables import LIIndenter
+from collections import namedtuple
LINECAPS={None: None, 'butt':0,'round':1,'projecting':2,'squared':2}
LINEJOINS={None: None, 'miter':0, 'mitre':0, 'round':1,'bevel':2}
@@ -138,6 +140,41 @@
R[j] = v
return R
+def _calcBezierPoints(P, kind):
+ '''calculate all or half of a bezier curve
+ kind==0 all, 1=first half else second half'''
+ if kind==0:
+ return P
+ else:
+ Q0 = (0.5*(P[0][0]+P[1][0]),0.5*(P[0][1]+P[1][1]))
+ Q1 = (0.5*(P[1][0]+P[2][0]),0.5*(P[1][1]+P[2][1]))
+ Q2 = (0.5*(P[2][0]+P[3][0]),0.5*(P[2][1]+P[3][1]))
+ R0 = (0.5*(Q0[0]+Q1[0]),0.5*(Q0[1]+Q1[1]))
+ R1 = (0.5*(Q1[0]+Q2[0]),0.5*(Q1[1]+Q2[1]))
+ S0 = (0.5*(R0[0]+R1[0]),0.5*(R0[1]+R1[1]))
+ return [P[0],Q0,R0,S0] if kind==1 else [S0,R1,Q2,P[3]]
+
+def _quadrantDef(xpos, ypos, corner, r, kind=0, direction='left-right',
m=0.4472):
+ t = m*r
+ if xpos=='right' and ypos=='bottom': #bottom right
+ xhi,ylo = corner
+ P = [(xhi - r, ylo),(xhi-t, ylo), (xhi, ylo + t), (xhi, ylo + r)]
+ elif xpos=='right' and ypos=='top': #top right
+ xhi,yhi = corner
+ P = [(xhi, yhi - r),(xhi, yhi - t), (xhi - t, yhi), (xhi - r, yhi)]
+ elif xpos=='left' and ypos=='top': #top left
+ xlo,yhi = corner
+ P = [(xlo + r, yhi),(xlo + t, yhi), (xlo, yhi - t), (xlo, yhi - r)]
+ elif xpos=='left' and ypos=='bottom': #bottom left
+ xlo,ylo = corner
+ P = [(xlo, ylo + r),(xlo, ylo + t), (xlo + t, ylo), (xlo + r, ylo)]
+ else:
+ raise ValueError('Unknown quadrant position %s' % repr((xpos,ypos)))
+ if direction=='left-right' and P[0][0]>P[-1][0] or direction=='bottom-top'
and P[0][1]>P[-1][1]:
+ P.reverse()
+ P = _calcBezierPoints(P, kind)
+ return P
+
def _hLine(canvLine, scp, ecp, y, hBlocks, FUZZ=rl_config._FUZZ):
'''
Draw horizontal lines; do not draw through regions specified in hBlocks
@@ -208,11 +245,17 @@
class _ExpandedCellTuple(tuple):
pass
+
+RoundingRectDef = namedtuple('RoundingRectDefs','x0 y0 w h x1 y1 ar SL')
+RoundingRectLine = namedtuple('RoundingRectLine','xs ys xe ye weight color cap
dash join')
+
class Table(Flowable):
def __init__(self, data, colWidths=None, rowHeights=None, style=None,
repeatRows=0, repeatCols=0, splitByRow=1,
emptyTableAction=None, ident=None,
hAlign=None,vAlign=None, normalizedData=0, cellStyles=None,
rowSplitRange=None,
- spaceBefore=None,spaceAfter=None, longTableOptimize=None,
minRowHeights=None):
+ spaceBefore=None,spaceAfter=None, longTableOptimize=None,
minRowHeights=None,
+ cornerRadii=__UNSET__, #or [topLeft, topRight, bottomLeft
bottomRight]
+ ):
self.ident = ident
self.hAlign = hAlign or 'CENTER'
self.vAlign = vAlign or 'MIDDLE'
@@ -297,6 +340,9 @@
if style:
self.setStyle(style)
+ if cornerRadii is not __UNSET__: #instance argument overrides
+ self._setCornerRadii(cornerRadii)
+
self._rowSplitRange = rowSplitRange
if spaceBefore is not None:
self.spaceBefore = spaceBefore
@@ -311,6 +357,7 @@
minRowHeights =
minRowHeights+(nrows-lmrh)*minRowHeights.__class__((0,))
self._minRowHeights = minRowHeights
+
def __repr__(self):
"incomplete, but better than nothing"
r = getattr(self,'_rowHeights','[unknown]')
@@ -507,9 +554,15 @@
if ew is None: return None
w = max(w,ew)
return w
- elif isinstance(v,Flowable) and v._fixedWidth:
- if hasattr(v, 'width') and isinstance(v.width,(int,float)): return
v.width
- if hasattr(v, 'drawWidth') and
isinstance(v.drawWidth,(int,float)): return v.drawWidth
+ elif isinstance(v,Flowable):
+ if v._fixedWidth:
+ if hasattr(v, 'width') and isinstance(v.width,(int,float)):
return v.width
+ if hasattr(v, 'drawWidth') and
isinstance(v.drawWidth,(int,float)): return v.drawWidth
+ if hasattr(v,'__styledWrap__'): #very experimental
+ try:
+ return getattr(v,'__styledWrap__')(s)[0]
+ except:
+ pass
# Even if something is fixedWidth, the attribute to check is not
# necessarily consistent (cf. Image.drawWidth). Therefore, we'll
# be extra-careful and fall through to this code if necessary.
@@ -715,7 +768,7 @@
and assign some best-guess values."""
W = list(self._argW) # _calc_pc(self._argW,availWidth)
- verbose = 0
+ #verbose = 1
totalDefined = 0.0
percentDefined = 0
percentTotal = 0
@@ -733,8 +786,7 @@
else:
assert isinstance(w,(int,float))
totalDefined = totalDefined + w
- if verbose: print('prelim width calculation. %d columns, %d undefined
width, %0.2f units remain' % (
- self._ncols, numberUndefined, availWidth - totalDefined))
+ #if verbose: print('prelim width calculation. %d columns, %d
undefined width, %0.2f units remain' % (self._ncols, numberUndefined,
availWidth - totalDefined))
#check columnwise in each None column to see if they are sizable.
given = []
@@ -753,6 +805,7 @@
style = self._cellStyles[rowNo][colNo]
new = elementWidth(value,style) or 0
new += style.leftPadding+style.rightPadding
+ #if verbose: print('[%d,%d] new=%r-->%r' %
(rowNo,colNo,new - style.leftPadding+style.rightPadding, new))
final = max(final, new)
siz = siz and self._canGetWidth(value) # irrelevant now?
if siz:
@@ -765,21 +818,22 @@
given.append(colNo)
if len(given) == self._ncols:
return
- if verbose: print('predefined width: ',given)
- if verbose: print('uncomputable width: ',unsizeable)
- if verbose: print('computable width: ',sizeable)
+ #if verbose: print('predefined width: ',given)
+ #if verbose: print('uncomputable width: ',unsizeable)
+ #if verbose: print('computable width: ',sizeable)
+ #if verbose: print('minimums=%r' %
(list(sorted(list(minimums.items()))),))
# how much width is left:
remaining = availWidth - (totalMinimum + totalDefined)
if remaining > 0:
# we have some room left; fill it.
- definedPercentage = (totalDefined/availWidth)*100
+ definedPercentage = (totalDefined/float(availWidth))*100
percentTotal += definedPercentage
if numberUndefined and percentTotal < 100:
undefined = numberGreedyUndefined or numberUndefined
- defaultWeight = (100-percentTotal)/undefined
+ defaultWeight = (100-percentTotal)/float(undefined)
percentTotal = 100
- defaultDesired = (defaultWeight/percentTotal)*availWidth
+ defaultDesired = (defaultWeight/float(percentTotal))*availWidth
else:
defaultWeight = defaultDesired = 1
# we now calculate how wide each column wanted to be, and then
@@ -826,7 +880,7 @@
# column is (104/264), which, multiplied by the desired
# width of 264, is 104: the amount assigned to the remaining
# column.
- proportion = effectiveRemaining/totalDesired
+ proportion = effectiveRemaining/float(totalDesired)
# we sort the desired widths by difference between desired and
# and minimum values, a value called "disappointment" in the
# code. This means that the columns with a bigger
@@ -841,7 +895,7 @@
totalDesired -= desired
effectiveRemaining -= minimum
if totalDesired:
- proportion = effectiveRemaining/totalDesired
+ proportion = effectiveRemaining/float(totalDesired)
else:
finalSet.append((minimum, desired, colNo))
for minimum, desired, colNo in finalSet:
@@ -851,7 +905,7 @@
else:
for colNo, minimum in minimums.items():
W[colNo] = minimum
- if verbose: print('new widths are:', W)
+ #if verbose: print('new widths are:', W)
self._argW = self._colWidths = W
return W
@@ -1091,6 +1145,8 @@
assert len(cmd) == 10
self._linecmds.append(tuple(cmd))
+ elif cmd[0]=="ROUNDEDCORNERS":
+ self._setCornerRadii(cmd[1])
else:
(op, (sc, sr), (ec, er)), values = cmd[:3] , cmd[3:]
if sr in ('splitfirst','splitlast'):
@@ -1104,25 +1160,48 @@
def _drawLines(self):
ccap, cdash, cjoin = None, None, None
- self.canv.saveState()
- for op, (sc,sr), (ec,er), weight, color, cap, dash, join, count, space
in self._linecmds:
- if isinstance(sr,strTypes) and sr.startswith('split'): continue
- if cap!=None and ccap!=cap:
- self.canv.setLineCap(cap)
- ccap = cap
- if dash is None or dash == []:
- if cdash is not None:
- self.canv.setDash()
- cdash = None
- elif dash != cdash:
- self.canv.setDash(dash)
- cdash = dash
- if join is not None and cjoin!=join:
- self.canv.setLineJoin(join)
- cjoin = join
- sc, ec, sr, er = self.normCellRange(sc,ec,sr,er)
- getattr(self,_LineOpMap.get(op, '_drawUnknown' ))( (sc, sr), (ec,
er), weight, color, count, space)
- self.canv.restoreState()
+ canv = self.canv
+ canv.saveState()
+
+ rrd = self._roundingRectDef
+ if rrd: #we are collection some lines
+ SL = rrd.SL
+ SL[:] = [] #empty saved lines list
+ ocanvline = canv.line
+ aSL = SL.append
+ def rcCanvLine(xs, ys, xe, ye):
+ if (
+ (xs==xe and (xs>=rrd.x1 or xs<=rrd.x0)) #vertical line
that needs to be saved
+ or
+ (ys==ye and (ys>=rrd.y1 or ys<=rrd.y0)) #horizontal line
that needs to be saved
+ ):
+
aSL(RoundingRectLine(xs,ys,xe,ye,weight,color,cap,dash,join))
+ else:
+ ocanvline(xs,ys,xe,ye)
+ canv.line = rcCanvLine
+
+ try:
+ for op, (sc,sr), (ec,er), weight, color, cap, dash, join, count,
space in self._linecmds:
+ if isinstance(sr,strTypes) and sr.startswith('split'): continue
+ if cap!=None and ccap!=cap:
+ canv.setLineCap(cap)
+ ccap = cap
+ if dash is None or dash == []:
+ if cdash is not None:
+ canv.setDash()
+ cdash = None
+ elif dash != cdash:
+ canv.setDash(dash)
+ cdash = dash
+ if join is not None and cjoin!=join:
+ canv.setLineJoin(join)
+ cjoin = join
+ sc, ec, sr, er = self.normCellRange(sc,ec,sr,er)
+ getattr(self,_LineOpMap.get(op, '_drawUnknown' ))( (sc, sr),
(ec, er), weight, color, count, space)
+ finally:
+ if rrd:
+ canv.line = ocanvline
+ canv.restoreState()
self._curcolor = None
def _drawUnknown(self, start, end, weight, color, count, space):
@@ -1306,12 +1385,14 @@
splitH = self._rowHeights
else:
splitH = self._argH
+ cornerRadii = getattr(self,'_cornerRadii',None)
R0 = self.__class__( data[:n], colWidths=self._colWidths,
rowHeights=splitH[:n],
repeatRows=repeatRows, repeatCols=repeatCols,
splitByRow=splitByRow, normalizedData=1,
cellStyles=self._cellStyles[:n],
ident=ident,
spaceBefore=getattr(self,'spaceBefore',None),
- longTableOptimize=lto)
+ longTableOptimize=lto,
+ cornerRadii=cornerRadii[:2] if cornerRadii else None)
nrows = self._nrows
ncols = self._ncols
@@ -1392,6 +1473,7 @@
ident=ident,
spaceAfter=getattr(self,'spaceAfter',None),
longTableOptimize=lto,
+ cornerRadii = cornerRadii,
)
R1._cr_1_1(n,nrows,repeatRows,A) #linecommands
R1._cr_1_1(n,nrows,repeatRows,self._bkgrndcmds,_srflMode=True)
@@ -1405,6 +1487,7 @@
ident=ident,
spaceAfter=getattr(self,'spaceAfter',None),
longTableOptimize=lto,
+ cornerRadii = ([0,0] + cornerRadii[2:]) if cornerRadii
else None,
)
R1._cr_1_0(n,A)
R1._cr_1_0(n,self._bkgrndcmds,_srflMode=True)
@@ -1463,7 +1546,117 @@
else:
raise NotImplementedError
+ def _makeRoundedCornersClip(self, FUZZ=rl_config._FUZZ):
+ self._roundingRectDef = None
+ cornerRadii = getattr(self,'_cornerRadii',None)
+ if not cornerRadii or max(cornerRadii)<=FUZZ: return
+ nrows = self._nrows
+ ncols = self._ncols
+ ar = [min(self._rowHeights[i],self._colWidths[j],cornerRadii[k]) for
+ k,(i,j) in enumerate((
+ (0,0),
+ (0,ncols-1),
+ (nrows-1,0),
+ (nrows-1, ncols-1),
+ ))]
+ rp = self._rowpositions
+ cp = self._colpositions
+
+ x0 = cp[0]
+ y0 = rp[nrows]
+ x1 = cp[ncols]
+ y1 = rp[0]
+ w = x1 - x0
+ h = y1 - y0
+ self._roundingRectDef = RoundingRectDef(x0, y0, w, h, x1, y1, ar, [])
+ P = self.canv.beginPath()
+ P.roundRect(x0, y0, w, h, ar)
+ c = self.canv
+ c.addLiteral('%begin table rect clip')
+ c.clipPath(P,stroke=0)
+ c.addLiteral('%end table rect clip')
+
+ def _restoreRoundingObscuredLines(self):
+ x0, y0, w, h, x1, y1, ar, SL = self._roundingRectDef
+ if not SL: return
+ canv = self.canv
+ canv.saveState()
+ ccap = cdash = cjoin = self._curweight = self._curcolor = None
+ line = canv.line
+ cornerRadii = self._cornerRadii
+ for (xs,ys,xe,ye,weight,color,cap,dash,join) in SL:
+ if cap!=None and ccap!=cap:
+ canv.setLineCap(cap)
+ ccap = cap
+ if dash is None or dash == []:
+ if cdash is not None:
+ canv.setDash()
+ cdash = None
+ elif dash != cdash:
+ canv.setDash(dash)
+ cdash = dash
+ if join is not None and cjoin!=join:
+ canv.setLineJoin(join)
+ cjoin = join
+ self._prepLine(weight, color)
+ if ys==ye:
+ #horizontal line
+ if ys>y1 or ys<y0:
+ line(xs,ys,xe,ye) #simple line that's outside the clip
+ continue
+ #which corners are involved
+ if ys==y0:
+ ypos = 'bottom'
+ r0 = ar[2]
+ r1 = ar[3]
+ else: #ys==y1
+ ypos = 'top'
+ r0 = ar[0]
+ r1 = ar[1]
+ if xs>=x0+r0 and xe<=x1-r1:
+ line(xs,ys,xe,ye) #simple line with no rounding
+ continue
+ #we have some rounding so we must use a path
+ c0 = _quadrantDef('left',ypos,(xs,ys), r0, kind=2,
direction='left-right') if xs<x0+r0 else None
+ c1 = _quadrantDef('right',ypos,(xe,ye), r1, kind=1,
direction='left-right') if xe>x1-r1 else None
+ else:
+ #vertical line
+ if xs>x1 or xs<x0:
+ line(xs,ys,xe,ye) #simple line that's outside the clip
+ continue
+ #which corners are involved
+ if xs==x0:
+ xpos = 'left'
+ r0 = ar[2]
+ r1 = ar[0]
+ else: #xs==x1
+ xpos = 'right'
+ r0 = ar[3]
+ r1 = ar[1]
+ if ys>=y0+r0 and ye<=y1-r1:
+ line(xs,ys,xe,ye) #simple line with no rounding
+ continue
+ #we have some rounding so we must use a path
+ c0 = _quadrantDef(xpos,'bottom',(xs,ys), r0, kind=2,
direction='bottom-top') if ys<y0+r0 else None
+ c1 = _quadrantDef(xpos,'top',(xe,ye), r1, kind=1,
direction='bottom-top') if ye>y1-r1 else None
+ P = canv.beginPath()
+ if c0:
+ P.moveTo(*c0[0])
+ P.curveTo(c0[1][0],c0[1][1],c0[2][0],c0[2][1],
c0[3][0],c0[3][1])
+ else:
+ P.moveTo(xs,ys)
+ if not c1:
+ P.lineTo(xe,ye)
+ else:
+ P.lineTo(*c1[0])
+ P.curveTo(c1[1][0],c1[1][1],c1[2][0],c1[2][1],
c1[3][0],c1[3][1])
+ canv.drawPath(P, stroke=1, fill=0)
+ canv.restoreState()
+
def draw(self):
+ c = self.canv
+ c.saveState()
+ self._makeRoundedCornersClip()
self._curweight = self._curcolor = self._curcellstyle = None
self._drawBkgrnd()
if not self._spanCmds:
@@ -1483,6 +1676,9 @@
cellstyle = self._cellStyles[rowNo][colNo]
self._drawCell(cellval, cellstyle, (x, y), (width,
height))
self._drawLines()
+ c.restoreState()
+ if self._roundingRectDef:
+ self._restoreRoundingObscuredLines()
def _drawBkgrnd(self):
nrows = self._nrows
@@ -1649,6 +1845,12 @@
#external hyperlink
self.canv.linkRect("", cellstyle.destination, Rect=(colpos,
rowpos, colpos + colwidth, rowpos + rowheight), relative=1)
+ def _setCornerRadii(self, cornerRadii):
+ if isListOfNumbersOrNone(cornerRadii):
+ self._cornerRadii = None if not cornerRadii else list(cornerRadii)
+ (max(4-len(cornerRadii),0)*[0])
+ else:
+ raise ValueError('cornerRadii should be None or a list/tuple of
numeric radii')
+
_LineOpMap = { 'GRID':'_drawGrid',
'BOX':'_drawBox',
'OUTLINE':'_drawBox',
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/src/reportlab.egg-info/PKG-INFO
new/reportlab-3.5.59/src/reportlab.egg-info/PKG-INFO
--- old/reportlab-3.5.56/src/reportlab.egg-info/PKG-INFO 2020-12-01
17:29:31.000000000 +0100
+++ new/reportlab-3.5.59/src/reportlab.egg-info/PKG-INFO 2021-01-04
15:52:21.000000000 +0100
@@ -1,6 +1,6 @@
Metadata-Version: 1.1
Name: reportlab
-Version: 3.5.56
+Version: 3.5.59
Summary: The Reportlab Toolkit
Home-page: http://www.reportlab.com/
Author: Andy Robinson, Robin Becker, the ReportLab team and the community
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/src/rl_addons/rl_accel/_rl_accel.c
new/reportlab-3.5.59/src/rl_addons/rl_accel/_rl_accel.c
--- old/reportlab-3.5.56/src/rl_addons/rl_accel/_rl_accel.c 2020-09-24
15:27:24.000000000 +0200
+++ new/reportlab-3.5.59/src/rl_addons/rl_accel/_rl_accel.c 2020-12-27
12:44:36.000000000 +0100
@@ -30,7 +30,7 @@
#ifndef min
# define min(a,b) ((a)<(b)?(a):(b))
#endif
-#define VERSION "0.75"
+#define VERSION "0.80"
#define MODULE "_rl_accel"
struct module_state {
@@ -435,11 +435,37 @@
static PyObject *escapePDF(PyObject *module, PyObject* args)
{
- unsigned char *text;
- Py_ssize_t textLen;
+ unsigned char *inData;
+ Py_ssize_t length;
+ PyObject *retVal=NULL, *inObj, *_o1=NULL;
- if (!PyArg_ParseTuple(args, "s#:escapePDF", &text, &textLen)) return
NULL;
- return _escapePDF(text,textLen);
+ if (!PyArg_ParseTuple(args, "O:escapePDF", &inObj)) return NULL;
+ if(PyUnicode_Check(inObj)){
+ _o1 = PyUnicode_AsLatin1String(inObj);
+ if(!_o1){
+ PyErr_SetString(PyExc_ValueError,"argument not
decodable as latin1");
+ ERROR_EXIT();
+ }
+ inData = PyBytes_AsString(_o1);
+ inObj = _o1;
+ if(!inData){
+ PyErr_SetString(PyExc_ValueError,"argument not
converted to internal char string");
+ ERROR_EXIT();
+ }
+ }
+ else if(!PyBytes_Check(inObj)){
+ PyErr_SetString(PyExc_ValueError,"argument should be "
BYTESNAME " or latin1 decodable " STRNAME);
+ ERROR_EXIT();
+ }
+ inData = PyBytes_AsString(inObj);
+ length = PyBytes_GET_SIZE(inObj);
+ retVal = _escapePDF(inData,length);
+L_exit:
+ Py_XDECREF(_o1);
+ return retVal;
+L_ERR:
+ ADD_TB(module,"excapePDF");
+ goto L_exit;
}
static PyObject *sameFrag(PyObject *module, PyObject* args)
@@ -1240,7 +1266,7 @@
PyDoc_STRVAR(__DOC__,
"_rl_accel contains various accelerated utilities\n\
\n\
-\tescapePDF makes a string safe for PDF\n\
+\tescapePDF makes a unicode or latin1 bytes safe for PDF\n\
\n\
\tasciiBase85Encode does what is says\n\
\tasciiBase85Decode does what is says\n\
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_multibyte_jpn.py
new/reportlab-3.5.59/tests/test_multibyte_jpn.py
--- old/reportlab-3.5.56/tests/test_multibyte_jpn.py 2019-10-01
17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_multibyte_jpn.py 2020-12-27
12:44:36.000000000 +0100
@@ -56,14 +56,16 @@
# work in post Unicode world.
pdfmetrics.registerFont(CIDFont('HeiseiMin-W3','90ms-RKSJ-V'))
c.setFont('HeiseiMin-W3-90ms-RKSJ-V', 16)
- c.drawString(450, 650, '\223\214\213\236 vertical Shift-JIS')
- height = c.stringWidth('\223\214\213\236 vertical Shift-JIS',
'HeiseiMin-W3-90ms-RKSJ-V', 16)
+ s = u'\223\214\213\236 vertical Shift-JIS' #these are octal numbers
+ c.drawString(450, 650, s)
+ height = c.stringWidth(s, 'HeiseiMin-W3-90ms-RKSJ-V', 16)
c.rect(450-8,650,16,-height)
pdfmetrics.registerFont(CIDFont('HeiseiMin-W3','EUC-V'))
c.setFont('HeiseiMin-W3-EUC-V', 16)
- c.drawString(475, 650, '\xC5\xEC\xB5\xFE vertical EUC')
- height = c.stringWidth('\xC5\xEC\xB5\xFE vertical EUC',
'HeiseiMin-W3-EUC-V', 16)
+ s = u'\xC5\xEC\xB5\xFE vertical EUC'
+ c.drawString(475, 650, s)
+ height = c.stringWidth(s, 'HeiseiMin-W3-EUC-V', 16)
c.rect(475-8,650,16,-height)
@@ -76,8 +78,9 @@
wordWrap="CJK"
)
- gatwickText =
'\xe3\x82\xac\xe3\x83\x88\xe3\x82\xa6\xe3\x82\xa3\xe3\x83\x83\xe3\x82\xaf\xe7\xa9\xba\xe6\xb8\xaf\xe3\x81\xa8\xe9\x80\xa3\xe7\xb5\xa1\xe9\x80\x9a\xe8\xb7\xaf\xe3\x81\xa7\xe7\x9b\xb4\xe7\xb5\x90\xe3\x81\x95\xe3\x82\x8c\xe3\x81\xa6\xe3\x81\x84\xe3\x82\x8b\xe5\x94\xaf\xe4\xb8\x80\xe3\x81\xae\xe3\x83\x9b\xe3\x83\x86\xe3\x83\xab\xe3\x81\xa7\xe3\x81\x82\xe3\x82\x8b\xe5\xbd\x93\xe3\x83\x9b\xe3\x83\x86\xe3\x83\xab\xe3\x81\xaf\xe3\x80\x81\xe8\xa1\x97\xe3\x81\xae\xe4\xb8\xad\xe5\xbf\x83\xe9\x83\xa8\xe3\x81\x8b\xe3\x82\x8930\xe5\x88\x86\xe3\x81\xae\xe5\xa0\xb4\xe6\x89\x80\xe3\x81\xab\xe3\x81\x94\xe3\x81\x96\xe3\x81\x84\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe5\x85\xa8\xe5\xae\xa2\xe5\xae\xa4\xe3\x81\xab\xe9\xab\x98\xe9\x80\x9f\xe3\x82\xa4\xe3\x83\xb3\xe3\x82\xbf\xe3\x83\xbc\xe3\x83\x8d\xe3\x83\x83\xe3\x83\x88\xe7\x92\xb0\xe5\xa2\x83\xe3\x82\x92\xe5\xae\x8c\xe5\x82\x99\xe3\x81\x97\xe3\x81\xa6\xe3\x81\x8a\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe3\x83\x95\xe3\x82\xa1
\xe3\x83\x9f\xe3\x83\xaa\xe3\x83\xbc\xe3\x83\xab\xe3\x83\xbc\xe3\x83\xa0\xe3\x81\xaf5\xe5\x90\x8d\xe6\xa7\x98\xe3\x81\xbe\xe3\x81\xa7\xe3\x81\x8a\xe6\xb3\x8a\xe3\x82\x8a\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe3\x81\xbe\xe3\x81\x9f\xe3\x80\x81\xe3\x82\xa8\xe3\x82\xb0\xe3\x82\xbc\xe3\x82\xaf\xe3\x83\x86\xe3\x82\xa3\xe3\x83\x96\xe3\x83\xab\xe3\x83\xbc\xe3\x83\xa0\xe3\x81\xae\xe3\x81\x8a\xe5\xae\xa2\xe6\xa7\x98\xe3\x81\xaf\xe3\x80\x81\xe3\x82\xa8\xe3\x82\xb0\xe3\x82\xbc\xe3\x82\xaf\xe3\x83\x86\xe3\x82\xa3\xe3\x83\x96\xe3\x83\xa9\xe3\x82\xa6\xe3\x83\xb3\xe3\x82\xb8\xe3\x82\x92\xe3\x81\x94\xe5\x88\xa9\xe7\x94\xa8\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe4\xba\x8b\xe5\x89\x8d\xe3\x81\xab\xe3\x81\x94\xe4\xba\x88\xe7\xb4\x84\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x82\x8b\xe3\x82\xbf\xe3\x82\xa4\xe3\x83\xa0\xe3\x83\x88\xe3\x82\xa5\xe3\x83\x95\xe3\x83\xa9\xe3\x82\xa4\xe3\x83\xbb\xe3\x83\x91
\xe3\x83\x83\xe3\x82\xb1\xe3\x83\xbc\xe3\x82\xb8\xe3\x81\xab\xe3\x81\xaf\xe3\x80\x81\xe7\xa9\xba\xe6\xb8\xaf\xe3\x81\xae\xe9\xa7\x90\xe8\xbb\x8a\xe6\x96\x99\xe9\x87\x91\xe3\x81\x8c\xe5\x90\xab\xe3\x81\xbe\xe3\x82\x8c\xe3\x81\xa6\xe3\x81\x8a\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82'
- gatwickText2=
'\xe3\x82\xac\xe3\x83\x88\xe3\x82\xa6\xe3\x82\xa3\xe3\x83\x83\xe3\x82\xaf<font
color=red>\xe7\xa9\xba\xe6\xb8\xaf\xe3\x81\xa8\xe9\x80\xa3\xe7\xb5\xa1\xe9\x80\x9a\xe8\xb7\xaf\xe3\x81\xa7\xe7\x9b\xb4\xe7\xb5\x90</font>\xe3\x81\x95\xe3\x82\x8c\xe3\x81\xa6\xe3\x81\x84\xe3\x82\x8b\xe5\x94\xaf\xe4\xb8\x80\xe3\x81\xae\xe3\x83\x9b\xe3\x83\x86\xe3\x83\xab\xe3\x81\xa7\xe3\x81\x82\xe3\x82\x8b\xe5\xbd\x93\xe3\x83\x9b\xe3\x83\x86\xe3\x83\xab\xe3\x81\xaf\xe3\x80\x81\xe8\xa1\x97\xe3\x81\xae\xe4\xb8\xad\xe5\xbf\x83\xe9\x83\xa8\xe3\x81\x8b\xe3\x82\x8930\xe5\x88\x86\xe3\x81\xae\xe5\xa0\xb4\xe6\x89\x80\xe3\x81\xab\xe3\x81\x94\xe3\x81\x96\xe3\x81\x84\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe5\x85\xa8\xe5\xae\xa2\xe5\xae\xa4\xe3\x81\xab\xe9\xab\x98\xe9\x80\x9f\xe3\x82\xa4\xe3\x83\xb3\xe3\x82\xbf\xe3\x83\xbc\xe3\x83\x8d\xe3\x83\x83\xe3\x83\x88<link
fg="blue"
href="http://www.reportlab.com">\xe7\x92\xb0\xe5\xa2\x83\xe3\x82\x92\xe5\xae\x8c\xe5\x82\x99</link>\xe3\x81\x97\xe3\x81\xa6<u>\xe
3\x81\x8a\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x99</u>\xe3\x80\x82\xe3\x83\x95\xe3\x82\xa1\xe3\x83\x9f\xe3\x83\xaa\xe3\x83\xbc\xe3\x83\xab\xe3\x83\xbc\xe3\x83\xa0\xe3\x81\xaf5\xe5\x90\x8d\xe6\xa7\x98\xe3\x81\xbe\xe3\x81\xa7\xe3\x81\x8a\xe6\xb3\x8a\xe3\x82\x8a\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe3\x81\xbe\xe3\x81\x9f\xe3\x80\x81\xe3\x82\xa8\xe3\x82\xb0\xe3\x82\xbc\xe3\x82\xaf\xe3\x83\x86\xe3\x82\xa3\xe3\x83\x96\xe3\x83\xab\xe3\x83\xbc\xe3\x83\xa0\xe3\x81\xae\xe3\x81\x8a\xe5\xae\xa2\xe6\xa7\x98\xe3\x81\xaf\xe3\x80\x81\xe3\x82\xa8\xe3\x82\xb0\xe3\x82\xbc\xe3\x82\xaf\xe3\x83\x86\xe3\x82\xa3\xe3\x83\x96\xe3\x83\xa9\xe3\x82\xa6\xe3\x83\xb3\xe3\x82\xb8\xe3\x82\x92\xe3\x81\x94\xe5\x88\xa9\xe7\x94\xa8\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe4\xba\x8b\xe5\x89\x8d\xe3\x81\xab\xe3\x81\x94\xe4\xba\x88\xe7\xb4\x84\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x82\x8b\xe3\x82\xbf\xe3\x82\xa4\xe3\x83\xa
0\xe3\x83\x88\xe3\x82\xa5\xe3\x83\x95\xe3\x83\xa9\xe3\x82\xa4\xe3\x83\xbb\xe3\x83\x91\xe3\x83\x83\xe3\x82\xb1\xe3\x83\xbc\xe3\x82\xb8\xe3\x81\xab\xe3\x81\xaf\xe3\x80\x81\xe7\xa9\xba\xe6\xb8\xaf\xe3\x81\xae\xe9\xa7\x90\xe8\xbb\x8a\xe6\x96\x99\xe9\x87\x91\xe3\x81\x8c\xe5\x90\xab\xe3\x81\xbe\xe3\x82\x8c\xe3\x81\xa6\xe3\x81\x8a\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82'
+ #this is utf8
+ gatwickText =
b'\xe3\x82\xac\xe3\x83\x88\xe3\x82\xa6\xe3\x82\xa3\xe3\x83\x83\xe3\x82\xaf\xe7\xa9\xba\xe6\xb8\xaf\xe3\x81\xa8\xe9\x80\xa3\xe7\xb5\xa1\xe9\x80\x9a\xe8\xb7\xaf\xe3\x81\xa7\xe7\x9b\xb4\xe7\xb5\x90\xe3\x81\x95\xe3\x82\x8c\xe3\x81\xa6\xe3\x81\x84\xe3\x82\x8b\xe5\x94\xaf\xe4\xb8\x80\xe3\x81\xae\xe3\x83\x9b\xe3\x83\x86\xe3\x83\xab\xe3\x81\xa7\xe3\x81\x82\xe3\x82\x8b\xe5\xbd\x93\xe3\x83\x9b\xe3\x83\x86\xe3\x83\xab\xe3\x81\xaf\xe3\x80\x81\xe8\xa1\x97\xe3\x81\xae\xe4\xb8\xad\xe5\xbf\x83\xe9\x83\xa8\xe3\x81\x8b\xe3\x82\x8930\xe5\x88\x86\xe3\x81\xae\xe5\xa0\xb4\xe6\x89\x80\xe3\x81\xab\xe3\x81\x94\xe3\x81\x96\xe3\x81\x84\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe5\x85\xa8\xe5\xae\xa2\xe5\xae\xa4\xe3\x81\xab\xe9\xab\x98\xe9\x80\x9f\xe3\x82\xa4\xe3\x83\xb3\xe3\x82\xbf\xe3\x83\xbc\xe3\x83\x8d\xe3\x83\x83\xe3\x83\x88\xe7\x92\xb0\xe5\xa2\x83\xe3\x82\x92\xe5\xae\x8c\xe5\x82\x99\xe3\x81\x97\xe3\x81\xa6\xe3\x81\x8a\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe3\x83\x95\xe3\x82\xa
1\xe3\x83\x9f\xe3\x83\xaa\xe3\x83\xbc\xe3\x83\xab\xe3\x83\xbc\xe3\x83\xa0\xe3\x81\xaf5\xe5\x90\x8d\xe6\xa7\x98\xe3\x81\xbe\xe3\x81\xa7\xe3\x81\x8a\xe6\xb3\x8a\xe3\x82\x8a\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe3\x81\xbe\xe3\x81\x9f\xe3\x80\x81\xe3\x82\xa8\xe3\x82\xb0\xe3\x82\xbc\xe3\x82\xaf\xe3\x83\x86\xe3\x82\xa3\xe3\x83\x96\xe3\x83\xab\xe3\x83\xbc\xe3\x83\xa0\xe3\x81\xae\xe3\x81\x8a\xe5\xae\xa2\xe6\xa7\x98\xe3\x81\xaf\xe3\x80\x81\xe3\x82\xa8\xe3\x82\xb0\xe3\x82\xbc\xe3\x82\xaf\xe3\x83\x86\xe3\x82\xa3\xe3\x83\x96\xe3\x83\xa9\xe3\x82\xa6\xe3\x83\xb3\xe3\x82\xb8\xe3\x82\x92\xe3\x81\x94\xe5\x88\xa9\xe7\x94\xa8\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe4\xba\x8b\xe5\x89\x8d\xe3\x81\xab\xe3\x81\x94\xe4\xba\x88\xe7\xb4\x84\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x82\x8b\xe3\x82\xbf\xe3\x82\xa4\xe3\x83\xa0\xe3\x83\x88\xe3\x82\xa5\xe3\x83\x95\xe3\x83\xa9\xe3\x82\xa4\xe3\x83\xbb\xe3\x83\x9
1\xe3\x83\x83\xe3\x82\xb1\xe3\x83\xbc\xe3\x82\xb8\xe3\x81\xab\xe3\x81\xaf\xe3\x80\x81\xe7\xa9\xba\xe6\xb8\xaf\xe3\x81\xae\xe9\xa7\x90\xe8\xbb\x8a\xe6\x96\x99\xe9\x87\x91\xe3\x81\x8c\xe5\x90\xab\xe3\x81\xbe\xe3\x82\x8c\xe3\x81\xa6\xe3\x81\x8a\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82'
+ gatwickText2=
b'\xe3\x82\xac\xe3\x83\x88\xe3\x82\xa6\xe3\x82\xa3\xe3\x83\x83\xe3\x82\xaf<font
color=red>\xe7\xa9\xba\xe6\xb8\xaf\xe3\x81\xa8\xe9\x80\xa3\xe7\xb5\xa1\xe9\x80\x9a\xe8\xb7\xaf\xe3\x81\xa7\xe7\x9b\xb4\xe7\xb5\x90</font>\xe3\x81\x95\xe3\x82\x8c\xe3\x81\xa6\xe3\x81\x84\xe3\x82\x8b\xe5\x94\xaf\xe4\xb8\x80\xe3\x81\xae\xe3\x83\x9b\xe3\x83\x86\xe3\x83\xab\xe3\x81\xa7\xe3\x81\x82\xe3\x82\x8b\xe5\xbd\x93\xe3\x83\x9b\xe3\x83\x86\xe3\x83\xab\xe3\x81\xaf\xe3\x80\x81\xe8\xa1\x97\xe3\x81\xae\xe4\xb8\xad\xe5\xbf\x83\xe9\x83\xa8\xe3\x81\x8b\xe3\x82\x8930\xe5\x88\x86\xe3\x81\xae\xe5\xa0\xb4\xe6\x89\x80\xe3\x81\xab\xe3\x81\x94\xe3\x81\x96\xe3\x81\x84\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe5\x85\xa8\xe5\xae\xa2\xe5\xae\xa4\xe3\x81\xab\xe9\xab\x98\xe9\x80\x9f\xe3\x82\xa4\xe3\x83\xb3\xe3\x82\xbf\xe3\x83\xbc\xe3\x83\x8d\xe3\x83\x83\xe3\x83\x88<link
fg="blue"
href="http://www.reportlab.com">\xe7\x92\xb0\xe5\xa2\x83\xe3\x82\x92\xe5\xae\x8c\xe5\x82\x99</link>\xe3\x81\x97\xe3\x81\xa6<u>\x
e3\x81\x8a\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x99</u>\xe3\x80\x82\xe3\x83\x95\xe3\x82\xa1\xe3\x83\x9f\xe3\x83\xaa\xe3\x83\xbc\xe3\x83\xab\xe3\x83\xbc\xe3\x83\xa0\xe3\x81\xaf5\xe5\x90\x8d\xe6\xa7\x98\xe3\x81\xbe\xe3\x81\xa7\xe3\x81\x8a\xe6\xb3\x8a\xe3\x82\x8a\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe3\x81\xbe\xe3\x81\x9f\xe3\x80\x81\xe3\x82\xa8\xe3\x82\xb0\xe3\x82\xbc\xe3\x82\xaf\xe3\x83\x86\xe3\x82\xa3\xe3\x83\x96\xe3\x83\xab\xe3\x83\xbc\xe3\x83\xa0\xe3\x81\xae\xe3\x81\x8a\xe5\xae\xa2\xe6\xa7\x98\xe3\x81\xaf\xe3\x80\x81\xe3\x82\xa8\xe3\x82\xb0\xe3\x82\xbc\xe3\x82\xaf\xe3\x83\x86\xe3\x82\xa3\xe3\x83\x96\xe3\x83\xa9\xe3\x82\xa6\xe3\x83\xb3\xe3\x82\xb8\xe3\x82\x92\xe3\x81\x94\xe5\x88\xa9\xe7\x94\xa8\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe4\xba\x8b\xe5\x89\x8d\xe3\x81\xab\xe3\x81\x94\xe4\xba\x88\xe7\xb4\x84\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x82\x8b\xe3\x82\xbf\xe3\x82\xa4\xe3\x83\x
a0\xe3\x83\x88\xe3\x82\xa5\xe3\x83\x95\xe3\x83\xa9\xe3\x82\xa4\xe3\x83\xbb\xe3\x83\x91\xe3\x83\x83\xe3\x82\xb1\xe3\x83\xbc\xe3\x82\xb8\xe3\x81\xab\xe3\x81\xaf\xe3\x80\x81\xe7\xa9\xba\xe6\xb8\xaf\xe3\x81\xae\xe9\xa7\x90\xe8\xbb\x8a\xe6\x96\x99\xe9\x87\x91\xe3\x81\x8c\xe5\x90\xab\xe3\x81\xbe\xe3\x82\x8c\xe3\x81\xa6\xe3\x81\x8a\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82'
c.setFont('HeiseiMin-W3', 12)
jPara = Paragraph(gatwickText, jStyle)
@@ -253,16 +256,23 @@
## c.showPage()
from reportlab.lib import textsplit
-
+ def sascii(x):
+ s = ascii(x)
+ if s.startswith('u') or s.startswith('b'): s = s[1:]
+ if s.startswith("'") or s.startswith('"'): s = s[1:]
+ if s.startswith('\\u') or s.startswith('\\x'): s = s[1:]
+ if s.endswith("'") or s.endswith('"'): s = s[:-1]
+ return s
+
c.setFont('HeiseiMin-W3', 14)
y = 700
- c.drawString(70, y, 'cannot end line')
+ c.drawString(70, y, 'cannot start line')
y -= 20
for group in textsplit.CANNOT_START_LINE:
c.drawString(70, y, group)
y -= 20
c.setFont('Helvetica',10)
- c.drawString(70, y, ' '.join([ascii(x)[4:-1] for x in group]))
+ c.drawString(70, y, ' '.join([sascii(x) for x in group]))
c.setFont('HeiseiMin-W3', 14)
y -= 20
@@ -275,7 +285,7 @@
c.drawString(70, y, group)
y -= 20
c.setFont('Helvetica',10)
- c.drawString(70, y, ' '.join([ascii(x)[2:] for x in group]))
+ c.drawString(70, y, ' '.join([sascii(x) for x in group]))
c.setFont('HeiseiMin-W3', 14)
y -= 20
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_paragraphs.py
new/reportlab-3.5.59/tests/test_paragraphs.py
--- old/reportlab-3.5.56/tests/test_paragraphs.py 2020-07-20
09:39:52.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_paragraphs.py 2020-12-27
12:44:36.000000000 +0100
@@ -5,13 +5,14 @@
from reportlab import xrange
from reportlab.lib.testutils import setOutDir,makeSuiteForClasses, outputfile,
printLocation
setOutDir(__name__)
-import unittest, os
+import unittest, os, random
from reportlab.platypus import Paragraph, SimpleDocTemplate, XBox, Indenter,
XPreformatted, PageBreak, Spacer
from reportlab.lib.styles import ParagraphStyle
from reportlab.lib.units import inch
from reportlab.lib.abag import ABag
from reportlab.lib.colors import red, black, navy, white, green
from reportlab.lib.randomtext import randomText
+from reportlab.rl_config import invariant as rl_invariant
from reportlab.lib.enums import TA_LEFT, TA_RIGHT, TA_CENTER, TA_JUSTIFY
from reportlab.rl_config import defaultPageSize, rtlSupport
from reportlab.pdfbase import ttfonts
@@ -83,7 +84,7 @@
2. ...
3. ...
"""
-
+ if rl_invariant: random.seed(1854640162)
story = []
SA = story.append
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_pdfbase_ttfonts.py
new/reportlab-3.5.59/tests/test_pdfbase_ttfonts.py
--- old/reportlab-3.5.56/tests/test_pdfbase_ttfonts.py 2019-10-01
17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_pdfbase_ttfonts.py 2020-12-27
12:44:36.000000000 +0100
@@ -47,7 +47,7 @@
font = _fonts[fontName]
doc = c._doc
kfunc = font.face.charToGlyph.keys if isPy3 else
font.face.charToGlyph.iterkeys
- for s in kfunc():
+ for s in sorted(list(kfunc())):
if s<0x10000:
font.splitString(uniChr(s),doc)
state = font.state[doc]
@@ -55,7 +55,7 @@
#print('len(assignments)=%d'% len(state.assignments))
nzero = 0
ifunc = state.assignments.items if isPy3 else state.assignments.iteritems
- for code, n in ifunc():
+ for code, n in sorted(list(ifunc())):
if code==0: nzero += 1
cn[n] = uniChr(code)
if nzero>1: print('%s there were %d zero codes' % (fontName,nzero))
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_pdfgen_general.py
new/reportlab-3.5.59/tests/test_pdfgen_general.py
--- old/reportlab-3.5.56/tests/test_pdfgen_general.py 2020-09-18
15:27:00.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_pdfgen_general.py 2021-01-01
19:09:10.000000000 +0100
@@ -463,6 +463,12 @@
t.textLine('canvas.rect(x, y, width, height) - x,y is lower left')
c.roundRect(inch,6.25*inch,2*inch,0.6*inch,0.1*inch)
+ c.saveState()
+ c.setStrokeColor(red)
+ c.roundRect(inch*1.1,6.35*inch,1.8*inch,0.4*inch,[0.1*inch,0,0.09*inch,0])
+ c.setStrokeColor(green)
+ c.roundRect(inch*1.15,6.40*inch,1.7*inch,0.3*inch,[0,0.1*inch,0,0.09*inch])
+ c.restoreState()
t.setTextOrigin(4*inch, 6.55*inch)
t.textLine('canvas.roundRect(x,y,width,height,radius)')
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_breaking.py
new/reportlab-3.5.59/tests/test_platypus_breaking.py
--- old/reportlab-3.5.56/tests/test_platypus_breaking.py 2020-09-02
14:34:06.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_platypus_breaking.py 2020-12-27
12:44:36.000000000 +0100
@@ -5,7 +5,8 @@
__version__='3.3.0'
from reportlab.lib.testutils import setOutDir,makeSuiteForClasses, outputfile,
printLocation
setOutDir(__name__)
-import sys, os, time, re
+import sys, os, time, re, random
+from reportlab.rl_config import invariant as rl_invariant
from operator import truth
import unittest
from reportlab.platypus.flowables import Flowable, KeepTogether,
KeepTogetherSplitAtTop
@@ -63,6 +64,7 @@
def _test0(self):
"This makes one long multi-page paragraph in test_platypus_breaking."
+ if rl_invariant: random.seed(1532760416)
def RT(k,theme='PYTHON',sentences=1,cache={}):
if k not in cache:
cache[k] = randomText(theme=theme,sentences=sentences)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_cjk_wrap.py
new/reportlab-3.5.59/tests/test_platypus_cjk_wrap.py
--- old/reportlab-3.5.56/tests/test_platypus_cjk_wrap.py 2019-10-01
17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_platypus_cjk_wrap.py 2020-12-27
12:44:36.000000000 +0100
@@ -20,10 +20,10 @@
#says "Japanese is difficult, isn't it?"
-shortText =
'\u65e5\u672c\u8a9e\u306f\u96e3\u3057\u3044\u3067\u3059\u306d\uff01'
+shortText =
u'\u65e5\u672c\u8a9e\u306f\u96e3\u3057\u3044\u3067\u3059\u306d\uff01'
-gatwickText =
'\xe3\x82\xac\xe3\x83\x88\xe3\x82\xa6\xe3\x82\xa3\xe3\x83\x83\xe3\x82\xaf\xe7\xa9\xba\xe6\xb8\xaf\xe3\x81\xa8\xe9\x80\xa3\xe7\xb5\xa1\xe9\x80\x9a\xe8\xb7\xaf\xe3\x81\xa7\xe7\x9b\xb4\xe7\xb5\x90\xe3\x81\x95\xe3\x82\x8c\xe3\x81\xa6\xe3\x81\x84\xe3\x82\x8b\xe5\x94\xaf\xe4\xb8\x80\xe3\x81\xae\xe3\x83\x9b\xe3\x83\x86\xe3\x83\xab\xe3\x81\xa7\xe3\x81\x82\xe3\x82\x8b\xe5\xbd\x93\xe3\x83\x9b\xe3\x83\x86\xe3\x83\xab\xe3\x81\xaf\xe3\x80\x81VERYLONGENGLISHGOESHERE\xe8\xa1\x97\xe3\x81\xae\xe4\xb8\xad\xe5\xbf\x83\xe9\x83\xa8\xe3\x81\x8b\xe3\x82\x8930\xe5\x88\x86\xe3\x81\xae\xe5\xa0\xb4\xe6\x89\x80\xe3\x81\xab\xe3\x81\x94\xe3\x81\x96\xe3\x81\x84\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe5\x85\xa8\xe5\xae\xa2\xe5\xae\xa4\xe3\x81\xab\xe9\xab\x98\xe9\x80\x9f\xe3\x82\xa4\xe3\x83\xb3\xe3\x82\xbf\xe3\x83\xbc\xe3\x83\x8d\xe3\x83\x83\xe3\x83\x88\xe7\x92\xb0\xe5\xa2\x83\xe3\x82\x92\xe5\xae\x8c\xe5\x82\x99\xe3\x81\x97\xe3\x81\xa6\xe3\x81\x8a\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe3\x83\
x95\xe3\x82\xa1\xe3\x83\x9f\xe3\x83\xaa\xe3\x83\xbc\xe3\x83\xab\xe3\x83\xbc\xe3\x83\xa0\xe3\x81\xaf5\xe5\x90\x8d\xe6\xa7\x98\xe3\x81\xbe\xe3\x81\xa7\xe3\x81\x8a\xe6\xb3\x8a\xe3\x82\x8a\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe3\x81\xbe\xe3\x81\x9f\xe3\x80\x81\xe3\x82\xa8\xe3\x82\xb0\xe3\x82\xbc\xe3\x82\xaf\xe3\x83\x86\xe3\x82\xa3\xe3\x83\x96\xe3\x83\xab\xe3\x83\xbc\xe3\x83\xa0\xe3\x81\xae\xe3\x81\x8a\xe5\xae\xa2\xe6\xa7\x98\xe3\x81\xaf\xe3\x80\x81\xe3\x82\xa8\xe3\x82\xb0\xe3\x82\xbc\xe3\x82\xaf\xe3\x83\x86\xe3\x82\xa3\xe3\x83\x96\xe3\x83\xa9\xe3\x82\xa6\xe3\x83\xb3\xe3\x82\xb8\xe3\x82\x92\xe3\x81\x94\xe5\x88\xa9\xe7\x94\xa8\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe4\xba\x8b\xe5\x89\x8d\xe3\x81\xab\xe3\x81\x94\xe4\xba\x88\xe7\xb4\x84\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x82\x8b\xe3\x82\xbf\xe3\x82\xa4\xe3\x83\xa0\xe3\x83\x88\xe3\x82\xa5\xe3\x83\x95\xe3\x83\xa9\xe3\x82\xa4\xe3\x83\
xbb\xe3\x83\x91\xe3\x83\x83\xe3\x82\xb1\xe3\x83\xbc\xe3\x82\xb8\xe3\x81\xab\xe3\x81\xaf\xe3\x80\x81\xe7\xa9\xba\xe6\xb8\xaf\xe3\x81\xae\xe9\xa7\x90\xe8\xbb\x8a\xe6\x96\x99\xe9\x87\x91\xe3\x81\x8c\xe5\x90\xab\xe3\x81\xbe\xe3\x82\x8c\xe3\x81\xa6\xe3\x81\x8a\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82'
+gatwickText =
b'\xe3\x82\xac\xe3\x83\x88\xe3\x82\xa6\xe3\x82\xa3\xe3\x83\x83\xe3\x82\xaf\xe7\xa9\xba\xe6\xb8\xaf\xe3\x81\xa8\xe9\x80\xa3\xe7\xb5\xa1\xe9\x80\x9a\xe8\xb7\xaf\xe3\x81\xa7\xe7\x9b\xb4\xe7\xb5\x90\xe3\x81\x95\xe3\x82\x8c\xe3\x81\xa6\xe3\x81\x84\xe3\x82\x8b\xe5\x94\xaf\xe4\xb8\x80\xe3\x81\xae\xe3\x83\x9b\xe3\x83\x86\xe3\x83\xab\xe3\x81\xa7\xe3\x81\x82\xe3\x82\x8b\xe5\xbd\x93\xe3\x83\x9b\xe3\x83\x86\xe3\x83\xab\xe3\x81\xaf\xe3\x80\x81VERYLONGENGLISHGOESHERE\xe8\xa1\x97\xe3\x81\xae\xe4\xb8\xad\xe5\xbf\x83\xe9\x83\xa8\xe3\x81\x8b\xe3\x82\x8930\xe5\x88\x86\xe3\x81\xae\xe5\xa0\xb4\xe6\x89\x80\xe3\x81\xab\xe3\x81\x94\xe3\x81\x96\xe3\x81\x84\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe5\x85\xa8\xe5\xae\xa2\xe5\xae\xa4\xe3\x81\xab\xe9\xab\x98\xe9\x80\x9f\xe3\x82\xa4\xe3\x83\xb3\xe3\x82\xbf\xe3\x83\xbc\xe3\x83\x8d\xe3\x83\x83\xe3\x83\x88\xe7\x92\xb0\xe5\xa2\x83\xe3\x82\x92\xe5\xae\x8c\xe5\x82\x99\xe3\x81\x97\xe3\x81\xa6\xe3\x81\x8a\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe3\x83
\x95\xe3\x82\xa1\xe3\x83\x9f\xe3\x83\xaa\xe3\x83\xbc\xe3\x83\xab\xe3\x83\xbc\xe3\x83\xa0\xe3\x81\xaf5\xe5\x90\x8d\xe6\xa7\x98\xe3\x81\xbe\xe3\x81\xa7\xe3\x81\x8a\xe6\xb3\x8a\xe3\x82\x8a\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe3\x81\xbe\xe3\x81\x9f\xe3\x80\x81\xe3\x82\xa8\xe3\x82\xb0\xe3\x82\xbc\xe3\x82\xaf\xe3\x83\x86\xe3\x82\xa3\xe3\x83\x96\xe3\x83\xab\xe3\x83\xbc\xe3\x83\xa0\xe3\x81\xae\xe3\x81\x8a\xe5\xae\xa2\xe6\xa7\x98\xe3\x81\xaf\xe3\x80\x81\xe3\x82\xa8\xe3\x82\xb0\xe3\x82\xbc\xe3\x82\xaf\xe3\x83\x86\xe3\x82\xa3\xe3\x83\x96\xe3\x83\xa9\xe3\x82\xa6\xe3\x83\xb3\xe3\x82\xb8\xe3\x82\x92\xe3\x81\x94\xe5\x88\xa9\xe7\x94\xa8\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82\xe4\xba\x8b\xe5\x89\x8d\xe3\x81\xab\xe3\x81\x94\xe4\xba\x88\xe7\xb4\x84\xe3\x81\x84\xe3\x81\x9f\xe3\x81\xa0\xe3\x81\x91\xe3\x82\x8b\xe3\x82\xbf\xe3\x82\xa4\xe3\x83\xa0\xe3\x83\x88\xe3\x82\xa5\xe3\x83\x95\xe3\x83\xa9\xe3\x82\xa4\xe3\x83
\xbb\xe3\x83\x91\xe3\x83\x83\xe3\x82\xb1\xe3\x83\xbc\xe3\x82\xb8\xe3\x81\xab\xe3\x81\xaf\xe3\x80\x81\xe7\xa9\xba\xe6\xb8\xaf\xe3\x81\xae\xe9\xa7\x90\xe8\xbb\x8a\xe6\x96\x99\xe9\x87\x91\xe3\x81\x8c\xe5\x90\xab\xe3\x81\xbe\xe3\x82\x8c\xe3\x81\xa6\xe3\x81\x8a\xe3\x82\x8a\xe3\x81\xbe\xe3\x81\x99\xe3\x80\x82'
def myMainPageFrame(canvas, doc):
"The page frame used for all PDF documents."
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_indents.py
new/reportlab-3.5.59/tests/test_platypus_indents.py
--- old/reportlab-3.5.56/tests/test_platypus_indents.py 2020-01-22
15:40:54.000000000 +0100
+++ new/reportlab-3.5.59/tests/test_platypus_indents.py 2020-12-27
12:44:36.000000000 +0100
@@ -7,6 +7,7 @@
from reportlab.lib.testutils import setOutDir,makeSuiteForClasses, outputfile,
printLocation
setOutDir(__name__)
import sys, os, random
+from reportlab.rl_config import invariant as rl_invariant
from operator import truth
import unittest
from reportlab.pdfbase.pdfmetrics import stringWidth
@@ -65,6 +66,7 @@
def test0(self):
"IndentTestCase test0"
+ if rl_invariant: random.seed(1479316371)
# Build story.
story = []
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_index.py
new/reportlab-3.5.59/tests/test_platypus_index.py
--- old/reportlab-3.5.56/tests/test_platypus_index.py 2019-10-01
17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_platypus_index.py 2020-12-27
12:44:36.000000000 +0100
@@ -6,7 +6,8 @@
from reportlab import xrange
from reportlab.lib.testutils import setOutDir,makeSuiteForClasses, outputfile,
printLocation
setOutDir(__name__)
-import sys, os
+import sys, os, random
+from reportlab.rl_config import invariant as rl_invariant
from os.path import join, basename, splitext
from math import sqrt
import unittest
@@ -83,6 +84,7 @@
Index terms are grouped by their first 2, and first 3 characters.
The page numbers should be clickable and link to the indexed word.
'''
+ if rl_invariant: random.seed(1753799561)
# Build story.
for headers in False, True:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_leftright.py
new/reportlab-3.5.59/tests/test_platypus_leftright.py
--- old/reportlab-3.5.56/tests/test_platypus_leftright.py 2020-01-22
15:40:54.000000000 +0100
+++ new/reportlab-3.5.59/tests/test_platypus_leftright.py 2020-12-27
12:44:36.000000000 +0100
@@ -5,7 +5,8 @@
__version__='3.3.0'
from reportlab.lib.testutils import setOutDir,makeSuiteForClasses, outputfile,
printLocation
setOutDir(__name__)
-import sys, os, time
+import sys, os, time, random
+from reportlab.rl_config import invariant as rl_invariant
from operator import truth
import unittest
from reportlab.platypus.flowables import Flowable
@@ -88,6 +89,7 @@
def testIt(self):
"LeftRightTestCase.testit"
+ if rl_invariant: random.seed(464568862)
# Build story.
story = []
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_lists.py
new/reportlab-3.5.59/tests/test_platypus_lists.py
--- old/reportlab-3.5.56/tests/test_platypus_lists.py 2019-10-01
17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_platypus_lists.py 2020-12-27
12:44:36.000000000 +0100
@@ -3,7 +3,8 @@
from reportlab import xrange
from reportlab.lib.testutils import setOutDir,makeSuiteForClasses, outputfile,
printLocation
setOutDir(__name__)
-import os,unittest
+import os,unittest, random
+from reportlab.rl_config import invariant as rl_invariant
from reportlab.platypus import Spacer, SimpleDocTemplate, Table, TableStyle,
ListFlowable, ListItem, \
Paragraph, PageBreak, DDIndenter, MultiCol
from reportlab.lib.styles import getSampleStyleSheet, ParagraphStyle
@@ -60,6 +61,7 @@
"Make documents with tables"
def test1(self):
+ if rl_invariant: random.seed(888147853)
styleSheet = getSampleStyleSheet()
doc =
SimpleDocTemplate(outputfile('test_platypus_lists1.pdf'),showBoundary=True)
story=[]
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_paragraphs.py
new/reportlab-3.5.59/tests/test_platypus_paragraphs.py
--- old/reportlab-3.5.56/tests/test_platypus_paragraphs.py 2020-10-29
17:06:02.000000000 +0100
+++ new/reportlab-3.5.59/tests/test_platypus_paragraphs.py 2020-12-27
12:44:36.000000000 +0100
@@ -15,7 +15,7 @@
from reportlab.lib.colors import Color
from reportlab.lib.units import cm
from reportlab.lib.enums import TA_LEFT, TA_RIGHT, TA_CENTER, TA_JUSTIFY
-from reportlab.lib.utils import _className, asBytes, asUnicode
+from reportlab.lib.utils import _className, asBytes, asUnicode, asNative
from reportlab.lib.styles import getSampleStyleSheet, ParagraphStyle
from reportlab.platypus.xpreformatted import XPreformatted
from reportlab.platypus.frames import Frame, ShowBoundaryValue
@@ -186,13 +186,74 @@
style = ParagraphStyle(
'normal', fontName='Helvetica', fontSize=12,
embeddedHyphenation=1, splitLongWords=0, hyphenationLang='en-GB')
- text =
'Super\xc2\xadcali\xc2\xadfragi\xc2\xadlistic\xc2\xadexpi\xc2\xadali\xc2\xaddocious'
+ shy = asNative(u'\xad')
+ text =
shy.join(('Super','cali','fragi','listic','expi','ali','docious'))
f.addFromList([Paragraph(text, style)], c)
text = u'<span color="red">Super</span><span
color="pink">­cali­</span>fragi­listic­expi­ali­docious'
f.addFromList([Paragraph(text, style)], c)
c.showPage()
c.save()
+ def test_platypus_paragraphs_embedded2(self):
+ from hashlib import md5 as hashlib_md5
+
+ fontName = 'Helvetica'
+ fontSize = 10
+
+ texts = [asUnicode(text) for text
+ in [
+ b'UU\xc2\xadDIS\xc2\xadTU\xc2\xadSA\xc2\xadLA JA
TAI\xc2\xadMIK\xc2\xadKO',
+ b'NUO\xc2\xadRI
KAS\xc2\xadVA\xc2\xadTUS\xc2\xadMET\xc2\xadSIK\xc2\xadK\xc3\x96',
+ b'VART\xc2\xadTU\xc2\xadNUT
KAS\xc2\xadVA\xc2\xadTUS\xc2\xadMET\xc2\xadSIK\xc2\xadK\xc3\x96',
+ b'UU\xc2\xadDIS\xc2\xadTUS-KYP\xc2\xadS\xc3\x84
MET\xc2\xadSIK\xc2\xadK\xc3\x96',
+ b'SIE\xc2\xadMEN- JA
SUO-JUS\xc2\xadPUU-MET\xc2\xadSIK\xc2\xadK\xc3\x96',
+
b'E\xc2\xadRI-I\xc2\xadK\xc3\x84\xc2\xadIS-RA\xc2\xadKEN\xc2\xadTEI\xc2\xadNEN
MET\xc2\xadSIK\xc2\xadK\xc3\x96',
+ ]
+ ]
+ maxWidth = stringWidth('VARTTUNUT KAS', fontName, fontSize)+0.5
+ span = lambda _t, _c: "<span color='%s'>%s</span>" % (_c, _t)
+
+ pagesize = (20+maxWidth, 800)
+ c = Canvas(outputfile('test_platypus_paragraphs_embedded2.pdf'),
pagesize=pagesize)
+
+ expected = [
+ (163, b'\x7f\xd7_^\x07\x9c!u\x02\xb4\x13z\xb5y6C'),
+ (163, b'\xab\x82\xbf\xb3\xfc\xb5\xaau\x15\xb1<\x8eX\xbe35'),
+ (163, b'LL\xb1\xfd.\x8a\x8bk\xde\xcdK\x16P\xebWh'),
+ (163, b'\xa9fj\xdd\xb9\x11N\xcf\xbb\x12\xfb\xd9\xa5\xf0v<'),
+ (163, b'\x18r\x98\x17\xd8&\x8c\x01{\xf3|r\xca\xccQy'),
+ (163, b'\xb7\xf2\x0f/d\xe9<\xd1B?\xe5\x8c\xcbO\x06?'),
+ ]
+ observed = []
+ for eh in 0, 1, 2:
+ for slw in 0, 1:
+ f = Frame(10, 10, maxWidth, 780,
+ showBoundary=ShowBoundaryValue(dashArray=(1,1)),
+ leftPadding=0,
+ rightPadding=0,
+ topPadding=0,
+ bottomPadding=0,
+ )
+ style = ParagraphStyle(
+ 'normal', fontName=fontName, fontSize=fontSize,
+ embeddedHyphenation=eh, splitLongWords=slw,
+ hyphenationLang=None)
+ f.addFromList([Paragraph('slw=%d eh=%d' % (slw,eh), style)], c)
+ for text in texts:
+ f.addFromList([Paragraph(text, style)], c)
+ mfText = text.split(u'\xad')
+ mfText[0] = span(mfText[0],'red')
+ if len(mfText)>1:
+ mfText[1] = span(mfText[1],'pink')
+ if len(mfText)>2:
+ mfText[-1] = span(mfText[-1],'blue')
+ mfText = u'­'.join(mfText)
+ f.addFromList([Paragraph(mfText, style)], c)
+ observed.append((len(c._code),
hashlib_md5(b"".join((asBytes(b,"latin1") for b in c._code))).digest()))
+ c.showPage()
+ c.save()
+ self.assertEqual(observed, expected)
+
def test_lele_img(self):
from reportlab.pdfgen.canvas import Canvas
from reportlab.platypus import Paragraph
@@ -621,9 +682,9 @@
\xd7\x93\xd7\xa8\xd7\x9b\xd7\x94
\xd7\xa9\xd7\x99\xd7\xaa\xd7\x95\xd7\xa4\xd7\x99\xd7\xaa
\xd7\x90\xd7\xaa\xd7\x94 \xd7\x93\xd7\xaa.'''
gif = os.path.join(testsFolder,'pythonpowered.gif')
- heading = Paragraph('\xd7\x96\xd7\x95\xd7\x94\xd7\x99
\xd7\x9b\xd7\x95\xd7\xaa\xd7\xa8\xd7\xaa',h3)
+ heading = Paragraph(b'\xd7\x96\xd7\x95\xd7\x94\xd7\x99
\xd7\x9b\xd7\x95\xd7\xaa\xd7\xa8\xd7\xaa',h3)
story.append(ImageAndFlowables(Image(gif),[heading,Paragraph(text,bt)]))
- heading = Paragraph('\xd7\x96\xd7\x95\xd7\x94\xd7\x99
\xd7\x9b\xd7\x95\xd7\xaa\xd7\xa8\xd7\xaa',h3)
+ heading = Paragraph(b'\xd7\x96\xd7\x95\xd7\x94\xd7\x99
\xd7\x9b\xd7\x95\xd7\xaa\xd7\xa8\xd7\xaa',h3)
story.append(ImageAndFlowables(Image(gif),[heading,Paragraph(text1,bt)]))
doc =
MyDocTemplate(outputfile('test_platypus_imageandflowables_rtl.pdf'),showBoundary=1)
doc.multiBuild(story)
@@ -1311,7 +1372,7 @@
bt = getSampleStyleSheet()['BodyText']
bt.fontName = 'DejaVuSans'
doc = SimpleDocTemplate(fn)
- story = [Paragraph('<b>%s</b>' % title,bt)]
+ story = [Paragraph('<b>%s</b>' % asNative(title),bt)]
story.extend([Paragraph(bu('&%s; = <span color="red">&%s;</span>' %
(k,k)), bt) for k, v in alphaSortedItems(greeks)])
doc.build(story)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/reportlab-3.5.56/tests/test_platypus_pleaseturnover.py
new/reportlab-3.5.59/tests/test_platypus_pleaseturnover.py
--- old/reportlab-3.5.56/tests/test_platypus_pleaseturnover.py 2019-10-01
17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_platypus_pleaseturnover.py 2020-12-27
12:44:36.000000000 +0100
@@ -5,8 +5,7 @@
__version__='3.3.0'
from reportlab.lib.testutils import setOutDir,makeSuiteForClasses, outputfile,
printLocation
setOutDir(__name__)
-import sys
-import unittest
+import sys, unittest
from reportlab.platypus.flowables import Flowable, PTOContainer, KeepInFrame
from reportlab.platypus import FrameBG
from reportlab.lib.units import cm
@@ -16,7 +15,6 @@
from reportlab.platypus.paragraph import Paragraph
from reportlab.platypus.tables import Table
from reportlab.platypus.frames import Frame
-from reportlab.lib.randomtext import randomText
from reportlab.platypus.doctemplate import PageTemplate, BaseDocTemplate,
FrameBreak
def myMainPageFrame(canvas, doc):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_preformatted.py
new/reportlab-3.5.59/tests/test_platypus_preformatted.py
--- old/reportlab-3.5.56/tests/test_platypus_preformatted.py 2020-01-22
15:40:54.000000000 +0100
+++ new/reportlab-3.5.59/tests/test_platypus_preformatted.py 2020-12-27
12:44:36.000000000 +0100
@@ -5,7 +5,7 @@
__version__='3.3.0'
from reportlab.lib.testutils import setOutDir,makeSuiteForClasses, outputfile,
printLocation
setOutDir(__name__)
-import sys, os, random
+import sys, os
from operator import truth
import unittest
from reportlab.pdfbase.pdfmetrics import stringWidth
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_programming.py
new/reportlab-3.5.59/tests/test_platypus_programming.py
--- old/reportlab-3.5.56/tests/test_platypus_programming.py 2019-10-01
17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_platypus_programming.py 2020-12-27
12:44:36.000000000 +0100
@@ -7,8 +7,7 @@
"""
from reportlab.lib.testutils import setOutDir,makeSuiteForClasses, outputfile,
printLocation
setOutDir(__name__)
-import sys
-import unittest
+import sys, unittest
class PlatypusProgrammingTestCase(unittest.TestCase):
"test platypus programming"
@@ -60,6 +59,9 @@
from reportlab.platypus import Paragraph
from reportlab.lib import colors
from reportlab.lib.randomtext import randomText, PYTHON
+ import random
+ from reportlab.rl_config import invariant as rl_invariant
+ if rl_invariant: random.seed(2103696747)
# Build story.
story = []
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_tables.py
new/reportlab-3.5.59/tests/test_platypus_tables.py
--- old/reportlab-3.5.56/tests/test_platypus_tables.py 2020-12-01
17:29:04.000000000 +0100
+++ new/reportlab-3.5.59/tests/test_platypus_tables.py 2021-01-04
15:51:54.000000000 +0100
@@ -1066,6 +1066,72 @@
self.assertEqual(len(T[1]._bkgrndcmds),3)
doc.build(story)
+ def test5(self):
+ '''test rounded corners'''
+ story = []
+ story_add = story.append
+ ts_tables = [
+ ('BACKGROUND',(0,0),(-1,0),colors.pink),
+ ('BACKGROUND',(0,1),(-1,1),colors.lightblue),
+ ('ROWBACKGROUNDS',(0,2),(-1,-1),(colors.lightgrey,None)),
+ ('TEXTCOLOR',(0,0),(-1,0),colors.green),
+ ('TEXTCOLOR',(0,1),(-1,1),colors.red),
+ ('LINEABOVE', (0,0), (-1,0), 1, colors.purple),
+ ('LINEBELOW', (0,0), (-1,0), 2, colors.purple),
+ ('LINEABOVE', (0,1), (-1,1), 1, colors.orange),
+ ('LINEBELOW', (0,1), (-1,1), 2, colors.orange),
+ ('LINEBEFORE', (0,0), (0,-1), 1, colors.red),
+ ('LINEAFTER', (-1,0), (-1,-1), 1, colors.blue),
+ ('LINEBELOW', (0,-1), (-1,-1), 1, colors.green),
+ ('FONT', (2,2), (5,8), 'Times-Bold'),
+ ]
+ data = self.data34
+ from reportlab.platypus import Paragraph, Table, SimpleDocTemplate,
PageBreak
+ from reportlab.lib.styles import getSampleStyleSheet, ParagraphStyle
+ styleSheet = getSampleStyleSheet()
+ bodyText = styleSheet['BodyText']
+
+ story_add(Paragraph('The whole table',bodyText))
+ t = Table(data[:], style=ts_tables, repeatRows=2,
cornerRadii=[5,6,4,3])
+ story_add(t)
+ t = Table(data[:], style=ts_tables, repeatRows=2,
cornerRadii=[5,6,4,5])
+ T = t.split(4*72,90)
+ story_add(Paragraph('The split table part 0',bodyText))
+ story_add(T[0])
+ story_add(Paragraph('The split table part 1',bodyText))
+ story_add(T[1])
+ story_add(PageBreak())
+ ts2 = ts_tables+[('ROUNDEDCORNERS',[5,6,4,3])]
+ story_add(Paragraph('Rounded corners via style',bodyText))
+ t = Table(data[:], style=ts2, repeatRows=2)
+ story_add(t)
+ t = Table(data[:], style=ts2, repeatRows=2)
+ T = t.split(4*72,90)
+ story_add(Paragraph('The split table part 0',bodyText))
+ story_add(T[0])
+ story_add(Paragraph('The split table part 1',bodyText))
+ story_add(T[1])
+ story_add(PageBreak())
+ story_add(Paragraph('Rounded corners via style overridden by instance
argument',bodyText))
+ t = Table(data[:], style=ts2, repeatRows=2, cornerRadii=(0,3,5,0))
+ story_add(t)
+ t = Table(data[:], style=ts2, repeatRows=2, cornerRadii=t._cornerRadii)
+ T = t.split(4*72,90)
+ story_add(Paragraph('The split table part 0',bodyText))
+ story_add(T[0])
+ story_add(Paragraph('The split table part 1',bodyText))
+ story_add(T[1])
+ story_add(Paragraph('Rounded corners double linebelow',bodyText))
+ ts3 = ts_tables[:]
+ ts3.remove(('LINEBELOW', (0,-1), (-1,-1), 1, colors.green))
+ ts3.append(('LINEBELOW', (0,-1), (-1,-1), 1, colors.green, 1, None,
None, 3,1))
+ t = Table(data[:], style=ts3, repeatRows=2,
cornerRadii=[0,0,6,7])#[4,5,6,7])
+ story_add(t)
+ doc =
SimpleDocTemplate(outputfile('test_platypus_tables_rounded_corners.pdf'),
showBoundary=0)
+ doc.build(story)
+ assert(T[0]._cornerRadii==[0,3,0,0])
+ assert(T[1]._cornerRadii==[0,3,5,0])
+
def makeSuite():
return makeSuiteForClasses(TablesTestCase)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_toc.py
new/reportlab-3.5.59/tests/test_platypus_toc.py
--- old/reportlab-3.5.56/tests/test_platypus_toc.py 2019-10-01
17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_platypus_toc.py 2020-12-27
12:44:36.000000000 +0100
@@ -13,6 +13,7 @@
from os.path import join, basename, splitext
from math import sqrt
import random
+from reportlab.rl_config import invariant as rl_invariant
import unittest
from reportlab.lib.units import inch, cm
from reportlab.lib.pagesizes import A4
@@ -133,7 +134,7 @@
3. Only entries of every second level has links
...
"""
-
+ if rl_invariant: random.seed(2077179149)
maxLevels = 12
# Create styles to be used for document headers
@@ -181,7 +182,7 @@
with the right headings to make it go faster. We used
a simple 100-chapter document with one level.
"""
-
+ if rl_invariant: random.seed(1216902530)
chapters = 30 #goes over one page
headerStyle = makeHeaderStyle(0)
@@ -281,6 +282,7 @@
self.assertTrue(hasattr(doc,'seq'))
def test2(self):
+ if rl_invariant: random.seed(530125105)
chapters = 20 #so we know we use only one page
from reportlab.lib.colors import pink
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_wrapping.py
new/reportlab-3.5.59/tests/test_platypus_wrapping.py
--- old/reportlab-3.5.56/tests/test_platypus_wrapping.py 2020-01-22
15:40:54.000000000 +0100
+++ new/reportlab-3.5.59/tests/test_platypus_wrapping.py 2020-12-27
12:44:36.000000000 +0100
@@ -5,7 +5,7 @@
__version__='3.3.0'
from reportlab.lib.testutils import setOutDir,makeSuiteForClasses, outputfile,
printLocation
setOutDir(__name__)
-import sys, os, random
+import sys, os
from operator import truth
import unittest
from reportlab.pdfbase.pdfmetrics import stringWidth
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_platypus_xref.py
new/reportlab-3.5.59/tests/test_platypus_xref.py
--- old/reportlab-3.5.56/tests/test_platypus_xref.py 2019-10-01
17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_platypus_xref.py 2020-12-27
12:44:36.000000000 +0100
@@ -5,7 +5,8 @@
__version__='3.3.0'
from reportlab.lib.testutils import setOutDir,makeSuiteForClasses, outputfile,
printLocation
setOutDir(__name__)
-import sys, os, time
+import sys, os, time, random
+from reportlab.rl_config import invariant as rl_invariant
from operator import truth
import unittest
from reportlab.lib import colors
@@ -69,6 +70,7 @@
def _test0(self):
"This makes one long multi-page paragraph."
from reportlab.platypus.flowables import DocAssign, DocExec, DocPara,
DocIf, DocWhile
+ if rl_invariant: random.seed(1629812163)
# Build story.
story = []
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_rl_accel.py
new/reportlab-3.5.59/tests/test_rl_accel.py
--- old/reportlab-3.5.56/tests/test_rl_accel.py 2019-10-01 17:38:11.000000000
+0200
+++ new/reportlab-3.5.59/tests/test_rl_accel.py 2020-12-27 12:44:36.000000000
+0100
@@ -81,8 +81,15 @@
def testEscapePDF(self):
for func, kind in getFuncs('escapePDF'):
- assert func('(test)')=='\\(test\\)',"%s
escapePDF('(test)')=='\\\\(test\\\\)' fails with value %s!" % (
- kind,ascii(func('(test)')))
+ for s, sx in (
+ ('(test)', r'\(test\)'),
+ (r'\(test)', r'\\\(test\)'),
+ (b'\223\214\213\236',r'\223\214\213\236'),
+ (u'\223\214\213\236',r'\223\214\213\236'),
+ ):
+ r = func(s)
+ assert r==sx,"%s escapePDF('%s')=='%s' fails with value '%s'!"
% (
+ kind,s,sx,r)
def testCalcChecksum(self):
for func, kind in getFuncs('calcChecksum'):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/reportlab-3.5.56/tests/test_source_chars.py
new/reportlab-3.5.59/tests/test_source_chars.py
--- old/reportlab-3.5.56/tests/test_source_chars.py 2019-10-01
17:38:11.000000000 +0200
+++ new/reportlab-3.5.59/tests/test_source_chars.py 2020-12-27
12:44:36.000000000 +0100
@@ -23,6 +23,9 @@
self.output =
open(outputfile(os.path.splitext(os.path.basename(fn))[0]+'.txt'),'w')
+ def tearDown(self):
+ self.output.close()
+
def checkFileForTabs(self, filename):
txt = open_and_read(filename, 'r')
chunks = txt.split('\t')