3 # Modulator - Generate skeleton modules.
5 # The user fills out some forms with information about what the module
6 # should support (methods, objects), names of these things, prefixes to
7 # use for C code, whether the objects should also support access as numbers,
9 # When the user presses 'Generate code' we generate a complete skeleton
12 # Alternatively, the selections made can be save to a python sourcefile and
13 # this sourcefile can be passed on the command line (resulting in the same
16 # Jack Jansen, CWI, October 1994.
21 sys
.path
.append(os
.path
.join(os
.environ
['HOME'],
22 'src/python/Tools/modulator'))
26 from ScrolledListbox
import ScrolledListbox
33 # Check that string is a legal C identifier
36 if not str[0] in string
.letters
+'_':
39 if not c
in string
.letters
+string
.digits
+'_':
43 def getlistlist(list):
47 rv
.append(list.get(i
))
54 self
.main
.master
.title('Modulator: Module view')
55 self
.cmdframe
= Frame(self
.main
, {'relief':'raised', 'bd':'0.5m',
58 self
.objframe
= Frame(self
.main
, {Pack
:{'side':'top', 'fill':'x',
62 self
.check_button
= Button(self
.cmdframe
,
63 {'text':'Check', 'command':self
.cb_check
,
64 Pack
:{'side':'left', 'padx':'0.5m'}})
65 self
.save_button
= Button(self
.cmdframe
,
66 {'text':'Save...', 'command':self
.cb_save
,
67 Pack
:{'side':'left', 'padx':'0.5m'}})
68 self
.code_button
= Button(self
.cmdframe
,
69 {'text':'Generate code...',
70 'command':self
.cb_gencode
,
71 Pack
:{'side':'left', 'padx':'0.5m'}})
72 self
.quit_button
= Button(self
.cmdframe
,
74 'command':self
.cb_quit
,
75 Pack
:{'side':'right', 'padx':'0.5m'}})
77 self
.module
= UI_module(self
)
84 def cb_quit(self
, *args
):
86 if not askyn('You have not saved\nAre you sure you want to quit?'):
90 def cb_check(self
, *args
):
92 self
.module
.synchronize()
93 for o
in self
.objects
:
98 def cb_save(self
, *args
):
100 pycode
= self
.module
.gencode('m', self
.objects
)
104 fn
= askfile('Python file name: ')
113 def cb_gencode(self
, *args
):
115 pycode
= self
.module
.gencode('m', self
.objects
)
119 fn
= askfile('C file name: ')
128 message('An error occurred:-)')
130 genmodule
.write(fp
, m
)
134 def __init__(self
, parent
):
136 self
.frame
= Frame(parent
.objframe
, {'relief':'raised', 'bd':'0.2m',
139 self
.f1
= Frame(self
.frame
, {Pack
:{'side':'top', 'pady':'0.5m',
141 self
.f2
= Frame(self
.frame
, {Pack
:{'side':'top', 'pady':'0.5m',
143 self
.f3
= Frame(self
.frame
, {Pack
:{'side':'top', 'pady':'0.5m',
145 self
.f4
= Frame(self
.frame
, {Pack
:{'side':'top', 'pady':'0.5m',
148 self
.l1
= Label(self
.f1
, {'text':'Module:', Pack
:{'side':'left',
150 self
.name_entry
= Entry(self
.f1
, {'relief':'sunken',
151 Pack
:{'side':'left', 'padx':'0.5m', 'expand':1}})
152 self
.l2
= Label(self
.f1
, {'text':'Abbrev:', Pack
:{'side':'left',
154 self
.abbrev_entry
= Entry(self
.f1
, {'relief':'sunken', 'width':5,
155 Pack
:{'side':'left', 'padx':'0.5m'}})
157 self
.l3
= Label(self
.f2
, {'text':'Methods:', Pack
:{'side':'left',
159 self
.method_list
= ScrolledListbox(self
.f2
, {'relief':'sunken','bd':2,
160 Pack
:{'side':'left', 'expand':1,
161 'padx':'0.5m', 'fill':'both'}})
163 self
.l4
= Label(self
.f3
, {'text':'Add method:', Pack
:{'side':'left',
165 self
.method_entry
= Entry(self
.f3
, {'relief':'sunken',
166 Pack
:{'side':'left', 'padx':'0.5m', 'expand':1}})
167 self
.method_entry
.bind('<Return>', self
.cb_method
)
168 self
.delete_button
= Button(self
.f3
, {'text':'Delete method',
169 'command':self
.cb_delmethod
,
173 self
.newobj_button
= Button(self
.f4
, {'text':'new object',
174 'command':self
.cb_newobj
,
178 def cb_delmethod(self
, *args
):
179 list = self
.method_list
.curselection()
181 self
.method_list
.delete(i
)
183 def cb_newobj(self
, *arg
):
184 self
.parent
.objects
.append(UI_object(self
.parent
))
186 def cb_method(self
, *arg
):
187 name
= self
.method_entry
.get()
190 self
.method_entry
.delete('0', 'end')
191 self
.method_list
.insert('end', name
)
193 def synchronize(self
):
194 n
= self
.name_entry
.get()
196 message('Module name not set')
199 message('Module name not an identifier:\n'+n
)
201 if not self
.abbrev_entry
.get():
202 self
.abbrev_entry
.insert('end', n
)
203 m
= getlistlist(self
.method_list
)
206 message('Method name not an identifier:\n'+n
)
209 def gencode(self
, name
, objects
):
215 for i
in range(len(objects
)):
217 rv
= rv
+ objects
[i
].gencode(oname
)
219 rv
= rv
+ (name
+' = genmodule.module()\n')
220 rv
= rv
+ (name
+'.name = '+`self
.name_entry
.get()`
+'\n')
221 rv
= rv
+ (name
+'.abbrev = '+`self
.abbrev_entry
.get()`
+'\n')
222 rv
= rv
+ (name
+'.methodlist = '+`
getlistlist(self
.method_list
)`
+'\n')
223 rv
= rv
+ (name
+'.objects = ['+string
.joinfields(onames
, ',')+']\n')
230 def __init__(self
, parent
):
233 object_number
= object_number
+ 1
234 self
.num
= object_number
235 self
.vpref
= 'o'+`self
.num`
+'_'
236 self
.frame
= Toplevel(parent
.objframe
)
238 self
.frame
.title('Modulator: object view')
239 # self.frame = Frame(parent.objframe, {'relief':'raised', 'bd':'0.2m',
240 # Pack:{'side':'top',
242 self
.f1
= Frame(self
.frame
, {Pack
:{'side':'top', 'pady':'0.5m',
244 self
.f2
= Frame(self
.frame
, {Pack
:{'side':'top', 'pady':'0.5m',
246 self
.f3
= Frame(self
.frame
, {Pack
:{'side':'top', 'pady':'0.5m',
248 self
.f4
= Frame(self
.frame
, {Pack
:{'side':'top', 'pady':'0.5m',
252 self
.l1
= Label(self
.f1
, {'text':'Object:', Pack
:{'side':'left',
254 self
.name_entry
= Entry(self
.f1
, {'relief':'sunken',
255 Pack
:{'side':'left', 'padx':'0.5m', 'expand':1}})
256 self
.l2
= Label(self
.f1
, {'text':'Abbrev:', Pack
:{'side':'left',
258 self
.abbrev_entry
= Entry(self
.f1
, {'relief':'sunken', 'width':5,
259 Pack
:{'side':'left', 'padx':'0.5m'}})
261 self
.l3
= Label(self
.f2
, {'text':'Methods:', Pack
:{'side':'left',
263 self
.method_list
= ScrolledListbox(self
.f2
, {'relief':'sunken','bd':2,
264 Pack
:{'side':'left', 'expand':1,
265 'padx':'0.5m', 'fill':'both'}})
267 self
.l4
= Label(self
.f3
, {'text':'Add method:', Pack
:{'side':'left',
269 self
.method_entry
= Entry(self
.f3
, {'relief':'sunken',
270 Pack
:{'side':'left', 'padx':'0.5m', 'expand':1}})
271 self
.method_entry
.bind('<Return>', self
.cb_method
)
272 self
.delete_button
= Button(self
.f3
, {'text':'Delete method',
273 'command':self
.cb_delmethod
,
278 self
.l5
= Label(self
.f4
, {'text':'functions:',
281 self
.f5
= Frame(self
.f4
, {Pack
:{'side':'left', 'pady':'0.5m',
283 self
.l6
= Label(self
.f4
, {'text':'Types:',
284 Pack
:{'side':'left', 'padx':'0.5m'}})
285 self
.f6
= Frame(self
.f4
, {Pack
:{'side':'left', 'pady':'0.5m',
288 for i
in genmodule
.FUNCLIST
:
290 self
.f5
.setvar(vname
, 0)
291 b
= Checkbutton(self
.f5
, {'variable':vname
, 'text':i
,
292 Pack
:{'side':'top', 'pady':'0.5m',
293 'anchor':'w','expand':1}})
295 self
.f5
.setvar(self
.vpref
+'new', 1)
298 for i
in genmodule
.TYPELIST
:
299 vname
= self
.vpref
+ i
300 self
.f6
.setvar(vname
, 0)
301 b
= Checkbutton(self
.f6
, {'variable':vname
, 'text':i
,
302 Pack
:{'side':'top', 'pady':'0.5m',
306 def cb_method(self
, *arg
):
307 name
= self
.method_entry
.get()
310 self
.method_entry
.delete('0', 'end')
311 self
.method_list
.insert('end', name
)
313 def cb_delmethod(self
, *args
):
314 list = self
.method_list
.curselection()
316 self
.method_list
.delete(i
)
318 def synchronize(self
):
319 n
= self
.name_entry
.get()
321 message('Object name not set')
323 if not self
.abbrev_entry
.get():
324 self
.abbrev_entry
.insert('end', n
)
325 n
= self
.abbrev_entry
.get()
327 message('Abbreviation not an identifier:\n'+n
)
329 m
= getlistlist(self
.method_list
)
332 message('Method name not an identifier:\n'+n
)
335 self
.f5
.setvar(self
.vpref
+'tp_getattr', 1)
338 def gencode(self
, name
):
340 rv
= rv
+ (name
+' = genmodule.object()\n')
341 rv
= rv
+ (name
+'.name = '+`self
.name_entry
.get()`
+'\n')
342 rv
= rv
+ (name
+'.abbrev = '+`self
.abbrev_entry
.get()`
+'\n')
343 rv
= rv
+ (name
+'.methodlist = '+`
getlistlist(self
.method_list
)`
+'\n')
345 for fn
in genmodule
.FUNCLIST
:
346 vname
= self
.vpref
+ fn
347 if self
.f5
.getvar(vname
) == '1':
349 rv
= rv
+ (name
+'.funclist = '+`fl`
+'\n')
352 for fn
in genmodule
.TYPELIST
:
353 vname
= self
.vpref
+ fn
354 if self
.f5
.getvar(vname
) == '1':
357 rv
= rv
+ (name
+'.typelist = '+`fl`
+'\n')
364 if len(sys
.argv
) < 2:
367 elif len(sys
.argv
) == 2:
368 fp
= open(sys
.argv
[1])
373 sys
.stderr
.write('An error occurred:-)\n')
375 ##genmodule.write(sys.stdout, m)
377 sys
.stderr
.write('Usage: modulator [file]\n')