X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/e234d4c9b72709629e655b2935a3bf1262eebcb1..1fded56b375bf7a4687af1cdb182899614c1b2a8:/wxPython/distrib/wx_conv.py diff --git a/wxPython/distrib/wx_conv.py b/wxPython/distrib/wx_conv.py new file mode 100644 index 0000000000..1ac2d1b819 --- /dev/null +++ b/wxPython/distrib/wx_conv.py @@ -0,0 +1,220 @@ +""" +Convert modules from the old 'from wxPython.wx import *' style to +the new 'import wx' style. + +Author: dfh@forestfield.co.uk (David Hughes) + + +This should probably go in the tools package and have a startup script +like the others, but I don't think it's ready for prime-time yet. So +just put it in distrib for now so it doesn't get lost... + +--Robin +""" + + +import os, sys, time +import string +t0 = time.time() + + +import wx +print 'length = ', len(wx._newnames) + +for key in ['true', 'True', 'false', 'False']: # use native Python not wx. + if key in wx._newnames: + del wx._newnames[key] + +import wx.calendar, wx.gizmos, wx.glcanvas, wx.grid, wx.help, wx.html, \ + wx.htmlhelp, wx.iewin, wx.ogl, wx.stc, wx.wizard, wx.xrc +import wx.lib +##import wx.lib.activexwrapper, wx.lib.analogclock, wx.lib.anchors, \ +import wx.lib.activexwrapper, wx.lib.anchors, \ + wx.lib.buttons, wx.lib.calendar, wx.lib.ClickableHtmlWindow, \ + wx.lib.colourdb, wx.lib.colourselect, wx.lib.dialogs, \ + wx.lib.ErrorDialogs, wx.lib.evtmgr, wx.lib.fancytext, \ + wx.lib.filebrowsebutton, wx.lib.gridmovers, wx.lib.grids, \ + wx.lib.imagebrowser, wx.lib.imageutils, wx.lib.infoframe, \ + wx.lib.intctrl, wx.lib.layoutf, wx.lib.multisash, \ + wx.lib.popupctl, wx.lib.printout, wx.lib.rcsizer, \ + wx.lib.rightalign, wx.lib.sheet, wx.lib.stattext, \ + wx.lib.throbber, wx.lib.timectrl, wx.lib.wxPlotCanvas, \ + wx.lib.wxpTag +import wx.lib.mixins, wx.lib.editor, wx.lib.colourchooser +import wx.lib.mixins.grid, wx.lib.mixins.imagelist, \ + wx.lib.mixins.listctrl +## wx.lib.mixins.listctrl, wx.lib.mixins.rubberband +import wx.lib.editor.editor, wx.lib.editor.images, wx.lib.editor.selection +import wx.lib.colourchooser.canvas, wx.lib.colourchooser.intl, wx.lib.colourchooser.pycolourbox, \ + wx.lib.colourchooser.pycolourchooser, wx.lib.colourchooser.pycolourslider, wx.lib.colourchooser.pypalette + +wxlist = [] +for kd in wx._newnames.items(): + wxlist.append(kd) +wxlist.sort() + +n = 0 +for item in wxlist: + n += 1 +## print n, item +print 'length = ', len(wx._newnames) +print 'imports completed in ', time.time()-t0, 'secs' + +base_path = 'G:/wxConvert/Test1' +exclude_dir = ( 'wx', 'wx_cc', 'reportlab', 'sqlite') # MUST exclude wx if it is below base_dir, others optional + +other_subs = { 'true': 'True', + 'false': 'False' + } + +punct = string.punctuation.replace('_','') # exclude single underscore +punct = punct.replace('.','') # and period +punct = punct.replace('*','') # and asterisk, all allowed in names +punctable = string.maketrans(punct, ' '*len(punct)) # map punctuation characters to spaces +numfiles = 0 + +#---------------------------------------------------------------------------- + +class AFile: + " file object - collection of properties relating to current instance" + def __init__(self, subsdict): + self.subsdict = subsdict.copy() # dictionary of universal and local substitutions to make + self.importing = [] # list of wx modules being imported + +#---------------------------------------------------------------------------- + +def visit(noargs, thispath, contentlist): + """ Function is called by os walk for every directory in base_path, + including base_path itself. Contentlist is a list of files/dirs in thispath. + Wx conversion function is called for every qualifying file in list + """ + path = thispath + base = 'something' + while base: # check if thispath or a parent is excluded + path, base = os.path.split(path) + if base in exclude_dir: + print 'Excluded:', thispath + return + + for item in contentlist: + pathname = os.path.join(thispath, item) + if os.path.isfile(pathname) and pathname[-3:].lower() == '.py': + wxconvert(pathname) + +def wxconvert(pathname): + """ Scan each line of text in pathname. Replace each occurrence of any key in wx._newnames + dictionary with the content stored under that key + """ + global numfiles + afile = AFile(other_subs) + infile = open(pathname, 'r') + linelist = infile.readlines() + infile.close() + + lnum = 0 + outlist = [] + for line in linelist: + lnum += 1 + tokenlist = line.replace('.__', ' ').translate(punctable).split() # split on white space and punctuation + line, status = checkimports(afile, line, tokenlist) # return line with 'import' modifications + if not status: + print 'Unable to convert line %d in %s' % (lnum, pathname) + break + else: + for key in afile.subsdict: # do other changes first + if line.find(key) >= 0: + line = line.replace(key, afile.subsdict[key]) + for token in tokenlist: # change wx names + if token in wx._newnames: + candidate = wx._newnames[token] + module = candidate[:candidate.rfind('.')] + if module in afile.importing: + line = line.replace(token, candidate) + outlist.append(line) + else: + outfile = open(pathname, 'w') + outfile.writelines(outlist) + numfiles += 1 + print 'Converted:', pathname + outfile.close() + +def checkimports(afile, line, tlist): + """ Scan tokenlist for wxPython import statement. Add to afile.subsdict any + name changes that are necessary for the rest of the current source file. + Add to afile.importing any new import modules + Return a tuple (status, newstring) - + line, possibly modified if an import statmeny + status: 0: unable to handle complexity, 1: OK + """ + aline = line + if len(tlist) == 0: return (aline, 1) + indent = '' + for ch in line: + if ch in string.whitespace: + indent += ' ' + else: + break + + if tlist[0] == 'import': # import module [as name] [module [as name]...] + skip = False + for t in tlist[1:]: + if skip: + skip = False + elif t == 'as': + skip = True + elif t.startswith('wx'): + aline = aline.replace(t, rename_module(afile, t)) + elif (tlist[0] == 'from' and + tlist[1] == 'wxPython' and + tlist[2] == 'import'): # from wxPython import module + if len(tlist) > 4: # ...[as name] [module [as name]...] + return ('', 0) # too complicated + module = rename_module(afile,tlist[-1]) + aline = indent = 'import ' + module + '\n' + elif (tlist[0] == 'from' and + tlist[1].startswith('wxPython') and + tlist[2] == 'import'): # from module import .... + if tlist[-1] <> '*': # ...name [as name] [name [as name]...] + aline = aline.replace(tlist[1], rename_module(afile, tlist[1])) + skip = False + for t in tlist[3:]: + if skip: + skip = False + elif t == 'as': + skip = True + else: + elem = t.split('.') + if elem[-1].startswith('wx'): # remove wx prefix from last element of name + elem[-1] = elem[-1][2:] + afile.subsdict[t] = '.'.join(elem) # and apply to each occurrence in source + else: # from module import * + module = rename_module(afile,tlist[1]) + aline = indent = 'import ' + module + '\n' + return (aline, 1) + +def rename_module(afile, t, type='A'): + """ Substitute wx for wxPython.wx or wx, and wx.foo.bar for wxPython.foo.bar in token + foo.bar => wx.foo.bar is also permitted (from wxPython import foo.bar) + """ + if t in ['wx', 'wxPython.wx']: + module = 'wx' + elif t.startswith('wxPython'): + module = t.replace('wxPython', 'wx') + elif t.startswith('wx'): + module = t + else: + module = 'wx.' + t + if module not in afile.importing: + afile.importing.append(module) + return module + +def main(): + " Convert every file in base_dir and all subdirectories except in exclude_dir list" + + os.path.walk(base_path, visit, None) + print '%d files converted in %.2f seconds' % (numfiles, time.time() - t0) + +#---------------------------------------------------------------------------- + +if __name__ == '__main__': + main()