Merge lp:~who+dev/inkscape/inkscape-p23 into lp:~inkscape.dev/inkscape/trunk

Proposed by Windell Oskay
Status: Needs review
Proposed branch: lp:~who+dev/inkscape/inkscape-p23
Merge into: lp:~inkscape.dev/inkscape/trunk
Diff against target: 231 lines (+43/-25)
6 files modified
share/extensions/bezmisc.py (+25/-11)
share/extensions/cspsubdiv.py (+2/-1)
share/extensions/inkex.py (+6/-4)
share/extensions/simplepath.py (+7/-7)
share/extensions/simplestyle.py (+2/-1)
share/extensions/simpletransform.py (+1/-1)
To merge this branch: bzr merge lp:~who+dev/inkscape/inkscape-p23
Reviewer Review Type Date Requested Status
Inkscape Developers Pending
Review via email: mp+319886@code.launchpad.net

Commit message

Update certain extensions for compatibility with Python 3.

Description of the change

Summary: Change to several of the core python extension files for compatibility with Python 3. These modifications allow them to continue working in python 2.x, without adding dependencies.

Submitted for code review and possible merging.

The changed files are:
inkex.py
bezmisc.py
cspsubdiv.py
simplepath.py
simplestyle.py
simpletransform.py

In addition to these, I would note that ffgeom.py and cubicsuperpath.py work in both Python 2 and 3 without changes. I have not tested other extension files for compatibility.

These changes appear to be non-breaking within Inkscape, as tested via invoking extensions that depend upon these, including flatten, Voronoi pattern (generate from path), and alphabetsoup. I have tested back to Python 2.6 under Inkscape 0.91, and up to Python 3.6 on the command line. While this is neither a formal test procedure nor exhaustive, I have not observed issues or errors due to these changes. If there are formal tests that could identify other issues, I would certainly welcome learning about them.

One coding note that I have is that the function definitions in bezmisc.py required "manually" unpacking the named tuples on their inputs, which adds one line of code to each function. (It could be approached in other ways, but many of those would break extensions that rely upon this.) Someone more expert at python may know of a more elegant approach. I would welcome such suggestions.

I would assert that making the extension environment compatible with Python 3 is a worthwhile goal, even if we are quite some ways away from making Python 3 compatibility an option or requirement. A good near-term goal is that we encourage extension developers to write code that is compatible with both Python 2 and Python 3. The changes in this branch correct several issues that prevent existing extensions (those that call these "core" files) from running under Python 3.

This set of changes in this branch also potentially allows certain Inkscape extensions to be run from the command line without opening the Inkscape GUI (not otherwise possible for verbs) on systems running either Python 2 or 3 as default.

To post a comment you must log in.

Unmerged revisions

15598. By Windell Oskay

changes for compatibility with python 3

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'share/extensions/bezmisc.py'
2--- share/extensions/bezmisc.py 2016-03-16 09:58:21 +0000
3+++ share/extensions/bezmisc.py 2017-03-15 02:08:29 +0000
4@@ -18,6 +18,7 @@
5 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
6 '''
7
8+from __future__ import print_function
9 import math, cmath
10
11 def rootWrapper(a,b,c,d):
12@@ -55,8 +56,9 @@
13 return 1.0*(-d/c),
14 return ()
15
16-def bezierparameterize(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3))):
17+def bezierparameterize(input):
18 #parametric bezier
19+ ((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3))=input
20 x0=bx0
21 y0=by0
22 cx=3*(bx1-x0)
23@@ -69,8 +71,9 @@
24 return ax,ay,bx,by,cx,cy,x0,y0
25 #ax,ay,bx,by,cx,cy,x0,y0=bezierparameterize(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)))
26
27-def linebezierintersect(((lx1,ly1),(lx2,ly2)),((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3))):
28+def linebezierintersect(input):
29 #parametric line
30+ ((lx1,ly1),(lx2,ly2)),((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3))=input
31 dd=lx1
32 cc=lx2-lx1
33 bb=ly1
34@@ -99,19 +102,23 @@
35 retval.append(bezierpointatt(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)),i))
36 return retval
37
38-def bezierpointatt(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)),t):
39+def bezierpointatt(param1,t):
40+ ((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3))=param1
41 ax,ay,bx,by,cx,cy,x0,y0=bezierparameterize(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)))
42 x=ax*(t**3)+bx*(t**2)+cx*t+x0
43 y=ay*(t**3)+by*(t**2)+cy*t+y0
44 return x,y
45
46-def bezierslopeatt(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)),t):
47+def bezierslopeatt(param1,t):
48+ ((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3))=param1
49 ax,ay,bx,by,cx,cy,x0,y0=bezierparameterize(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)))
50 dx=3*ax*(t**2)+2*bx*t+cx
51 dy=3*ay*(t**2)+2*by*t+cy
52 return dx,dy
53
54-def beziertatslope(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)),(dy,dx)):
55+def beziertatslope(param1,param2):
56+ ((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3))=param1
57+ (dy,dx)=param2
58 ax,ay,bx,by,cx,cy,x0,y0=bezierparameterize(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)))
59 #quadratic coefficents of slope formula
60 if dx:
61@@ -136,9 +143,12 @@
62 retval.append(i)
63 return retval
64
65-def tpoint((x1,y1),(x2,y2),t):
66+def tpoint(param1,param2,t):
67+ (x1,y1)=param1
68+ (x2,y2)=param2
69 return x1+t*(x2-x1),y1+t*(y2-y1)
70-def beziersplitatt(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)),t):
71+def beziersplitatt(param1,t):
72+ ((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3))=param1
73 m1=tpoint((bx0,by0),(bx1,by1),t)
74 m2=tpoint((bx1,by1),(bx2,by2),t)
75 m3=tpoint((bx2,by2),(bx3,by3),t)
76@@ -167,7 +177,9 @@
77 mat-report no. 1992-10, Mathematical Institute, The Technical
78 University of Denmark.
79 '''
80-def pointdistance((x1,y1),(x2,y2)):
81+def pointdistance(point1,point2):
82+ (x1,y1)=point1
83+ (x2,y2)=point2
84 return math.sqrt(((x2 - x1) ** 2) + ((y2 - y1) ** 2))
85 def Gravesen_addifclose(b, len, error = 0.001):
86 box = 0
87@@ -214,13 +226,15 @@
88 #print multiplier, endsum, interval, asum, bsum, est1, est0
89 return est1
90
91-def bezierlengthSimpson(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)), tolerance = 0.001):
92+def bezierlengthSimpson(param1, tolerance = 0.001):
93+ ((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3))=param1
94 global balfax,balfbx,balfcx,balfay,balfby,balfcy
95 ax,ay,bx,by,cx,cy,x0,y0=bezierparameterize(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)))
96 balfax,balfbx,balfcx,balfay,balfby,balfcy = 3*ax,2*bx,cx,3*ay,2*by,cy
97 return Simpson(balf, 0.0, 1.0, 4096, tolerance)
98
99-def beziertatlength(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)), l = 0.5, tolerance = 0.001):
100+def beziertatlength(param1, l = 0.5, tolerance = 0.001):
101+ ((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3))=param1
102 global balfax,balfbx,balfcx,balfay,balfby,balfcy
103 ax,ay,bx,by,cx,cy,x0,y0=bezierparameterize(((bx0,by0),(bx1,by1),(bx2,by2),(bx3,by3)))
104 balfax,balfbx,balfcx,balfay,balfby,balfcy = 3*ax,2*bx,cx,3*ay,2*by,cy
105@@ -268,7 +282,7 @@
106 print s, st
107 '''
108 for curve in curves:
109- print beziertatlength(curve,0.5)
110+ print(beziertatlength(curve,0.5))
111
112
113 # vim: expandtab shiftwidth=4 tabstop=8 softtabstop=4 fileencoding=utf-8 textwidth=99
114
115=== modified file 'share/extensions/cspsubdiv.py'
116--- share/extensions/cspsubdiv.py 2011-11-21 20:58:06 +0000
117+++ share/extensions/cspsubdiv.py 2017-03-15 02:08:29 +0000
118@@ -2,7 +2,8 @@
119 from bezmisc import *
120 from ffgeom import *
121
122-def maxdist(((p0x,p0y),(p1x,p1y),(p2x,p2y),(p3x,p3y))):
123+def maxdist(input):
124+ ((p0x,p0y),(p1x,p1y),(p2x,p2y),(p3x,p3y))=input
125 p0 = Point(p0x,p0y)
126 p1 = Point(p1x,p1y)
127 p2 = Point(p2x,p2y)
128
129=== modified file 'share/extensions/inkex.py'
130--- share/extensions/inkex.py 2016-05-26 09:28:23 +0000
131+++ share/extensions/inkex.py 2017-03-15 02:08:29 +0000
132@@ -98,11 +98,13 @@
133 ...
134 inkex.errormsg(_("This extension requires two selected paths."))
135 """
136- if isinstance(msg, unicode):
137- sys.stderr.write(msg.encode("utf-8") + "\n")
138+ if sys.version_info.major == 2:
139+ if isinstance(msg, unicode):
140+ sys.stderr.write(msg.encode("utf-8") + "\n")
141+ else:
142+ sys.stderr.write((unicode(msg, "utf-8", errors='replace') + "\n").encode("utf-8"))
143 else:
144- sys.stderr.write((unicode(msg, "utf-8", errors='replace') + "\n").encode("utf-8"))
145-
146+ sys.stderr.write(msg + "\n")
147
148 def are_near_relative(a, b, eps):
149 return (a-b <= a*eps) and (a-b >= -a*eps)
150
151=== modified file 'share/extensions/simplepath.py' (properties changed: -x to +x)
152--- share/extensions/simplepath.py 2016-03-16 09:58:21 +0000
153+++ share/extensions/simplepath.py 2017-03-15 02:08:29 +0000
154@@ -48,7 +48,7 @@
155 offset = m.end()
156 continue
157 #TODO: create new exception
158- raise Exception, 'Invalid path data!'
159+ raise Exception('Invalid path data!')
160 '''
161 pathdefs = {commandfamily:
162 [
163@@ -86,14 +86,14 @@
164
165 while 1:
166 try:
167- token, isCommand = lexer.next()
168+ token, isCommand = next(lexer)
169 except StopIteration:
170 break
171 params = []
172 needParam = True
173 if isCommand:
174 if not lastCommand and token.upper() != 'M':
175- raise Exception, 'Invalid path, must begin with moveto.'
176+ raise Exception('Invalid path, must begin with moveto.')
177 else:
178 command = token
179 else:
180@@ -106,16 +106,16 @@
181 else:
182 command = pathdefs[lastCommand.upper()][0].lower()
183 else:
184- raise Exception, 'Invalid path, no initial command.'
185+ raise Exception('Invalid path, no initial command.')
186 numParams = pathdefs[command.upper()][1]
187 while numParams > 0:
188 if needParam:
189 try:
190- token, isCommand = lexer.next()
191+ token, isCommand = next(lexer)
192 if isCommand:
193- raise Exception, 'Invalid number of parameters'
194+ raise Exception('Invalid number of parameters')
195 except StopIteration:
196- raise Exception, 'Unexpected end of path'
197+ raise Exception('Unexpected end of path')
198 cast = pathdefs[command.upper()][2][-numParams]
199 param = cast(token)
200 if command.islower():
201
202=== modified file 'share/extensions/simplestyle.py' (properties changed: -x to +x)
203--- share/extensions/simplestyle.py 2016-03-16 09:58:21 +0000
204+++ share/extensions/simplestyle.py 2017-03-15 02:08:29 +0000
205@@ -1,3 +1,4 @@
206+#!/usr/bin/env python
207 """
208 simplestyle.py
209 Two simple functions for working with inline css
210@@ -17,7 +18,7 @@
211
212 You should have received a copy of the GNU General Public License
213 along with this program; if not, write to the Free Software
214-Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
215+Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
216 """
217
218 svgcolors={
219
220=== modified file 'share/extensions/simpletransform.py' (properties changed: -x to +x)
221--- share/extensions/simpletransform.py 2016-03-16 09:58:21 +0000
222+++ share/extensions/simpletransform.py 2017-03-15 02:08:29 +0000
223@@ -131,7 +131,7 @@
224 def fuseTransform(node):
225 if node.get('d')==None:
226 #FIXME: how do you raise errors?
227- raise AssertionError, 'can not fuse "transform" of elements that have no "d" attribute'
228+ raise AssertionError('can not fuse "transform" of elements that have no "d" attribute')
229 t = node.get("transform")
230 if t == None:
231 return