1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174
|
# This module is used by the Pmw package system.
# The PmwLoader class can be used to simulate a python module,
# but also supports importing of submodules on demand. This technique
# reduces startup time because Pmw submodules which are not used are
# not loaded.
#
# The PmwLoader class also supports runtime selection of the Pmw
# version(s) to use.
import sys
import os
import string
import types
_PMW_DEF = 'Pmw.def' # Pmw definition file
_BASEMODULE = 'Base' # Name of Base module
class PmwLoader:
def __init__(self, dirpath, instdirs, dirs):
self._dirpath = dirpath
self._instdirs = instdirs
self._dirs = dirs
self._initialised = 0
self._version = string.replace(instdirs[0][4:], '_', '.')
self._alpha_versions = ()
#======================================================================
# Public methods. These methods will be seen as "module methods".
def setversion(self, version):
if self._version == version:
return
if self._initialised:
raise ValueError, 'Cannot change Pmw version after initialisation'
self._version = version
def setalphaversions(self, *alpha_versions):
if self._alpha_versions == alpha_versions:
return
if self._initialised:
raise ValueError, \
'Cannot change Pmw alpha versions after initialisation'
self._alpha_versions = alpha_versions
def version(self, alpha = 0):
if alpha:
return self._alpha_versions
else:
return self._version
def installedversions(self, alpha = 0):
rtn = []
if alpha:
dirs = filter(lambda x: x[:5] == 'Alpha', self._dirs)
dirs.sort()
dirs.reverse()
for dir in dirs:
rtn.append(string.replace(dir[6:], '_', '.'))
else:
for dir in self._instdirs:
rtn.append(string.replace(dir[4:], '_', '.'))
return rtn
#======================================================================
# Private methods
def _getmodule(self,modpath):
__import__(modpath)
mod = sys.modules[modpath]
return mod
def _initialise(self):
searchpath = []
for version in self._alpha_versions:
alphadir = '_Pmw.Alpha_%s.lib' % string.replace(version, '.', '_')
searchpath.append(alphadir)
libdir = '_Pmw.Pmw_%s.lib' % string.replace(self._version, '.', '_')
searchpath.append(libdir)
# Create attributes for the PmwBase classes and functions.
for path in searchpath:
try:
basemodule = self._getmodule(path + '.Pmw' + _BASEMODULE)
break
except ImportError, msg:
if path == searchpath[-1]:
# No PmwBase module found.
raise ImportError, msg
for k,v in basemodule.__dict__.items():
if k[0] is not '_' and type(v) != types.ModuleType:
self.__dict__[k] = v
# Set the Pmw definitions from the Pmw.def file.
dict = {
'_widgets' : {},
'_extraWidgets' : {},
'_functions' : {},
'_modules' : {},
}
for name in dict.keys():
self.__dict__[name] = {}
searchpath.reverse()
for path in searchpath:
pathbit = apply(os.path.join, tuple(string.split(path[5:], '.')))
lpath = os.path.join(self._dirpath, pathbit)
d = {}
execfile(os.path.join(lpath,_PMW_DEF), d)
for k,v in d.items():
if dict.has_key(k):
if type(v) == types.TupleType:
for item in v:
modpath = path + '.Pmw' + item
dict[k][item] = modpath
elif type(v) == types.DictionaryType:
for k1, v1 in v.items():
modpath = path + '.Pmw' + v1
dict[k][k1] = modpath
self.__dict__.update(dict)
self._widgets_keys = self._widgets.keys()
self._extraWidgets_keys = self._extraWidgets.keys()
self._functions_keys = self._functions.keys()
self._modules_keys = self._modules.keys()
self._initialised = 1
def __getattr__(self, name):
if not self._initialised:
self._initialise()
# Beware: _initialise may have defined 'name'
if name in self.__dict__.keys():
return self.__dict__[name]
# The requested attribute is not yet set. Look it up in the
# tables set by Pmw.def, import the appropriate module and
# set the attribute so that it will be found next time.
if name in self._widgets_keys:
# The attribute is a widget name.
mod = self._getmodule(self._widgets[name])
cls = getattr(mod,name)
self.__dict__[name] = cls
return cls
if name in self._functions_keys:
# The attribute is a function from one of the modules.
modname = self._functions[name]
mod = self._getmodule(modname)
func = getattr(mod, name)
self.__dict__[name] = func
return func
if name in self._modules_keys:
# The attribute is a module
mod = self._getmodule(self._modules[name])
self.__dict__[name] = mod
return mod
if name in self._extraWidgets_keys:
# XXX I should import them all, once I've started.
# The attribute is a widget name in a module of another name
modname = self._extraWidgets[name]
mod = self._getmodule(modname)
cls = getattr(mod, name)
self.__dict__[name] = cls
return cls
# The attribute is not known by Pmw, report an error.
raise AttributeError, name
|