the instance object as though it were a function. The program is started by a call op-
eration—by its call operator-overloading method, instead of a normally named
method—so that the classes in this module can also be used to generate callback han-
dlers in tkinter-based GUIs. As we’ll see in the upcoming chapters, button-presses in
tkinter invoke a callable object with no arguments; by registering a PortableLauncher
instance to handle the press event, we can automatically start a new program from
another program’s GUI. A GUI might associate a launcher with a GUI’s button press
with code like this:
Button(root, text=name, command=PortableLauncher(name, commandLine))
When run standalone, this module’s selftest function is invoked as usual. As coded,
System blocks the caller until the program exits, but PortableLauncher (really, Spawn or
Fork) and Start do not:
C:\...\PP4E> type echo.py
print('Spam')
input('press Enter')
C:\...\PP4E> python launchmodes.py
default mode...
echo.py
system mode...
echo.py
Spam
press Enter
DOS start mode...
echo.py
As more practical applications, this file is also used in Chapter 8 to launch GUI dialog
demos independently, and again in a number of Chapter 10’s examples, including
PyDemos and PyGadgets—launcher scripts designed to run major examples in this
book in a portable fashion, which live at the top of this book’s examples distribution
directory. Because these launcher scripts simply import PortableLauncher and register
instances to respond to GUI events, they run on both Windows and Unix unchanged
(tkinter’s portability helps, too, of course). The PyGadgets script even customizes
PortableLauncher to update a GUI label at start time:
class Launcher(launchmodes.PortableLauncher): # use wrapped launcher class
def announce(self, text): # customize to set GUI label
Info.config(text=text)
We’ll explore these two client scripts, and others, such as Chapter 11’s PyEdit after we
start coding GUIs in Part III. Partly because of its role in PyEdit, this edition extends
this module to automatically replace forward slashes with backward slashes in the
script’s file path name. PyEdit uses forward slashes in some filenames because they are
allowed in file opens on Windows, but some Windows launcher tools require the
backslash form instead. Specifically, system, popen, and startfile in os require back-
slashes, but spawnv does not. PyEdit and others inherit the new pathname fix of
fixWindowsPath here simply by importing and using this module’s classes; PyEdit
A Portable Program-Launch Framework | 267