3725
|
1 |
from reportlab.lib.utils import isUnicodeType, isSeqType
|
|
2 |
from math import log
|
|
3 |
_log_10 = lambda x,log=log,_log_e_10=log(10.0): log(x)/_log_e_10
|
|
4 |
_fp_fmts = "%.0f", "%.1f", "%.2f", "%.3f", "%.4f", "%.5f", "%.6f"
|
|
5 |
def fp_str(*a):
|
|
6 |
'''convert separate arguments (or single sequence arg) into space separated numeric strings'''
|
|
7 |
if len(a)==1 and isSeqType(a[0]): a = a[0]
|
|
8 |
s = []
|
|
9 |
A = s.append
|
|
10 |
for i in a:
|
|
11 |
sa =abs(i)
|
|
12 |
if sa<=1e-7: A('0')
|
|
13 |
else:
|
|
14 |
l = sa<=1 and 6 or min(max(0,(6-int(_log_10(sa)))),6)
|
|
15 |
n = _fp_fmts[l]%i
|
|
16 |
if l:
|
|
17 |
j = len(n)
|
|
18 |
while j:
|
|
19 |
j -= 1
|
|
20 |
if n[j]!='0':
|
|
21 |
if n[j]!='.': j += 1
|
|
22 |
break
|
|
23 |
n = n[:j]
|
|
24 |
A((n[0]!='0' or len(n)==1) and n or n[1:])
|
|
25 |
return ' '.join(s)
|
|
26 |
|
|
27 |
#hack test for comma users
|
|
28 |
if ',' in fp_str(0.25):
|
|
29 |
_FP_STR = fp_str
|
|
30 |
def fp_str(*a):
|
|
31 |
return _FP_STR(*a).replace(',','.')
|
|
32 |
|
|
33 |
def unicode2T1(utext,fonts,font0=None):
|
|
34 |
'''return a list of (font,string) pairs representing the unicode text'''
|
|
35 |
R = []
|
|
36 |
font, fonts = fonts[0], fonts[1:]
|
|
37 |
if font0 is None: font0 = font
|
|
38 |
enc = font.encName
|
|
39 |
if 'UCS-2' in enc:
|
|
40 |
enc = 'UTF16'
|
|
41 |
while utext:
|
|
42 |
try:
|
|
43 |
if isUnicodeType(utext):
|
|
44 |
s = utext.encode(enc)
|
|
45 |
else:
|
|
46 |
s = utext
|
|
47 |
R.append((font,s))
|
|
48 |
break
|
|
49 |
except UnicodeEncodeError as e:
|
|
50 |
i0, il = e.args[2:4]
|
|
51 |
if i0:
|
|
52 |
R.append((font,utext[:i0].encode(enc)))
|
|
53 |
if fonts:
|
|
54 |
R.extend(unicode2T1(utext[i0:il],fonts,font0))
|
|
55 |
else:
|
|
56 |
R.append((font0._notdefFont,font0._notdefChar*(il-i0)))
|
|
57 |
utext = utext[il:]
|
|
58 |
return R
|
|
59 |
|
|
60 |
def _instanceStringWidthU(self, text, size, encoding='utf8'):
|
|
61 |
"""This is the "purist" approach to width"""
|
|
62 |
if not isUnicodeType(text): text = text.decode(encoding)
|
|
63 |
return sum([sum(map(f.widths.__getitem__,list(map(ord,t)))) for f, t in unicode2T1(text,[self]+self.substitutionFonts)])*0.001*size
|
|
64 |
|
|
65 |
if __name__=='__main__':
|
|
66 |
import sys, os
|
|
67 |
for modname in 'reportlab.lib.rl_accel','reportlab.lib._rl_accel':
|
|
68 |
for cmd in (
|
|
69 |
#"unicode2T1('abcde fghi . jkl ; mno',fonts)",
|
|
70 |
#"unicode2T1(u'abcde fghi . jkl ; mno',fonts)",
|
|
71 |
"_instanceStringWidthU(font,'abcde fghi . jkl ; mno',10)",
|
|
72 |
"_instanceStringWidthU(font,u'abcde fghi . jkl ; mno',10)",
|
|
73 |
):
|
|
74 |
print '%s %s' % (modname,cmd)
|
|
75 |
s=';'.join((
|
|
76 |
"from reportlab.pdfbase.pdfmetrics import getFont",
|
|
77 |
"from %s import unicode2T1,_instanceStringWidthU" % modname,
|
|
78 |
"fonts=[getFont('Helvetica')]+getFont('Helvetica').substitutionFonts""",
|
|
79 |
"font=fonts[0]",
|
|
80 |
))
|
|
81 |
os.system('%s -m timeit -s"%s" "%s"' % (sys.executable,s,cmd))
|