Skip to content

Commit 95ea574

Browse files
author
hartsantler
committed
Dart backend: translate operator overloading including inplace assignement operators to Dart.
1 parent 5831872 commit 95ea574

3 files changed

Lines changed: 252 additions & 1 deletion

File tree

pythonjs/python_to_pythonjs.py

Lines changed: 30 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -506,7 +506,36 @@ def visit_AugAssign(self, node):
506506
a = '%s = Math.floor(%s/%s)' %(target, target, self.visit(node.value))
507507
writer.write(a)
508508

509-
elif self._with_js or self._with_dart:
509+
elif self._with_dart:
510+
if op == '+=':
511+
a = '%s.__iadd__(%s)' %(target, self.visit(node.value))
512+
elif op == '-=':
513+
a = '%s.__isub__(%s)' %(target, self.visit(node.value))
514+
elif op == '*=':
515+
a = '%s.__imul__(%s)' %(target, self.visit(node.value))
516+
elif op == '/=':
517+
a = '%s.__idiv__(%s)' %(target, self.visit(node.value))
518+
elif op == '%=':
519+
a = '%s.__imod__(%s)' %(target, self.visit(node.value))
520+
elif op == '&=':
521+
a = '%s.__iand__(%s)' %(target, self.visit(node.value))
522+
elif op == '|=':
523+
a = '%s.__ior__(%s)' %(target, self.visit(node.value))
524+
elif op == '^=':
525+
a = '%s.__ixor__(%s)' %(target, self.visit(node.value))
526+
elif op == '<<=':
527+
a = '%s.__ilshift__(%s)' %(target, self.visit(node.value))
528+
elif op == '>>=':
529+
a = '%s.__irshift__(%s)' %(target, self.visit(node.value))
530+
else:
531+
raise NotImplementedError
532+
533+
b = '%s %s %s' %(target, op, self.visit(node.value))
534+
## dart2js is smart enough to optimize this if/else away ##
535+
writer.write('if instanceof(%s, Number) or instanceof(%s, String): %s' %(target,target,b) )
536+
writer.write('else: %s' %a)
537+
538+
elif self._with_js: ## no operator overloading in with-js mode
510539
a = '%s %s %s' %(target, op, self.visit(node.value))
511540
writer.write(a)
512541

pythonjs/pythonjs_to_dart.py

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -129,6 +129,29 @@ def visit_ClassDef(self, node):
129129
elif b.name == '__setitem__':
130130
b.name = ''
131131
b._prefix = 'void operator []='
132+
elif b.name == '__add__':
133+
b.name = ''
134+
b._prefix = 'operator +'
135+
elif b.name == '__iadd__':
136+
b.name = ''
137+
b._prefix = 'void operator +='
138+
elif b.name == '__sub__':
139+
b.name = ''
140+
b._prefix = 'operator -'
141+
elif b.name == '__mul__':
142+
b.name = ''
143+
b._prefix = 'operator *'
144+
elif b.name == '__div__':
145+
b.name = ''
146+
b._prefix = 'operator /'
147+
148+
elif b.name == '__or__':
149+
b.name = ''
150+
b._prefix = 'operator |'
151+
elif b.name == '__xor__':
152+
b.name = ''
153+
b._prefix = 'operator ^'
154+
132155

133156

134157
line = self.visit(b)
@@ -158,6 +181,24 @@ def visit_ClassDef(self, node):
158181
operator = 'operator []'
159182
elif b.name == '__setitem__':
160183
operator = 'operator []='
184+
elif b.name == '__add__':
185+
operator = 'operator +'
186+
elif b.name == '__sub__':
187+
operator = 'operator -'
188+
elif b.name == '__mul__':
189+
operator = 'operator *'
190+
elif b.name == '__div__':
191+
operator = 'operator /'
192+
elif b.name == '__and__':
193+
operator = 'operator &'
194+
elif b.name == '__or__':
195+
operator = 'operator |'
196+
elif b.name == '__xor__':
197+
operator = 'operator ^'
198+
elif b.name == '__lshift__':
199+
operator = 'operator <<'
200+
elif b.name == '__rshift__':
201+
operator = 'operator >>'
161202

162203
args = [self.visit(a) for a in b.args.args][1:]
163204
args = ','.join(args)
@@ -302,6 +343,8 @@ def visit_Is(self, node):
302343
def _visit_call_helper_instanceof(self, node):
303344
args = map(self.visit, node.args)
304345
if len(args) == 2:
346+
if args[1] == 'Number':
347+
args[1] = 'num'
305348
return '%s is %s' %tuple(args)
306349
else:
307350
raise SyntaxError( args )
Lines changed: 179 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,179 @@
1+
<html>
2+
<head>
3+
<script src="pythonscript.js"></script>
4+
5+
<script type="text/python">
6+
7+
class Vector3:
8+
def __init__(self, x=0, y=0, z=0 ):
9+
self._x = x
10+
self._y = y
11+
self._z = z
12+
13+
def set(self, x,y,z):
14+
self._x = x
15+
self._y = y
16+
self._z = z
17+
18+
@property
19+
def x(self):
20+
return self._x
21+
@x.setter
22+
def x(self, value):
23+
print 'x setter', value
24+
self._x = value
25+
26+
@property
27+
def y(self):
28+
return self._y
29+
@y.setter
30+
def y(self, value):
31+
print 'y setter', value
32+
self._y = value
33+
34+
@property
35+
def z(self):
36+
return self._z
37+
@z.setter
38+
def z(self, value):
39+
print 'z setter', value
40+
self._z = value
41+
42+
43+
def add(self, other):
44+
self.set( self.x+other.x, self.y+other.y, self.z+other.z )
45+
return self
46+
47+
def __add__(self, other):
48+
if instanceof(other, Number):
49+
return Vector3( self.x+other, self.y+other, self.z+other )
50+
else:
51+
return Vector3( self.x+other.x, self.y+other.y, self.z+other.z )
52+
53+
def __iadd__(self, other):
54+
if instanceof(other, Number):
55+
self.addScalar( other )
56+
else:
57+
self.add( other )
58+
59+
def addScalar(self, s):
60+
self.set( self.x+s, self.y+s, self.z+s )
61+
return self
62+
63+
64+
def sub(self, other):
65+
self.set( self.x-other.x, self.y-other.y, self.z-other.z )
66+
return self
67+
68+
def __sub__(self, other):
69+
if instanceof(other, Number):
70+
return Vector3( self.x-other, self.y-other, self.z-other )
71+
else:
72+
return Vector3( self.x-other.x, self.y-other.y, self.z-other.z )
73+
74+
def __isub__(self, other):
75+
if instanceof(other, Number):
76+
self.set( self.x-other, self.y-other, self.z-other )
77+
else:
78+
self.sub( other )
79+
80+
81+
def multiply(self, other):
82+
self.set( self.x*other.x, self.y*other.y, self.z*other.z )
83+
return self
84+
85+
def __mul__(self, other):
86+
if instanceof(other, Number):
87+
return Vector3( self.x*other, self.y*other, self.z*other )
88+
else:
89+
return Vector3( self.x*other.x, self.y*other.y, self.z*other.z )
90+
91+
def __imul__(self, other):
92+
if instanceof(other, Number):
93+
self.multiplyScalar( other )
94+
else:
95+
self.multiply( other )
96+
97+
def multiplyScalar(self, s):
98+
self.set( self.x*s, self.y*s, self.z*s )
99+
return self
100+
101+
def divide(self, other):
102+
self.set( self.x/other.x, self.y/other.y, self.z/other.z )
103+
return self
104+
105+
def divideScalar(self, s):
106+
self.set( self.x/s, self.y/s, self.z/s )
107+
return self
108+
109+
def __div__(self, other):
110+
if instanceof(other, Number):
111+
return Vector3( self.x/other, self.y/other, self.z/other )
112+
else:
113+
return Vector3( self.x/other.x, self.y/other.y, self.z/other.z )
114+
115+
def __idiv__(self, other):
116+
if instanceof(other, Number):
117+
self.divideScalar( other )
118+
else:
119+
self.divide( other )
120+
121+
122+
def __xor__(self, s): ## ^
123+
self.set( self.x^s, self.y^s, self.z^s )
124+
return self
125+
126+
def show_vec(v):
127+
print '-------------'
128+
print v.x
129+
print v.y
130+
print v.z
131+
132+
def main():
133+
n = 1
134+
n += 2
135+
print n
136+
137+
v1 = Vector3(1, 2, 3)
138+
v2 = Vector3(10, 0, 10)
139+
print v1, v2
140+
print 'testing +'
141+
a = v1 + v2
142+
show_vec(a)
143+
144+
print 'testing +='
145+
a += 2.5
146+
show_vec(a)
147+
a += v1
148+
show_vec(a)
149+
150+
print 'testing -='
151+
a -= v1
152+
show_vec(a)
153+
a -= 100
154+
show_vec(a)
155+
156+
print 'testing *'
157+
b = v1 * v2
158+
show_vec(b)
159+
160+
print 'testing *='
161+
b *= 10.0
162+
show_vec(b)
163+
b *= v2
164+
show_vec(b)
165+
166+
print 'testing setters'
167+
b.x = 1
168+
b.y = 2
169+
b.z = 3
170+
171+
172+
173+
</script>
174+
</head>
175+
176+
<body>
177+
<button onclick="main()">click me</button>
178+
</body>
179+
</html>

0 commit comments

Comments
 (0)