Newer
Older
twander / twander.1
.TH twander 1 "TundraWare Inc."


.SH NAME
twander \- File Browser


.SH OVERVIEW
Wander around a filesystem executing commands of your choice on
selected files and directories. If you're new to \'twander\' and want
to know why this program is better and different than whatever you're
using at the moment, take a moment to read the section called 
.B DESIGN PHILOSOPHY 
toward the end of this document first.

Similarly, if this is the first time you've worked with \'twander\',
there is a section towards the end of this document entitled
.B INSTALLING \'twander\'
which describes how the program should be installed.


.SH SYNOPSIS
twander [-cdhqrstv] [startdir]


.SH OPTIONS
.TP
.B startdir
Directory in which to begin. (default: ./)

If this directory does not exist or cannot be opened, \'twander\'
will display an error message and abort.

.TP
.B -c path/name of Configuration File
Specify the location and name of the configuration
file. (default is ~/.twander)

If this file does not exist or cannot be opened, \'twander\' will
display a warning to that effect but continue to run.  This is
reasonable behavior because \'twander\' provides a command to reload
the Configuration File without exiting the program (which you would 
presumably do after fixing the Configuration File problem).

.TP
.B -d debuglevel
Start in debug mode dumping the items specified in the debuglevel.
(default: debuglevel=0/debug off)

\'twander\' is able to selectively dump debugging information to
stdout.  \'debuglevel\' is understood to be a bitfield in which
each bit specifies some kind of debugging information or
behavior.  \'debuglevel\' can be specified in either decimal
or hex (using the form 0x#) formats.  The bits in the bitfield
are defined as follows:

.nf
Bit  Hex Value   Meaning
---  ---------   -------

0    0x001       Dump Internal Options & User-Settable Options 
1    0x002       Dump User-Defined Variables 
2    0x004       Dump Command Definitions 
3    0x008       Dump Key Bindings 
4    0x010       Display, Do Not Execute, Commands When Invoked 
5    0x020       Dump Directory Stack As It Changes 
6    0x040       Dump Command History Stack After Command Executes 
7    0x080       Dump Contents Of Program Memories As They Change 
8    0x100       Reserved/Unused
9    0x200       Reserved/Unused
10   0x400       Reserved/Unused
11   0x800       Dump Requested Debug Information And Exit Immediately
.fi

These bits can be combined to provided very specific debugging
information.  For example, \'-d 0x80f\' will dump (to stdout) all the
Internal Options, User-Settable Options, User-Defined Options, Command
Definitions, and Key Bindings and then terminate the program.

.TP
.B -h
Print help information on stdout.

.TP
.B -q
Quiet mode - suppresses warnings. (default: warnings on)

.TP
.B -r 
Turn off automatic refreshing of directory display. (default: refresh
on)

Normally \'twander\' re-reads and displays the current directory
every few seconds to reflect any changes that might have occurred to
that directory's contents.  This option is useful on slow machines (or
slow X connections) and/or when working with very large directories.
In this situation, the frequent updating of the \'twander\' display
can make the program unacceptably slow and unresponsive.  In this case
you can still force an update manually with the REFRESH function (default
assignment is to the Control-l key).

.TP
.B -t
Turn off quoting when substituting built-in variables. (default: quoting on)

Anytime \'twander\' encounters a reference to one of the built-in
variables which do string replacement (DIR, DSELECTION, DSELECTIONS,
MEM1-12, PROMPT:, SELECTION, SELECTIONS) in a command, it will replace
them with
.B double quoted
strings.  This is necessary because any of these can return values which
have embedded spaces in them.  By quoting them, they can be passed to a
command or script as a single item.  The -t option disables this behavior
and replaces the built-in variable with unquoted literals.

.TP
.B -v
Print detailed version information.


.SH OTHER WAYS TO SET \'twander\' OPTIONS

In addition to these command line options, there are two other ways
you can set \'twander\' program features.  If you prefer, you
can set the command line options via the environment variable,
TWANDER.  That way you don't have to type them in each time you
start the program.  Say you set the environment variable this way
on Unix:

.nf
export TWANDER=-qt
.fi

From then on, every time you run the program, the -q and -t options
would be invoked (No Quoting, No Warnings) just as if you had typed
them in on the command line.

The second way to set these (and MANY  more) program options is 
by setting the appropriate entries in the Configuration File.  This
is covered later in this document.

\'twander\' evaluates options in the following order (from first
to last:

.IP \(bu 4
Internally set default value of options

.IP \(bu 4
Options set in the Configuration File

.IP \(bu 4
Options set in the TWANDER environment variable

.IP \(bu 4
Options set on the command line


.P
This means, for example, that the environment variable overrides a
corresponding setting in the Configuration File, but the command line
overrides the environment variable.  Furthermore, there are many
program options which can 
.B only
be set/changed the Configuration File and are not available in
either the environment variable or on the command line.  

This also means that options set on the command line are not read
until after the Configuration File has been processed.  So, the -q
argument on the command line will not inhibit warnings generated
during the reading of the Configuration File.  This is best done by
adding the statement, "WARN=False" at the top of the Configuration
File.

If the Configuration File is reloaded while the program is running
(see the READCONF key below), any options set in the file will have
the last word.  This allows you to edit the Configuration File and
have your changes reflected in a running instance of \'twander\', but
it also means that the environment variable/command line arguments are
ignored after initial program startup.


.SH KEYBOARD USE

By design, \'twander\' allows you to do almost everything of interest
using only the keyboard. Various \'twander\' features are thus
associated with particular keystrokes which are described below.  It
is also very simple to change the default key assignments with entries
in the Configuration File, also described below.


.SH NOTES ON KEYBOARD ARROW/KEYPAD BEHAVIOR AND TEXT DIALOG EDITS

Generally, the arrow and keypad keys should do what you would expect
on the system in question. On Win32 systems, particularly, there ought
to be no odd arrow/keypad behavior.  

X-Windows is somewhat more problematic in this area.  Just what an
arrow key is "supposed" to do depends on how it's been mapped in your X
server software.  Testing \'twander\' on various X servers showed
quite a bit of variability in how they handled the arrows and keypad.
So ... if you're running in an X Windows universe and arrows or keypad
do nothing, or do strange things, look into your key maps, don't blame
\'twander\'.

There are several features of \'twander\' than will present the user a
text entry dialog.  These include the CHANGEDIR and RUNCMD features as
well as the [PROMPT:...] Built-In Variable (all described below).

Any time you are entering text in such a dialog, be aware that the
text can be edited several ways - You can edit it using the
arrow/keypad editing assignments which are enabled/normal for your
operating system, OR you can use emacs-style commands to edit the
text.  For instance, Control-a, Control-k will erase the text
currently entered in the dialog.


.SH DEFAULT KEYBOARD AND MOUSE BINDINGS

Here, ordered by category, are the default keyboard and mouse
bindings for \'twander\'.  The general format is:

.TP
.B Description (Program Function Name)
.PD 000
Default Key Assignment
.IP
Default Mouse Assignment (if any)
.PD
.P

The "Program Function Name" is the internal variable \'twander\'
uses to associate a particular feature with a particular keystroke
or mouse action.  You can ignore it unless you intend to override
the default assignments.  This use is described below in the
section entitled,
.B Key Binding Statements.

It is important to realize that \'twander\' key-bindings are
.B case-sensitive.
This means that \'Control-b\' and \'Control-B\' are different.
This was a conscious design decision because it effectively
doubles the number of Control/Alt key combinations available
for the addition of future features.

The default bindings chosen for \'twander\' features are all currently
.B lower-case.
If your program suddenly stops responding to keyboard commands,
check to make sure you don't have CapsLock turned on.

.B NOTE:
Some \'twander\' features are doubled on the mouse.  These mouse
button assignments are documented below for the sake of completeness.
However,
.B mouse button assignments cannot be changed by the user,
even in the Configuration File.

.SS General Program Commands

This family of commands controls the operation of \'twander\' itself.

.TP
.B Clear History (CLRHIST)
Control-y

Clears out various program histories including the All Directory list,
the Directory Stack, the Command History, and the last
manually-entered values for CHANGEDIR and RUNCMD.  The 12 Program
Memories are not cleared - they have specially dedicated key bindings
for this purpose.

.TP
.B Decrement Font Size (FONTDECR)
Control-[

Decrease font size.

.TP
.B Increment Font Size (FONTINCR)
Control-]

Increase font size.

These two features allow you to change the display font sizes while 
\'twander\' is running.  But, you may not immediately get the results
you expect.  \'twander\' internally keeps track of separate font
sizes for the main display, the main menu text, and the help menu
text.  When you use the two font sizing commands above, \'twander\'
subtracts or adds 1 to each of these three values respectively.  On
systems like Win32 using TrueType fonts, this works as you would
expect, because every font is effectively available in every size.
However, in systems like X-Windows or Win32 using fixed-size fonts,
you may have to press these keys repeatedly until \'twander\' finds
a font matching the requested size.

This can also cause some parts of the display to change but not
others.  Suppose you are running on X-Windows and have specified that
the main display is use a 12 point font, and that menus and help
should use 10 point font.  Let's also suppose that the next font
available larger than 12 point is 16 point.  If you press FONTINCR
twice, both the menu text and help text will jump to 12 point, but the
main display text will remain unchanged.  Why?  Because pressing
FONTINCR twice tells \'twander\' to set the main display to 14 point
(12+1+1) which does not exist, and the menu and help text to 12 point
(10+1+1) which does exist, so the change is visible.

Reloading the Configuration File (READCONF) will reset the fonts
to either their default values or any font sizes specified in the
Configuration File.

.TP
.B Display Command Menu (MOUSECTX)
Right-Mouse-Button

Displays a list of all available commands in a pop-up menu near the mouse
pointer.  If no commands are defined, this feature does nothing at all.
This means commands can be invoked one of three ways: Directly via the
Command Key defined in the Configuration File, via selection in the
Command Menu at the top of the GUI, or via selection from the Command
Menu.

Win32 users should note that, unlike Windows Explorer, the \'twander\'
Command Menu does not change the set of currently selected items.  It
merely provides a list of available commands.  This allows the
command chosen via the Command Menu to operate on a previously
selected set of items.

.TP
.B Display Directory Menu (MOUSEDIR)
Shift-Right-Mouse-Button

Displays a list of all the directories visited so far in a pop-up menu
near the mouse.  This means that you can navigate to a previously
visited directory in one of two ways: Via a selection in the
Directory Menu at the top of the GUI or via a selection from
this pop-up menu.

.TP
.B Display History Menu (None - Derived internally)
Control-Shift-Right-Mouse-Button

Displays a list of all commands executed so far (including those
entered manually) in a pop-up menu near the mouse pointer.  If the
Command History is empty, this command does nothing.  This means you
can repeat a previously entered command via the History Menu or this
mouse command.  (You can also repeat the last manually entered command
by pressing RUNCMD - it will preload its text entry area with the last
command you entered by hand.)

.TP
.B Quit Program (QUITPROG)
Control-q

Exit the program.

.TP
.B Re-Read Configuration File (READCONF)
Control-r

Re-read the Configuration File.  This allows you to edit the
Configuration File while \'twander\' is running and then read your
changes in without having to exit the program.  This is handy when
editing or changing Command Definitions.  However, if you edit the
Configuration File and introduce an error, \'twander\' will terminate
when you try to re-read it (just as it will if you try to start the
program with a bad Configuration File).

.TP
.B Refresh Display (REFRESH)
Control-l

Re-read the current directory's contents and display it.  This is most useful
if you have turned off automatic directory refreshing with the -r command
line flag.  

.TP
.B Toggle Details (TOGDETAIL)
Control-t

Toggle between detailed and filename-only views of the directory.

.TP
.B Toggle \'win32all\' Features (TOGWIN32ALL)
Control-w

As described later in this document, \'twander\' provides enhanced
features for Win32 users who also install Mark Hammond's \'win32all\'
extensions for Python on Win32.   This key binding will toggle those
advanced features on- and off.  This is useful if you happen to
be examining a very large directory.  The \'win32all\' features,
while handy, can be computationally expensive and make updates of
a directory with many entries somewhat slow.  This toggle is provided
as a means to temporarily disable the advanced features when viewing
such a directory.

.SS Directory Navigation

This family of commands controls movement between directories.  If at any point,
you attempt to navigate into a directory that does not exist or which
does not have appropriate permissions, \'twander\' will issue an appropriate
message, and remain in the original directory where the request was issued.
This is
.B unlike
the case of a non-existent or unreadable directory specified when the program
is first started.  In that case, \'twander\' reports the error and aborts.

.TP
.B Change Directory (CHANGEDIR)
Control-x

This is a shortcut that allows you to directly move to a new directory/path -
i.e., Without having to navigate to it.

Unless you have set the MAXDIR option to 0, CHANGEDIR keeps track of
your last manually entered directory and presents it as a default when
you press CHANGEDIR again.  You can then move to that directory, edit
the string to specify another directory, or delete it and enter an
entirely new directory.  Directories can be edited with either the
arrow and keypad keys defined on your system or by emacs editing
commands like Control-a, Control-k, Control-e, and so forth.

.TP
.B Go To Home Directory (DIRHOME)
Control-h

If the "HOME" environment variable is defined on your system, this will move
you to that directory.  If the "HOME" environment variable is not defined,
this command will move to the original starting directory.

.TP
.B Go Back One Directory (DIRBACK and MOUSEBACK)
.PD 000
Control-b
.IP
Control-DoubleClick-Left-Mouse-Button
.PD

\'twander\' keeps track of every directory visited and the order in
which they are visited.  This command allows you to move back
successively until you get to the directory in which you started.
This feature is implemented as a stack - each "backing up" removes
the directory name from the visited list.  The "Directory" menu (see
.B MENU OPTIONS
below) implements a similar feature in a different way and keeps track of
all directories visited regardless of order, never discarding any entry.

.TP
.B Go To Root Directory (DIRROOT)
Control-j

Go to the root directory.

.TP
.B Go To Starting Directory (DIRSTART)
Control-s

Go back to the original directory in which \'twander\' was started.

.TP
.B Go Up To Parent Directory (DIRUP and MOUSEUP)
.PD 000
Control-u
.IP
Control-DoubleClick-Right-Mouse-Button
.PD

Move to the parent of the current directory ("..").

.SS Selection Keys

This family of commands controls the selection of one or more (or no)
items in the current directory.

.TP
.B Select All Items (SELALL)
Control-Comma

Select every item in the current directory.  The ".." entry at
the top of the directory listing is not included. (We almost
never want to include the parent directory when issuing a
command on "everything in this directory".  If you do wish
to include the "..", do the SELALL command first, then click
on ".." while holding down the Control key.)

.TP
.B Invert Current Selection (SELINV)
Control-i

Unselects everything which was selected and selects everything which
was not.  As with SELALL, and for the same reason, the ".." entry is
never selected on an inversion.


.TP
.B Unselect All Items (SELNONE)
Control-Period

Unselect everything in the current directory.

.TP
.B Select Next Item (SELNEXT)
Control-n

Select next item down in the directory.

.TP
.B Select Previous Item (SELPREV)
Control-p

Select previous item up in the directory.

.TP
.B Select Last Item (SELEND)
Control-e

Select last item in the directory.

.TP
.B Select First Item (SELTOP)
Control-a

Select first item in the directory.  This will always be the
".." entry, but it is a quick way to get to the first part of
a very long directory listing which does not all fit on-screen.
.PP

The mouse can also be used to select one or more items.  A
single-click of the left mouse button selects a particular item.
Clicking and dragging selects an adjacent group of items.  Clicking an
item and then clicking a second item while holding down the "Shift"
key also selects an adjacent group of items.  Finally, a group
non-adjacent items can also be selected.  The first item is selected
with a single left mouse button click as usual.  Each subsequent
(non-adjacent) item is then selected by holding down the "Control"
key when clicking on the item.

.SS Scrolling Commands

If a given directory's contents cannot be displayed on a single
screen, \'twander\' supports both vertical and horizontal scrolling
via scrollbars.  This capability is doubled on the keyboard with:

.TP
.B Scroll Page Down (PGDN)
Control-v

Scroll down one page in the directory listing.

.TP
.B Scroll Page Up (PGUP)
Control-c

Scroll up one page in the directory listing.

.TP
.B Scroll Page Right (PGRT)
Control-g

Scroll to the right one page width.

.TP
.B Scroll Page Left (PGLFT)
Control-f

Scroll to the left one page width.

.SS Command Execution Options

This family of commands causes \'twander\' to actually
attempt to execute some command you've chosen:

.TP
.B Run Arbitrary Command (RUNCMD)
Control-z

This is a shortcut that allows you to run any command you'd like
without having to define it ahead of time in the Configuration File.
It is more-or-less like having a miniature command line environment at
your disposal.

You may enter a number of different things in the RUNCMD dialog.  You
may type literal text or refer to any of the variable types
(User-Define, Environment, or Built-In) supported by \'twander\' just
as you do in writing Command Definitions (see below).  This makes
it easy to enter complex commands without having to type everything
literally.  For example, if you would like to copy all the currently
selected files to a new directory, press RUNCMD and enter (on Unix):

.nf
cp [SELECTIONS] newdir
.fi

\'twander\' understands the variable reference syntax here just as it
does in a Command Definition.  This is also real handy so you don't
have to remember the exact syntax for environment variables (and how
it differs) across Unix and Win32.  Assuming the EDITOR environment
variable is set, for example, this command works the same on both
systems:

.nf
[$EDITOR] [SELECTIONS]
.fi

Unless you have set the MAXHIST option to 0, RUNCMD keeps track of
your last manually entered command and presents it as a default when
you press RUNCMD again.  You can then run the command again exactly
as you last entered it, you can modify it before running the command
again, or you can delete it and enter an entirely new command.  Commands
can be edited with either the arrow and keypad keys defined on your
system or by emacs editing commands like Control-a, Control-k,
Control-e, and so forth.

Also see the section below entitled,
.B Program Option Statements,
to understand the CMDSHELL option.  This option
greatly simplifies running command-line programs from RUNCMD so
their output can been seen in a GUI window.  This is particularly
handy on Unix.


.TP
.B Run Selected File / Move To Selected Directory (SELKEY and MOUSESEL)
.PD 000
Return (Enter Key)
.IP
DoubleClick-Left-Mouse-Button
.PD

If the selected item is a Directory, \'twander\' will move into
that directory when this command is issued.  If the selected item
is a file, \'twander\' will attempt to execute it.  Whether or not
the file is actually executed depends on how the underlying operating
system views that file.  

In the case of Unix-like operating systems, the execute permission
must be set for the user running \'twander\' (or their group) for the
file to be executed.

On Win32, the file will be executed if the user has permission to do
so
.B and
that file is either executable or there is a Windows association
defined for that file type.  For example, double-clicking on a
file ending with ".txt" will cause the file to be opened with
the \'notepad\' program (unless the association for ".txt" has
been changed).

If \'twander\' determines that it is running on neither a Unix-like
or Win32 system, double-clicking on a file does nothing.

.TP
.B Run User-Defined Command
User-Defined (Single Letter) Key

Each command defined in the Configuration File has a Command Key
associated with it.  Pressing that key will cause the associated
command to be run.  If no command is associated with a given
keystroke, nothing will happen when it is pressed.

.SS Program Memories

If you've used GUIs before, you're probably familiar with the idea
of a program "Clipboard" - a temporary holding area which is used when
cutting, copying, and pasting files.  This is a good idea, but has
several limitations.  First, most systems only have a 
.B single clipboard.
It would be mighty handy to have muliple Clipboard-like storage
areas for keeping track of several different operations at once.
Secondly, when you copy or paste something to a  conventional Clipboard,
.B its old contents get overwritten.
There is no way to keep appending items to the Clipboard.
Finally, items usually can only be cut or copied to the Clipboard
.B from the current directory.
It would be nice if we could not only keep adding things to the
Clipboard, but be able to do so as we navigate around the filesystem.

\'twander\' addresses these concerns by means of 12 separate "Program
Memories".  As you use \'twander\', you can add (append) the names of
any directories or files in the currently viewed directory by
selecting them and then using the appropriate \'twander\' MEMSETx key
(see below).  To take advantage of this feature, you write Command
Definitions (or manually issue a command via the RUNCMD key) which
reference the contents of a Program Memory using one of the [MEMx]
Built-In Variables.  (See the section below on Built-In Variables for
more details in how to apply Program Memories).

\'twander\' provides key combinations for selectively setting and
clearing particular Program Memories as well as a key combination
for clearing all Program Memories in a single keystroke:

.TP
.B Clear Selected Program Memory (MEMCLR1 - MEMCLR12)
Control-F1...Control-F12

Clear (empty) the selected Program Memory.

.TP
.B Clear All Program Memories (MEMCLRALL)
Control-m

Clear (empty) all 12 Program Memories at once.

.TP
.B Set Selected Program Memory (MEMSET1 - MEMSET12)
Alt-F1...Alt-F12

Append the names of the currently selected files and directories to
the Program Memory desired.  More specifically, append
.B the full pathname
of each selected directory or path to that Program Memory.


.SH MENU OPTIONS

Although \'twander\' is primarily keyboard-oriented, several
menu-based features are also implemented to make the program more
convenient to use.  These menus appear at the top of the \'twander\'
display window, above the directory listing.

A menu can be invoked in one of several ways.  You can click on it,
you can press its associated "Accelerator Key" combination, or you can
use the "Mouse Shortcut" to cause a copy of the menu to pop-up near
the mouse pointer.  The Accelerator Keys are shown in
parenthesis next to the menu names below and the Mouse Shortcuts are
similarly shown below in square brackets.

The first item in each menu is a dashed line ("----") which indicates
that it is a "tearoff" menu.  Clicking on the dashed line will detach
the menu from \'twander\' allowing it to be placed anywhere on screen.
Even when detatched, these menus remain current and in-sync with
\'twander\' as it continues to run.  You can also tear off multiple
instances of these menus if you'd like copies of them at several
locations on the screen simultaneously.

On Win32 systems, if a menu gets too long to physically fit on screen,
up- and down- scrolling arrows automatically appear at the top-
and bottom of the menu respectively.  This is not a feature of the
Unix Tk implementation, so menus which grow too large are simply 
truncated to fit the screen on Unix-like systems.  As described in
the following paragraphs, \'twander\' provides some options to
limit the size of the Directory and History menus especially, for this
reason.

.SS Commands Menu (Alt-c) [Right-Mouse-Button]

Every command defined in the Configuration File is listed in this menu
by its Command Name.  The association Command Key is also shown in
parenthesis.  Clicking on an item in this menu is the same as invoking
it from the keyboard by its Command Key.  This is a convenient way
to invoke an infrequently used command whose Command Key you've
forgotten.  It is also handy to confirm which commands are defined
after you've edited and reloaded the Configuration File.  The commands
are listed in the order in which they are defined in the configuration
file. This allows most frequently used commands to appear at the top
of the menu by defining them first in the Configuration File.  If no
commands are defined, either because the Configuration File contains
no Command Definitions or because the Configuration File cannot
be opened for some reason, the Commands Menu will be disabled
(grayed out).

.SS Directories Menu (Alt-d) [Shift-Right-Mouse-Button]

\'twander\' keeps track of every directory visited.  The previously
described command to move "Back" one directory allows directory navigation
in reverse traversal order - you can back up to where you started.
However, this feature "throws away" directories as it backs up, sort
of like an "undo" function.  

The "Directories" menu provides a slightly different approach to the
same task.  It keeps permanent track of every directory visited and
displays that list in sorted order.  This provides another way to move
directly to a previously visited directory without having to manually
navigate to it again, back up to it, or name it explictly using the
Change Directory command.

There are two user-settable options associated with the Directory
Menu.  MAXDIR specifies the maximum number of visited directories
to
.B display in the menu.
This defaults to 32 as is intended as a way to keep the menu
size reasonable.  If you set MAXDIR=0, it means you are
disabling this menu feature altogether as well as disabling
the tracking of the last manually entered directory via
the CHANGEDIR key (default: Control-x).

MAXDIRBUF specifies how many directories \'twander\' keeps track
of internally, no matter how many are actually displayed.  It defaults
to 250.

In summary, the Directory Menu shows the last MAXDIR directories
visited in alphabetically sorted order (unless you change MAXDIRBUF to
be smaller than MAXDIR). "Visited", in this case, is stretching things
a bit. All Directory Shortcut (see below) locations are preloaded into
the Directory Menu when the program starts even though they have not
yet actually been visited.

The Directory Menu is emptied and grayed out when you press the
CLRHIST key (default: Control-y).

.SS History Menu (Alt-h) [Shift-Control-Right-Mouse-Button]

\'twander\' keeps track of every command you attempt to execute,
whether it is an invocation of a Command Definition found in the
Configuration File or a manually entered command via the RUNCMD key
(default: Control-z).  This is done whether or not the command is
successfully executed.

This feature provides a quick way to re-execute a command you've
previously run.  When you select a command to run this way,
a dialog box is opened, giving you an opportunity to edit
the command before running it again.

There are two user-settable options associated with the History
Menu.  MAXHIST specifies the maximum number of previously run commands
to
.B display in the menu.
This defaults to 32 as is intended as a way to keep the menu
size reasonable.  If you set MAXHIST=0, it means you are
disabling this menu feature altogether as well as disabling
the tracking of the last manually entered command via
the RUNCMD key.

MAXHISTBUF specifies how many previously-run commands \'twander\'
keeps track of internally, no matter how many are actually displayed.
It defaults to 250.

One other point of clarification is in order here.  If you run
one of the commands defined in your Configuration File, it is
stored in the History
.B after all variable substitutions have been made.
But, manually entered commands are stored in the History
.B literally as typed -
i.e., Without variable substitution.  This allows you easily reuse a
manually entered command in another directory or context.
(Presumably, Command Definitions in the Configuration File are written
in such a way so as to be useful across many different directories and
contexts.  Running such a command again is simply a matter of pressing
its associated letter key once more.  By storing the resolved version
of the command in the History, you can see what such a command
actually did.)


The History Menu is emptied and grayed out when you press the
CLRHIST key (default: Control-y).

.SS Help Menu (Alt-l) [No Mouse Shortcut]

This menu provides information about various internal settings of
\'twander\' including User-Defined Variables, Command Definitions,
Internal Program Variables, User-Settable Options, Keyboard
Assignments, and Directory Shortcuts.  It also has an About feature
which provides version and copyright information about the program.

For the most part, this help information should fit on screen easily.
However, very long Command Definitions will probably not fit on-screen
once User-Defined and Environment Variables have been substituted.  In
this case, if you are curious about just how \'twander\' is
interpreting your Command Definitions, invoke the program with the
relevant debug bit turned on and watch the output on stdout as
\'twander\' runs.


.SH THE \'twander\' CONFIGURATION FILE

Much of \'twander\'s flexibility comes from the fact that it is
a
.B macro-programmable user interface.
The program itself does little more than provide a way to navigate
around a filesystem.  It must be configured (programmed) to actually
do something with the files you specify.  This is done via a
"Configuration File".  This file is also used to set program options
and change keyboard assignments.  Although the program will run
without a Configuration File present, it will warn you that it is
doing so with no commands defined.


.SH LOCATION OF CONFIGURATION FILE

By default, the program expects to find configuration information in
.B $HOME/.twander
but you can override this with the -c command line option. (Recommended
for Win32 systems - see the section below entitled,
.B INSTALLING \'twander\'
)

Actually, \'twander\' can look in a number
of places to find its Configuration File.  It does this using
the following scheme (in priority order):

.IP \(bu 4
If the -c argument was given on the command line, use this argument
for a Configuration File.

.IP \(bu 4
If -c was not given on the command line, but the HOME environment
variable is set, look for the a Configuration File as $HOME/.twander.

.IP \(bu 4
If the HOME environment variable is not set
.B and
a -c command line argument was not provided, look
for a file called ".twander" in the directory from which
\'twander\' was invoked.


.SH CONFIGURATION FILE FORMAT

\'twander\' Configuration Files consist of freeform lines of text.
Each line is considered independently - no configuration line may
cross into the next line.  Whitespace is ignored within a line as are
blank lines.

There are several possible legal lines in a \'twander\' Configuration
File:

.nf
Comments
Program Option Statements
Key Binding Statements
Directory Shortcut Statements
Variables And Command Definitions
.fi

(See the ".twander" file provided with the program distribution
for examples of valid configuration statements.)

Everything else is considered invalid.  \'twander\' will respond with
errors or warnings as is appropriate anytime it encounters a problem
in a Configuration File.  An error will cause the program to
terminate, but the program continues to run after a warning.  For the
most part, \'twander\' tries to be forgiving and merely ignores
invalid configuration statements (after an appropriate warning).  It
only declares an error when it cannot continue.  This is both true
when the program initially loads as well as during any subsequent
Configuration File reloads initiated from the keyboard while running
\'twander\'.

The following sections describe each of the valid Configuration
File entires in more detail.

.SS Comments

A comment is begun with the "#" string which may be placed anywhere on a
line.  Comments may appear freely within a Configuration File.
\'twander\' strictly ignores everything from the "#" to the end of the
line on which it appears without exception.  This means that "#"
cannot occur anywhere within a User-Defined Variable Definition, Key
Binding Statement, or Command Definition (these are described below).
Comments
.B can
be placed on the same line to the right of such statements.

It is conceivable that the "#" character might be needed in the 
Command String portion of a Command Definition.  \'twander\'
provides a Built-In Variable, [HASH], for exactly this purpose.
See the section below entitled,
.B Variables And Command Definitions,
for a more complete description.

.SS Program Option Statements

Many of \'twander\'s internal program defaults can be overriden in the
Configuration File using Program Option statements.  These statements
look just like User-Defined variables except \'twander\' recognizes
the variable name as a program option rather than an arbitrary
variable.  Program Option Statements thus take the form:

.nf
Option Name = Option Value
.fi

The Option Name is case-sensitive and must be entered exactly as
described below.  For instance, \'twander\' understands
"AUTOREFRESH" as a program option, but will treat "AutoRefresh"
as a User-Defined Variable.

.SS Key Binding Statements

No program that runs in many operating environments can satisfy 
everyone's (anyone's!) idea of what the "correct" key bindings
should be.  An emacs user, vi user, BSD user, and Windows user
are going to differ considerably on what keys should be bound
to what feature.

This feature is available only for
.B Keyboard Assignments.
Mouse Button Assignments may not be changed by the user.  An attempt
to do so in the Configuration File will cause \'twander\' to display a
warning and ignore the offending line.

It is not difficult to override the default keyboard bindings by
adding entries in the Configuration File.  Doing so requires some
familiarity with how Tkinter names keystrokes.  Good resources for
learning this exist abundantly on the Internet, among them:

.nf
http://www.pythonware.com/library/tkinter/introduction/index.htm
http://www.nmt.edu/tcc/help/pubs/lang.html
http://www.cs.mcgill.ca/~hv/classes/MS/TkinterPres/
.fi

(As an aside - Tkinter is nothing more than a Python interface to
the Tcl/Tk windowing system.  The "real" naming conventions for
keystokes can be found in the many sources of Tk documentation,
both in print and on the Internet.)

Keyboard binding assignments look just like local variable definitions
in the Configuration File.  (The \'twander\' Configuration File parser
automatically distinguishes between Key Binding Statements and User-Defined
Variables.  This means you can never use one of the program
function names as one of your own variable names.) Key Binding
Statements thus take the form:

.nf
Program-Function-Name = Tkinter-Keystroke-Name
.fi

Changing the default bindings is therefore nothing more than a matter
of assigning the appropriate Program Function Name (found in
parenthesis next to the description in the default descriptions above)
to the desired keystroke.  

Examples of all the default key bindings are shown as comments in the
".twander" example Configuration File supplied in the program
distribution.  The easiest way to rebind a particular function is to
uncomment the relevant line and change the right side of the
assignment to the new key you'd like to use.  More detailed
instructions on what to do are found in the example ".twander" file
itself.

It is important to observe several rules when rebinding keys:

.IP \(bu 4
It is best if keyboard navigation commands are all Control or Function
keys.  If you assign a navigation or selection function to a single
keystroke, it may conflict with a user-defined command.  If you assign
it to a keypad/special key it may conflict with that key's normal GUI
behavior.

.IP \(bu 4
The Tkinter keynames should placed on the right side of the "=" symbol
.B without any quotation marks.

.nf
So, this is correct:    QUITPROG = <F3>

But, this is not:       QUITPROG = '<F3>'
.fi

.IP \(bu 4 
The Program Function Name variables (the left side of the assignment)
may not be used as names for your own user-defined variables elsewhere
in the Configuration File.  In fact, \'twander\' will never even
recognize such an attempt.  For example, suppose you try to do this:

.nf
QUITPROG = something-or-other
.fi

Because you want to be able to reference [QUITPROG] in a subsequent
Command Definition.  \'twander\' will actually interpret this as just
another key binding command, in this case binding the program function
QUITPROG to "something-or-other" - probably not what you intended.
Moreover, if you have a Command String somewhere with [QUITPROG] in it,
\'twander\' will declare and error and abort because it has no
User-Defined variable of that name in its symbol table.

.IP \(bu 4
When you're done making changes to the Configuration File, be sure to
either restart the program or reload the Configuration File to assign
the new bindings.

.IP \(bu 4
Be aware that \'twander\' does no sanity testing on the assignments
you change.  If you assign a particular \'twander\' function to
an illegal or silly key string, the program will probably blow-up
spectacularly.  At the very least, that program feature will probably
be unusable, even if \'twander\' manages to run.

.SS Directory Shortcut Statements



.SS Variables And Command Definitions

Most programs "ship from the factory" with a pre-defined
set of features or commands.  \'twander\' comes with
.B no built-in commands!
Instead, it comes with a mechanism which allows you to specify your
own
.B Command Definitions.
By means of a simple and very powerful macro lanuage, you "program"
\'twander\' and equip it with commands of your own choosing.  For
example, you might define commands to copy, delete, edit, and move the
files or directories you choose.  Perhaps you have a specialized shell
script for doing backups.  It's a simple matter to write a \'twander\'
Command Definition that will pass the names of the files and
directories you've selected to that backup script.  You might combine
this with \'twander\'s Program Memory feature to keep a running list
of the files and directories you want to backup and then finally issue
the backup command when you're ready.  Best of all, commands you 
define this way are always a single keystroke.  This means that
once you've programmed \'twander\' to suit your needs, actually using
it is very fast and convenient.

Command Definitions are built out of literal text and may also have
any combination of three variable types: User-Defined Variables,
Environment Variables, and Built-In Variables.

.SS User-Defined Variables And Environment Variables

User-Defined Variables are defined using the syntax:

.nf
Variable-Name = Replacement-String
.fi

Environment Variables are referenced using the syntax:

.nf
[$VARIABLE]
.fi

Say we have a configuration line like this,

.nf
EDITOR = emacs blah blah blah blah
.fi

Later on, when defining a command, instead of typing in "emacs blah
blah blah blah", you can just refer to the variable [EDITOR] - the
brackets indicate you are
.B referring
to a previously defined variable.

Similarly, suppose you have an environment variable called "EDITOR"
which indicates your preferred editing program.  Our definition
could thus become:

.nf
EDITOR = [$EDITOR] blah blah blah blah
.fi

Why bother with this?  Because it makes maintaining complex
Configuration Files easier.  If you look in the example ".twander"
Configuration File provided in the program distribution, you will see
this is mighty handy when setting up complex "xterm" sessions, for
example.

Here are several other subtleties regarding User-Defined Variables:

.IP \(bu 4
\'twander\' variable definitions are nothing more than a
string substitution mechanism.  Suppose you have a variable
definition that refers to another variable:

.nf
NewVar = somestring [OldVar]
.fi

It is important to realize that this only means: "If you encounter
the string \'[NewVar]\' 
.B in a subsequent Command Definition,
replace it with the string \'somestring [OldVar]\'.

In other words,
no evaluation of the right side of the expression takes 
place when a variable is 
.B defined.
Evaluation of a variable only takes place when the variable is
.B referenced
(in the Command String portion of a Command Definition).  The Command
Definition parser will continue to dereference variable names until
they are all resolved or it has reached the maximum nesting level (see
next bullet).


.IP \(bu 4
User-Defined Variables may be
.B nested
up to 32 levels deep.  You can have constructs like:

.nf
Var1 = Foo
Var2 = Bar
FB = [Var1][Var2]
.fi

Later on (when defining some command) when \'twander\' runs into the
variable reference [FB], it will keep substituting variables until all
[...] references have been resolved or it hits the nesting limit (32).
This limit has to be imposed to catch silly things like this:

.nf
Var = a[Var]
.fi

This recursive definition is a no-no and will be cause \'twander\'
to generate an error while parsing the Configuration File and then
terminate.

Your variable definitions can also nest other kinds of variables
(Environment and Built-Ins).  So, constructs like this are perfectly
OK:

.nf
Var1 = [$PAGER]
Var2 = command-arguments
V    = [Var1]  [Var2]  [DSELECTION]
.fi

.IP \(bu 4
In the example above, notice that since the right-hand side of
User-Defined Variables is literally replaced, we have to make sure
there is space between the various variable references.  If we used
[Var1][Var2][DSELECTION] we would get one long string back instead
of a command with arguments and a list of selected items.

.IP \(bu 4
Variables must be
.B defined before they are referenced
(in a Command Definition).  You can, however, include not-yet defined
variable name in another User-Variable Definition so long as all these
variable are defined by the time they appear in a Command String.  The
following is OK because all variables are defined by the time they
are actually needed:

.nf
Var1 = foo
Var2 = [Var3]    # This is just a string substitution, not a reference
Var3 = bar
MyVar = [Var1][Var2]

# Now comes the Command Definition
# If we put this before the Variable Definitions above,
# it would be an error.

x mycommand [MyVar]
.fi

.IP \(bu 4
Variable Names are case-sensitive - [EDITOR], [Editor],
and [editor] all refer to different variables.

.IP \(bu 4
The "#" character cannot be used in either the variable name
or the replacement string since doing so begins a comment.

.IP \(bu 4
The "=" is what separates the Variable Name from the replacement
string.  Therefore, the "=" cannot ever be part of a Variable Name.  A
Variable Name cannot begin with "$" (see next bullet).  Other than
these minor restrictions, both Variable Names and Replacement
Characters can be any string of characters of any length.  Good
judgment would suggest that Variable Names should be somewhat
self-descriptive and of reasonable length - i.e., Much shorter than
the replacement string!

.IP \(bu 4
A Variable Name must never begin with "$".  This is because a Command
Definition containing a string in the form [$something] is understood
by \'twander\' to be a reference to an
.B Environment Variable,
named "something". If you do this:

.nf
$MYVAR = some-string
.fi

You will never be able to subsequently reference it because,
[$MYVAR] tells \'twander\' to look in the current environment,
not its own symbol table to resolve the reference.  However, note
that "$" symbol may appear anywhere else but the first character
of a variable name.  So, for example, MY$VAR is fine.

.IP \(bu 4
Variable Names may not be redefined.  This means you can only define a
given Variable Name once per Configuration File.  It is also
considered a variable redefinition if you try to use a variable name
which matches either one of the Built-In Variables (used in Command
Definitions) or one of the Program Function Names (used for Key
Bindings).

.SS Command Definitions

The heart of the \'twander\' configuration process is creating
of one or more 
.B Command Definitions.
These definitions are the way user-defined commands are added to a
given instance of \'twander\'.  A Command Definition consists of three
fields separated by whitespace:

.nf
Command-Key  Command-Name  Command-String
.fi

The
.B Command Key
is any single character which can be typed on the keyboard.  This is
the key that will be used to invoke the command from the keyboard.
Command Keys are case-sensitive.  If "m" is used as a Command Key, "M"
will not invoke that command.  Command Keys must be unique within a
given Configuration File.  \'twander\' will declare an error and
refuse to run if it sees two Command Definitions with the same Command
Key in a given Configuration File.  A Command Key can never be "#"
which is always understood to be the beginning of a comment.

The
.B Command Name
is a string of any length containing any characters.  This is the name
of the command which is used to invoke the command from the Command
Menu.  Command Names are case-sensitive ("command" and "Command" are
different names), but they are not required to be unique within a
given Configuration File.  That is, two different Command Definitions
may have identical Command Names associated with them, though this is
not ordinarily recommended.

The
.B Command String
is any arbitrary string which is what \'twander\' actually tries to
execute when the command is invoked.

.SS A Simple Command Definition

In its simplest form, a Command Definition looks like this:

.nf
# A simple Command Definition

m  MyMore  more somefile
.fi

This command can be invoked pressing the "m" key on the keyboard or
selecting the "MyMore" entry from the Command Menu.  Either way,
\'twander\' will then execute the command, "more somefile".  

The problem is that this command as written actually will not give you
the result you'd like (...well, on X-Windows - is does work on Win32
as written).  (For more details on why, see the
.B GOTCHAS
section below.)  It turns out that starting a non-GUI program like
\'more\' in a new window needs some extra work.  What we want to do
is run \'more\' inside a copy of \'xterm\'.  Now our command looks like
this:

.nf
# Our command setup to run as a GUI window

m MyMore xterm -l -e more somefile
.fi

.SS User-Defined Variables In A Command String

The last example works quite nicely.  But, we're probably going to end up
using the string "xterm -l -e" over and over again for any
shell commands we'd like to see run in a new window.  Why not create
a User-Defined Variable for this string so we can simplify its use
throughout the whole Configuration File?  Now, our command looks
like this:

.nf
# Our command enhanced with a User-Defined Variable.
# Remember that the variable has to be defined *before*
# it is referenced.

XTERM = xterm -l -e                 # This defines the variable
m MyMore [XTERM] more somefile      # And the command then uses it
.fi

.SS Environment Variables In A Command String

This is all very nice, but we'd really like a command to be generic
and be easily used by a variety of users.  Not everyone likes the
"more" program as a pager.  In fact, on Unix-like systems there is an
environment variable ($PAGER) set by each user which names the paging
program that user prefers.  We can refer to environment variables just
like any other variable as explained previously.  Now our command
looks like this:

.nf
# Our command using both a User-Defined Variable and 
# an Environment Variable to make it more general

XTERM = xterm -l -e
m MyMore [XTERM] [$PAGER] somefile
.fi

.SS Built-In Variables In A Command String

It would also be really nice if the command applied to more than just
a single file called "somefile".  The whole point of \'twander\'
is to allow you to use the GUI to select one or more directories
and/or files and have your Command Definitions make use of those
selections.  \'twander\' uses a set of
.B Built-In Variables
to communicate the current directory and user selections to the
any commands you've defined.  Built-In Variables are referenced
just like User-Defined Variables and Environment Variables and
may be inserted any appropriate place in the Command String.
In our example, we probably want the command to pickup whatever
item the user has selected via the GUI and examine that item
with our paging program.  Now our command becomes:


.nf
# Our command in its most generic form using
# User-Defined, Environment, and Built-In Variables

XTERM = xterm -l -e
m MyMore [XTERM]  [$PAGER]  [DSELECTION]
.fi

The "DSELECTION" built-in is what communicates the currently
selected item from the GUI to your command when the command
actually gets run.

.SS Selection-Related Built-Ins

\'twander\' has a rich set of Built-In Variables for use in your
Command Definitions.  The first group of these is used to convey your
current directory and items which you've selected to a Command
Definition:


.IP \(bu 4
.B [DIR]

[DIR] is replaced with the current directory which \'twander\'
is viewing.

.IP \(bu 4
.B [DSELECTION]

[DSELECTION] is replaced with the fully-qualified path name
of the item currently selected in the GUI.  If more than
one item is selected, [DSELECTION] refers to the last item
in the group (the bottom-most, not the most recent item
you selected).

.IP \(bu 4
.B [DSELECTIONS]

[DSELECTIONS] is replaced with the fully-qualified path
name of 
.B all
items currently selected in the GUI.

.IP \(bu 4
.B [SELECTION]

[SELECTION] is replaced with the name of the currently
selected item in the GUI.  The path to that file is
.B not
included.  As with [DSELECTION], if more than one item is selected in
the GUI, the name of the last item in the group is returned for this
variable.

.IP \(bu 4
.B [SELECTIONS]

[SELECTIONS] is replaced with the names of
.B all
items currently selected in the GUI.  The path to those names is
not included.

.SS Prompting And Special-Purpose Built-Ins

There are also several special-purpose Built-In Variables which are used
for creating more powerful Command Definitions:

.IP \(bu 4
.B [HASH]

Because \'twander\' always recognizes the "#" as the beginning of a
comment, there is no direct way to include this character in a Command
String.  It is conceivable that some commands (such as \'sed\') need
to make use of this character.  The [HASH] built-in is provided for
this purpose.  Anywhere it appears in the Command String, it will be
replaced with the "#" at command execution time.  Unlike all the other
Built-In Variables, [HASH] is never quoted when it is replaced in a
Command String, regardless of whether the -t command argument is used
or not.

.IP \(bu 4
.B [PROMPT:Prompt-String]

[PROMPT:...] allows you to insert an interactive prompt for the user
anywhere you'd like in a Command String.  The user is prompted
with the "Prompt String" and this variable is replaced with their
response.  If they respond with nothing, it is interpreted as an
abort, and the command execution is terminated.  This makes commands
extremely powerful.  For instance, say you want to create a group copy
command:

.nf
# Copy a group of items to a location set by
# the user at runtime
UnixCopy  = cp -R
Win32Copy = copy

# Unix Version
c UnixCP [UnixCopy]  [DSELECTIONS]  [PROMPT:Enter Destination]

# Win32 Version
C Win32CP [Win32Copy]   [DSELECTIONS]  [PROMPT:Enter Destination]
.fi

.IP \(bu 4
.B [YESNO:Question-String]

[YESNO:...] allows you to prompt the user with a dialog containing a
Yes/No question and buttons for their response.  If the user presses
"Yes", command interpretation/execution continues.  If the user
presses "No", the command is aborted.  This is handy when you want to
make sure the user really wants to run the command before continuing.
For instance, suppose you define a recursive file/directory deletion
command.  Before running it, it's good to prompt the user to confirm
their intentions:

.nf
D BigDelete [YESNO:Are You Absolutely Sure About This?] rm -rf [SELECTIONS]
.fi

.SS Program Memory Built-Ins

As described previously, \'twander\' implements an advanced notion of
a Clipboard called "Program Memories".  There is a corresponding group
of Built-In Variables which allows the contents of these memories to
be used in a Command Definition:

.IP \(bu 4
.B [MEM1]...[MEM12]

Return the file/directory names currently stored in the indicated memory.
For example, to move all the files/directories currently named in
the first Program Memory to the current directory we could define
a move command like this:

.nf
m move mv [MEM1] ./
.fi

.SS Notes On Built-In Variable Use

.IP \(bu 4
Built-In Variables which return a directory name do
.B NOT
append a path separator character ("/" or "\\") to the end of the name
even though it is visible in the GUI.  This provides maximum
flexibility when defining commands.  It is up to the command author to
insert the appropriate path separator character where needed.  (NOTE:
Earlier releases of \'twander\'
.B did
include the trailing path separator and you may have to edit
older Configuration Files accordingly.  This change was necessary
because certain commands like Unix \'cp\' will not work if given
a source directory with the path separator included.)

 For example, another way to express the full path of the currently
selected item is:

.nf
# Unix Path Separator
UPSEP = /

#Win32 Path Separator
WPSEP = \\

[DIR][UPSEP][SELECTION]

or

[DIR][WPSEP][SELECTION]
.fi

Be aware that, because of \'twander\' quoting rules, such constructs
will result in strings like:

.nf
"/mydir"/"myfile"

or

"C:\\mydir"\\"myfile"
.fi

This should not generally be a problem with the various Unix
shells, and may work for some Win32 commands.  However, some
Win32 programs (noted on \'notepad\') reject this kind of
file name when passed on the command line.  The workaround
(and a generally easier way to do this sort of thing), is to use
the [DSELECTION] built-in which returns the full path name of
an item as a single quoted string.


.IP \(bu 4
User-Defined and Environment Variables are processed
at the time the Configuration File is read by \'twander\'.  That
is, they are handled
.B once
at load time.

.IP \(bu 4
By contrast, Built-In Variables are resolved
.B on each command invocation,
i.e - at command runtime.

.IP \(bu 4
The results of all built-ins (except HASH) are put inside
double-quotes when they are replaced in the Command String.  This
default is recommended so that any built-in substitutions of, say,
file names with spaces in them, will be properly recognized by your
commands.  You can suppress the addition of double-quotes by using the
-t command line option when starting \'twander\'.

.IP \(bu 4
Any of the variable types may appear multiple times in the
same Command String.  For example, suppose you want to
define a generic Unix copy command:

.nf
g gencopy cp -R  [PROMPT:Enter Source]  [PROMPT:Enter Destination]
.fi

When the user presses "g" (or clicks on "gencopy" on the Command
Menu), they will be presented with two prompts, one after the other,
and then the command will run.


.SH ADVANCED WIN32 FEATURES

As shipped from the factory, \'twander\' runs pretty much identically
on various Unix variants (FreeBSD, Linux) and Win32.  However,
\'twander\' is written to take advantage of Mark Hammond's
\'win32all\' Python extensions if they are present on the system.
These extensions add many Windows-specific features to Python
and allow \'twander\' to provide quite a bit more Windows-centric
information about files, directories, and drives.  You do 
.B not
have to install \'win32all\' for \'twander\' to operate properly
on your Win32 system.  Installing this package just means you'll
get even more \'twander\' features on Win32 than you would otherwise.
If you've installed \'win32all\', you can toggle these features
on- and off with the TOGWIN32ALL key described above.

.SS Getting \'win32all\'

You can get the \'win32all\' extensions one of two ways.  If you've
installed the Active State version of Python for Win32,
(http://www.activestate.com/Products/ActivePython/) \'win32all\' is
already installed on your system.  If you installed the standard
Python release for Win32
(http://www.python.org/download/download_windows.html), you must add
\'win32all\' to your installation.  You'll find the extensions and
painless installation instructions at:
http://starship.python.net/crew/mhammond/

.SS New Features Supported With \'win32all\'

One important note is in order here: The features enabled by
\'win32all\' are only available on "true" Win32 systems like Windows
2000 and Windows XP.  Earlier versions of Windows like Win98 and WinME
emulate portions of the Win32 API and do not implement the advanced
security features found in the NTFS file system.  Therefore, as noted
below, most of these features will not work on any of the older 16-bit
Windows operating systems.  \'twander\' handles this gracefully
without blowing-up so you can safely have \'win32all\' installed on
one of these older systems.

Once you have these extensions installed, \'twander\' will
automatically enable three new features otherwise unavailable.

.IP \(bu 4
When viewing file/directory detail information, the owner and group
names will be the actual names reported by the operating system rather
than the filler values normally seen in those fields (\'win32owner\'
and \'win32group\').  (Does not work on older Windows systems like
Win98.)

.IP \(bu 4
Instead of showing Unix-style file permissions (which don't mean much
under Win32), systems with \'win32all\' installed will show the
so-called "file attributes" maintained by the operating system.  Each
detailed entry in the display will have one or more of the following
attributes displayed in what is normally the Unix permissions field:

.nf
d - Directory
A - Archive
C - Compressed
H - Hidden
N - Normal
R - Read-Only
S - System
.fi

.IP \(bu 4
A top-level "Drive List View" is enabled if \'win32all\' is installed.
This shows you a list of all currently available drives reachable by
the system, and information about those drives.  For locally attached
drives, the drive label is shown.  For network-attached drives, the
share string is shown.  The drive type (CD/DVD, Fixed, Ramdisk,
Remote, Removable) is shown as are the free/total space statistics.
As is the case with other \'twander\' displays, these details can be
toggled on- and off via the TOGDETAIL key.

You can enter the Drive List View in a number of ways:

.nf
1) Select the ".." from the root directory of any drive.
2) Enter the string "\\\\" from the CHANGDIR dialog.
3) Press the DRIVELIST key (default: Control-k).
4) Start \'twander\' using "\\\\" as the starting directory
   argument, either on the command line or using the 
   Configuration File STARTDIR option.
.fi

The "Drive List View" is available on all Win32 variants, however the
free/total space values will be incorrect on older systems like Win98.

.SS Notes On Drive List View

The Drive List View is a little different than the usual
file/directory view.  Program behavior (semantics) is thus also slightly
different than usual in several ways:

.IP \(bu 4
While in Drive List View, the various Built-In Variables which return
the current selections will return
.B the name or names of the selected drive(s)
(without a trailing slash) just as you would expect them to
in a normal file/directory view.  This allows you to write
commands which take drive names (letters) as an argument.
The [DIR] Built-In returns an empty string in this view.

.IP \(bu 4
Normally, as you navigate around a file system, \'twander\' sets its
own program context to the current directory.  This is why you can
write Command Definitions using only the file/directory name currently
selected - \'twander\' knows the current directory.  When you are in
Drive List View, the notion of "current directory" has no real
meaning.  So, \'twander\' treats the directory from which you entered
Drive List View as the "current directory" while in that view.

.IP \(bu 4
By default, \'twander\' automatically rereads the current view
about every 3 seconds.  This is fine for a file/directory view
but would be annoyingly slow in the Drive List View since
it takes a moment or two to get the status of any floppy disk
drives attached to the system.  Instead of forcing the user to
listen to (and wait for) the floppy drive status to be determined
every 3 seconds, \'twander\' 
.B only reads the drive information once when it enters Drive List View.
This means if a drive is connected or a floppy is inserted into the
system while in Drive List View, this fact will not be automatically
noted.  You can force a manual update of the Drive List View by
pressing the REFRESH key (default: Control-l).

.IP \(bu 4
The TOGWIN32ALL key (default: Control-w) is disabled in
Drive List View.  This view is only available in \'win32all\'
mode and toggling it off makes no sense here.

.IP \(bu 4
The SELALL (default: Control-comma) and SELINV (default: Control-i)
features work slightly differently in Drive List View than they
do otherwise.  Ordinarily, these features never select the first
item of a file/directory display because it is always the ".."
entry pointing to the directory parent.  In Drive List View,
the first entry
.B is
an entry of interest - usually, but not always, Drive A: - so
these two keys
.B do
select it as is appropriate.

.SS Disabling \'win32all\' Features
You can toggle these features on-and off using the TOGWIN32ALL key
(default: Control-w).  You can also permanently disable them by
setting the USEWIN32ALL option to False in the Configuration File.
This allows you to leave \'win32all\' installed on your system 
if you need it for other reasons but don't want these features
enabled in \'twander\'


.SH GOTCHAS

There are several tricky corners of \'twander\' which need
further explanation:

.B \'twander\' Will Not Enter Certain Directories On Win32

Win32 allows file/directory names to contain non-ASCII
characters.  Python, as shipped, defaults to ASCII only
and grumbles mightily when it is asked to deal with a string
containing characters with ordinal values greater than
127 (i.e., 8-Bit "extended" ASCII).  The solution to this
problem is to enable Python to handle non-ASCII strings.
This is done by editing a file called "site.py".  This
file is normally found in:

.nf
C:\\Program Files\\PythonXX\\Lib
.fi

Where "XX" is the actual version of Python you're running.

Open this file with an editor and look for the following
text:

.nf
encoding = "ascii" # Default value set by _PyUnicode_Init()

if 0:
    # Enable to support locale aware default string encodings.
    import locale
.fi

Change the "if 0:" statement to "if 1:" and the problem
will disappear.


.B Getting Command Results Displayed In A New Window

When you invoke a command via \'twander\', whether via a command
definition in the Configuration File or the keyboard shortcut, you
generally want it to run in a new window.  If the program you are
running is GUI-aware, this should not be a problem.  However, if you
are using \'twander\' to run a command line program or script, you
have to take extra care in the formulation of the Command String.
In the case of Unix-like systems you have to invoke the command
so that it runs in some GUI context.  Say you want to use a pager like
\'less\' to view files.  You would expect that this entry might do it:

.nf
V   view    less    [DSELECTIONS]
.fi

Sadly, this will not work, at least not the way you expect.
If you started \'twander\' from a terminal session and use
the command above, it will work, but the results will appear
in the invoking terminal window,
.B not
in a new window as you might expect. If you started \'twander\'
from a GUI or disconnected it from the initiating terminal with
a \'nohup\' ... & invocation, you will get
.B no
output.  This is not a \'twander\' problem, it is innate to
how command line programs run under Unix-like shell control.  To achieve
the desired results, you'll need something like this in your
Configuration File:

.nf
V   view         xterm -l -e less [DSELECTIONS]
.fi

This causes your command line program to execute in an \'xterm\'
context.

This is not so much of an issue on Win32 systems where the first
form of the command above works fine.

.B Modal Operation Of New Windows

Notice our example commands above do not end with "&". 
These should not be needed on either Unix-like or Win32
operating systems.  When a command is executed, \'twander\'
starts a new thread of execution which runs concurrently
with \'twander\' itself.  This means you should be able to
continue using \'twander\' while the new command executes.
If not (\'twander\' is locked out while the new command runs -
so-called "modal" operation), it means your system does not
completely or correctly implement threading.  In this case,
try adding this statement to your Configuration File:
"USETHREADS=False" which will force \'twander\' to 
invoke new commands using conventional (heavyweight) process
spawning.

.B Windows That Don't Disappear On Command Completion

It appears that some X Windows implementations (noted on XFree86 /
FreeBSD) do not correctly destroy an \'xterm\' window after a command
initiated with -e terminates.  This is not a \'twander\' problem.  The
workaround is to add the following statement to your Configuration
File: "USETHREADS=False" This forces conventional (heavyweight)
process spawning when a command is run.  This mechanism correctly
destroys the window upon command completion.

.SH OTHER

File/Directory name sorting is done without-case sensitivity on
Win32 systems because the underlying operating system does not
observe case.

Because this program has not been tested on anything other than
Unix-like and Win32 systems, command execution by double-click
or pressing Enter is inhibited on all other operating systems
by default.

You must have Python 2.2 or later installed as well as Tkinter support
installed for that release.  In the case of Win32, Tkinter is bundled
with the standard Windows Python distribution.  In the case of
Unix-like systems, you may have to first install Python and then the
appropriate release of Tkinter.  This is the case, for example, with
FreeBSD.

You must install the \'win32all\' extensions if you want to use
the advanced Win32 features.


.SH BUGS AND MISFEATURES

The Configuration File parser does no validation to check the sanity
of its various entries for Command Definitions, Key Bindings, Options,
and Directory Shortcuts.  It is entirely possible to edit something
into this file that makes no sense at all and causes \'twander\'
to misbehave.

There appears to be a Tkinter/Tk bug on Unix which sometimes inhibits
the correct title display when you tear-off a menu.  This is a
cosmetic defect and may disappear as future releases of
Tkinter/Tk/X-Windows appear.

This program has not been tested on MacOS.  Please let me know how/if
it works there and any issues you discover.


.SH INSTALLING \'twander\'

Installation of \'twander\' is fairly simple and takes only a few
moments.  The most important thing before installing the program is to
make sure you have Python 2.2 (or later) with Tkinter support
installed on your system.

One other note: However you install the program, it is probably
easiest to get started by editing the example ".twander" file to
taste.  Be aware that this file is shipped with everything commented
out.  You have to uncomment/edit the section relevant to your
operating system: Unix-like or Win32.

.SS Installing Using The FreeBSD Port

If you've installed \'twander\' using the FreeBSD port, all you have
to do is copy the example Configuration File, ".twander" found in
/usr/local/share/doc/twander to your home directory and edit it to
taste.  

Make sure that /usr/local/bin is in your path.  To start the program,
just type "twander.py" from the shell prompt.

.SS Installing Manually On A Unix-like System

Copy the "twander.py" file to a directory somewhere on your path.
(/usr/local/bin is a good candidate).  Make sure this file has
permissions 755 and owner/group appropriate for your system
(root/wheel, root/root, or bin/bin).  Copy the ".twander" file
to your home directory and edit to taste.

To run the program, just type "twander.py" from a shell prompt.

.B Red Hat Linux Users Please Note:
RH Linux (and possibly other Linux systems) install two versions of
Python.  Version 1.52 is called \'python\', and Version 2.2 is called
\'python2\'.  \'twander\' requires the latter and will not run on the
former.  As shipped, \'twander\' invokes Python with the Unix shell
"#!" mechanism using the name \'python\' - which in this case is the
wrong version.  You can work around this problem one of several ways:

.IP \(bu 4
Rename \'python\' to \'python1\' and then rename \'python2\'
to \'python\'. (Not Recommended - could break other programs.)

.IP \(bu 4
Write an alias or shell script which explicity starts
\'twander\' with the correct version of Python:

.nf
#!/bin/sh
python2 twander.py $*
.fi

.IP \(bu 4
Change the first line of the \'twander\' code to refer
to \'python2\' instead of \'python\'.

.P 
Red Hat users who have upgraded from earlier versions should
also note that you may have files in your home directories owned by
owners and groups which are not defined in the system!  \'twander\'
shows the owner and group fields for such files as numbers rather than
names.  As best as we can determine, this is caused when an RH
installation is updated from an older version.

.SS Installing Manually On A Win32 System

Copy the "twander.py" file to a directory somewhere on your path,  or
create a new directory to hold this file and add that directory path
to the PATH environment variable.  

.B IMPORTANT NOTE TO WIN32 USERS:
Windows has the old MS-DOS legacy of assuming that a "." begins a file
"extension".  Although you can create and read files in the form
".something", it is not recommended because many Win32 programs get
confused when they see this.  It is also difficult to remove files
named this way with the standard Windows programs and utilities.  This
is especially the case for older Win32 operating systems like Win98.
For this reason, it is recommended that you rename the ".twander"
default Configuration File provided in the program distribution to
something else like "twander.conf" and use the \'twander\' -c command
line option to point to this Configuration File.


On Win32, where to put the Configuration File raises an interesting
question.  Microsoft operating systems normally do not set the "HOME"
environment variable, because they have no notion of a "home"
directory - Well, they do, but it is called "USERPROFILE" not "HOME".
So, you can either create a new user-specific environment variable
called HOME yourself (which points to your desired home directory) or
you can invoke \'twander\' with the -c argument to explictly declare
where it can find its Configuration File.

You can run the program several ways on Win32 systems:

.IP \(bu 4
Create a Win32 shortcut which points to the "twander.py" file using
the "pythonw" command to invoke it.  Normally, starting a Python
program from the Windows GUI creates a parent window which persists as
long as the program runs. Using "pythonw" instead of "python" to run
your program suppresses the creation of this blank parent window.  For
example, you might have something like this in the "Target:" field of
your shortcut:

.nf
"C:\\Program Files\\Python22\\pythonw.exe" C:\\twander.py \\
.fi

This runs the program starting at the root directory of
the current drive (assuming "twander.py" is located in C:\\.

.IP \(bu 4
Start a command line window and issue a command like the one
above directly from the command line.

.IP \(bu 4
Use Windows Explorer (or better still, an already running instance
of \'twander\'!) to navigate to the directory where "twander.py"
is located.  Double-click on the file.  If Python is properly
installed, there should be an association for ".py" file types
and \'twander\' should start automatically.


.SH GETTING HELP: THE \'twander\' MAILING LIST

TundraWare Inc. maintains an email list for \'twander\'
users to get help and exchange ideas.  To subscribe,
send mail to:

.nf
majordomo@tundraware.com
.fi

In the body (not the subject line) of the email, enter
the following text, substituting your own email address
as indicated:

.nf
subscribe twander-users your-email-address
.fi


.SH DESIGN PHILOSOPHY
Graphical User Interfaces (GUIs) are a blessing and a curse. On the
one hand, they make it easy to learn and use a computer system.  On
the other, they are a real inconvenience to experienced users who are 
touch typists.  Taking hands off the keyboard to use the mouse
can really slow down a good typist.

Nowhere is this more apparent than in filesystem browsers.  In one
corner we have the GUI variants like \'Konqueror\' and \'Microsoft
Windows Explorer\'.  These are very easy to use but you pretty much
need the mouse in your hand to do anything useful.  In the other
corner are the text-based file browsers like \'List\', \'Norton
Commander\', and \'Midnight Commander\'.  These are really efficient
to use, but have limited functionality and generally do not operate
very well on
.B groups
of things.

Both of these approaches also suffer from the well-known
interface problem of "What You See Is
.B All
You Get" - Each program has a predefined set of commands and the user
cannot easily extend these with their own, new commands.

\'twander\' is another approach to the filesystem navigation problem
which embraces the best of both the GUI-based approach and the
text-based approach.  It also provides a rich mechanism whereby each
user can easily define their own command set and thereby customize the
program as they see fit.  This is done with a number of key features:


.TP
1)
The
.B Navigation
of the filesystem is graphical - you can use the mouse to select files,
directories, or to change directories.  However, each major filesystem
navigational feature is also doubled on the keyboard (using Control keys)
so you can move around and select things without ever touching the mouse.

.TP
2)
\'twander\' also supports a number of
.B navigation shortcuts.
It provides single control-key access to changing directories, moving
to the previous directory, moving up one directory level, moving to
any previously visited directory, (de)selecting any or all
files/directories in the current view, and escaping to the operating
system to run a command.  Some (but not all) of these features are
also doubled via GUI/mouse operations.

.TP
3)
There are
.B no
built-in file or directory commands.  All commands which manipulate
the files or directories selected during navigation are user-defined.
This Command Definition is done in an external Configuration File
using a simple but powerful command macro language.  This means that
that the command set of the program can easily be changed or expanded
without having to release a new version of \'twander\' every time.
Better still, every different user can have their own command set
defined in a way that suits their style of working.  Best of all,
commands can be invoked either graphically (with a mouse click) or via
a single keypress to minimize moving your hands off the keyboard.

.TP
4)
Because \'twander\' is written in Python using Tkinter, the same
program runs essentially identically on many Unix-like and Win32
systems.  The only thing that may need to be changed across these
various platforms are the Command Definitions in the configuration
file.  You only need to learn one interface (and the commands you've
defined) across all the different systems you use.

.P
The consequence of all this is that \'twander\' is an extremely
powerful and highly customizable filesystem navigator.  Once
learned, both navigation and command execution are lightning-fast
(or at least, as fast as your machine can go ;) while minimizing
dependency on the mouse.


.SH COPYRIGHT AND LICENSING
\'twander\' is Copyright(c) 2002 TundraWare Inc.  For terms of use, see
the twander-license.txt file in the program distribution.  If you
install \'twander\' on a FreeBSD system using the 'ports' mechanism, you
will also find this file in /usr/local/share/doc/twander.


.SH AUTHOR
.nf
Tim Daneliuk
twander@tundraware.com