Initial git import v1.0
authorSteve Youngs <steve@sxemacs.org>
Tue, 13 Dec 2011 07:55:55 +0000 (17:55 +1000)
committerSteve Youngs <steve@sxemacs.org>
Tue, 13 Dec 2011 07:55:55 +0000 (17:55 +1000)
Signed-off-by: Steve Youngs <steve@sxemacs.org>
.gitignore [new file with mode: 0644]
ChangeLog.d/ChangeLog-0.1 [new file with mode: 0644]
ChangeLog.d/ChangeLog-0.2 [new file with mode: 0644]
ChangeLog.d/ChangeLog-0.3 [new file with mode: 0644]
ChangeLog.d/ChangeLog-0.4 [new file with mode: 0644]
ChangeLog.d/ChangeLog-0.5 [new file with mode: 0644]
ChangeLog.d/ChangeLog.SFCVS [new file with mode: 0644]
Makefile [new file with mode: 0644]
TODO [new file with mode: 0644]
codenames [new file with mode: 0644]
emoney.el [new file with mode: 0644]

diff --git a/.gitignore b/.gitignore
new file mode 100644 (file)
index 0000000..5904682
--- /dev/null
@@ -0,0 +1,4 @@
+*.elc
+*~
+*.bak
+emoney-version.el
diff --git a/ChangeLog.d/ChangeLog-0.1 b/ChangeLog.d/ChangeLog-0.1
new file mode 100644 (file)
index 0000000..24717d5
--- /dev/null
@@ -0,0 +1,29 @@
+# do not edit -- automatically generated by arch changelog
+# non-id: automatic-ChangeLog--steve@sxemacs.org--2004/emoney--main--0.1
+#
+
+2004-11-12 08:57:51 GMT        Steve Youngs <steve@eicq.org>   patch-1
+
+    Summary:
+      Remove ChangeLog file
+    Revision:
+      emoney--main--0.1--patch-1
+
+
+    removed files:
+     .arch-ids/ChangeLog.id ChangeLog
+
+
+2004-10-20 11:47:14 GMT        Steve Youngs <steve@sxemacs.org>        base-0
+
+    Summary:
+      Initial import
+    Revision:
+      emoney--main--0.1--base-0
+
+    Initial import of eMoney into arch
+
+    new files:
+     ChangeLog ChangeLog.SFCVS Makefile codenames emoney.el
+
+
diff --git a/ChangeLog.d/ChangeLog-0.2 b/ChangeLog.d/ChangeLog-0.2
new file mode 100644 (file)
index 0000000..2bd9dba
--- /dev/null
@@ -0,0 +1,318 @@
+# do not edit -- automatically generated by arch changelog
+# non-id: automatic-ChangeLog--steve@sxemacs.org--2005/emoney--main--0.2
+#
+
+2005-12-26 02:35:24 GMT        Steve Youngs <steve@sxemacs.org>        version-0
+
+    Summary:
+      eMoney 0.2 is released!
+    Revision:
+      emoney--main--0.2--version-0
+
+    eMoney 0.2 has been released.
+    
+    * emoney.el: Move "Todo" section into its own file.
+    
+
+    new files:
+     .arch-ids/TODO.id TODO
+
+    modified files:
+     emoney.el
+
+
+2005-11-03 14:37:16 GMT        Steve Youngs <steve@sxemacs.org>        patch-12
+
+    Summary:
+      Typo fix
+    Revision:
+      emoney--main--0.2--patch-12
+
+    * emoney.el (emoney-go-to-bank): Fix typo.
+    
+
+    modified files:
+     emoney.el
+
+
+2005-10-09 04:41:09 GMT        Steve Youngs <steve@sxemacs.org>        patch-11
+
+    Summary:
+      Bitrot removal and some minor clean up
+    Revision:
+      emoney--main--0.2--patch-11
+
+    This change removes the "demo" mode.  It was written before eMoney had
+    anything resembling a UI.  It may return in a future version of eMoney,
+    but for now it's history.
+    
+    Also removed is the very old (from balance.el days) hard-coded LaTeX
+    cheque printing.  That only ever worked on balance.el's author's printer,
+    wasn't customisable, and... well you get the picture.  It's gone!
+    
+    * emoney.el (emoney-in-demo-mode): Removed.
+      (emoney-mode): Update doc string... don't mention `emoney-demo'... it
+      doesn't exist anymore.
+      (emoney-demonstration-data): Removed.
+      (emoney-demonstration-help): Removed.
+      (emoney-demo): Removed.
+      (emoney-recalculate-buffer): Don't check is we're in "demo" mode.  No
+      such thing anymore.
+      (emoney-setup-accounts-buffer): 80 column clean up.
+      (emoney-transfer-funds): Ditto.
+      (emoney-parse-transaction-data): Remove the print stuff.
+      (emoney-number-it): Removed.  Old, bitrotted, hard-coded cheque
+      printing via LaTeX.
+      (emoney-print-make-words): Ditto.
+      (emoney-print-check): Ditto.
+      (emoney-setup-control-buffer): 80 column clean up.
+    
+
+    modified files:
+     emoney.el
+
+
+2005-10-09 03:42:58 GMT        Steve Youngs <steve@sxemacs.org>        patch-10
+
+    Summary:
+      Bring eMoney to life in a blaze of colour.
+    Revision:
+      emoney--main--0.2--patch-10
+
+    * emoney.el (emoney-faces): New custom group.
+      (emoney-account-name-face): New face.
+      (emoney-debit-face): Ditto.
+      (emoney-credit-face): Ditto.
+      (emoney-date-face): Ditto.
+      (emoney-clear-tran-face): Ditto.
+      (emoney-unclear-tran-face): Ditto.
+      (emoney-header-face): Ditto.
+      (emoney-setup-accounts-buffer): Use new eMoney faces.
+      (emoney-setup-header-buffer): Ditto.
+      (emoney-update-acc-buf-bal): Ditto.
+      (emoney-font-lock-keywords): New.  For the font-lock thang.
+    
+
+    modified files:
+     emoney.el
+
+
+2005-10-08 02:21:07 GMT        Steve Youngs <steve@sxemacs.org>        patch-9
+
+    Summary:
+      Fix balance display in A/C's buffer
+    Revision:
+      emoney--main--0.2--patch-9
+
+    * emoney.el (emoney-setup-accounts-buffer): Allow for situation where the
+      account hasn't been "recalculated".
+    
+
+    modified files:
+     emoney.el
+
+
+2005-10-08 01:26:12 GMT        Steve Youngs <steve@sxemacs.org>        patch-8
+
+    Summary:
+      Display each A/C's current balance in *Accounts Buffer*
+    Revision:
+      emoney--main--0.2--patch-8
+
+    * emoney.el (emoney-accounts-buffer-width): Set default to 25.  The
+      increase is to allow for balances being in the buffer.
+      (emoney-setup-accounts-buffer): Insert each account's current balance
+      into the buffer.
+      (emoney-largest-balance): Move it higher in the file to avoid a
+      compiler warning.
+      (emoney-update-acc-buf-bal): New.  Updates the balances in the Accounts
+      buffer.
+      (emoney-recalculate-buffer): Use it.
+    
+
+    modified files:
+     emoney.el
+
+
+2005-10-06 03:45:48 GMT        Steve Youngs <steve@sxemacs.org>        patch-7
+
+    Summary:
+      Build cleanup
+    Revision:
+      emoney--main--0.2--patch-7
+
+    * Makefile: Remove "superupgrade" target.
+    
+    * emoney.el: Autoload `browse-url' at compile-time
+    
+
+    modified files:
+     Makefile emoney.el
+
+
+2005-10-06 01:20:54 GMT        Steve Youngs <steve@sxemacs.org>        patch-6
+
+    Summary:
+      Menu and keymap additions -- calc & bank
+    Revision:
+      emoney--main--0.2--patch-6
+
+    * emoney.el (emoney-accounts-buffer-width): Make it customisable.
+      (emoney-accounts-buffer-height): Make it customisable, default it to 9.
+      (emoney-header-buffer-height): Make it customisable, default it to 4.
+      (emoney-mode-menu): Add menu items for opening Bank URL, and
+      calculator. 
+      (emoney-calc): New.  Wrapper to work around a bug in Emacs Calc... The
+      dreaded "window-edges" bug.
+      (emoney-mode-map): Bind `C-c c' to `emoney-calc'.
+      (emoney-setup-control-buffer): Use `emoney-calc'.
+    
+
+    modified files:
+     emoney.el
+
+
+2005-09-21 01:59:08 GMT        Steve Youngs <steve@sxemacs.org>        patch-5
+
+    Summary:
+      Go to your bank's web site from within eMoney
+    Revision:
+      emoney--main--0.2--patch-5
+
+    * emoney.el (emoney-bank-url): New.
+      (emoney-setup-control-buffer): Add button for surfing to your bank's
+      web site.
+      (emoney-go-to-bank): New.  For browsing to your bank's web site.
+      Default binding is `C-c b'.  Also used in
+      `emoney-setup-control-buffer'. 
+      (emoney-mode-map): Bind `C-c b' to `emoney-go-to-bank'.
+    
+
+    modified files:
+     emoney.el
+
+
+2005-09-12 13:29:37 GMT        Steve Youngs <steve@sxemacs.org>        patch-4
+
+    Summary:
+      Switch accounts via keyboard
+    Revision:
+      emoney--main--0.2--patch-4
+
+    I almost can't believe I let this go so long without adding it.  Now you
+    can switch accounts via the keyboard... bound to `C-c s'
+    
+    * emoney.el (emoney-switch-to-account): Renamed to
+      `emoney-mouse-switch-to-account'. 
+      (emoney-mouse-switch-to-account): New.
+      (emoney-accounts-buffer-map): Use it.
+      (emoney-switch-to-account): New version of this function, now it is for
+      switching accounts via the keyboard.
+      (emoney-mode-map): Bind `C-c b' to `emoney-switch-to-account'.
+    
+
+    modified files:
+     emoney.el
+
+
+2005-09-12 00:05:40 GMT        Steve Youngs <steve@sxemacs.org>        patch-3
+
+    Summary:
+      Makefile tweak
+    Revision:
+      emoney--main--0.2--patch-3
+
+    * Makefile (INSTALL): Drop the user/group options so eMoney can be
+      installed by non-root users.
+    
+
+    modified files:
+     Makefile
+
+
+2005-09-11 23:37:40 GMT        Steve Youngs <steve@sxemacs.org>        patch-2
+
+    Summary:
+      Window config improvements
+    Revision:
+      emoney--main--0.2--patch-2
+
+    This change works around a problem in Emacs Calc.  Calc wouldn't put
+    point back to the place it was before calc was called.  We fix it by
+    defadvice'ing `calc' and `calc-quit'.
+    
+    Also, we only save/restore the "pre eMoney" window configuration if
+    eMoney isn't running in its own frame.
+    
+    * emoney.el (calc): defadvice it so it saves the window config before
+      calc starts.
+      (calc-quit): defadvice it so that the "pre calc" window config is
+      restored when calc exits.
+      (emoney): Save the window config to a register instead of using a
+      global variable.  Only save the config if eMoney is _not_ using its own
+      frame.
+      (emoney-quit): Restore the window config from a register, only if
+      eMoney is _not_ using its own frame.
+      (emoney-old-window-config): Removed.
+    
+
+    modified files:
+     emoney.el
+
+
+2005-01-01 01:36:48 GMT        Steve Youngs <steve@sxemacs.org>        patch-1
+
+    Summary:
+      tla style version string
+    Revision:
+      emoney--main--0.2--patch-1
+
+    The patch introduces a tla style version string, something like...
+    
+      steve@sxemacs.org--2005/emoney--main--0.2--base-0
+    
+    It also adds the ChangeLog file from the previous version.  It is in
+    ./ChangeLog.d/ 
+    
+    * Makefile (VER): Bump to 0.2.
+    (EXTRA_SRC): Remove ChangeLog... we let tla do the job of tracking
+    changes. 
+    (all): Add emoney-version.el
+    (auto-autoloads.el): emoney-version.el is a dependency
+    (emoney-version.el): New target.
+    (version): Alias to above.
+    (distclean): Remove emoney-version.el* as well.
+    (.PHONY): New.  To ensure the emoney-version is built.
+    
+    * emoney.el (emoney-codename): "Capital Gain"
+    
+    * emoney.el (emoney-version): Require emoney-version.
+    
+
+    new files:
+     .arch-ids/.arch-inventory.id .arch-inventory
+     ChangeLog.d/.arch-ids/=id
+     ChangeLog.d/.arch-ids/ChangeLog-0.1.id
+     ChangeLog.d/ChangeLog-0.1
+
+    modified files:
+     Makefile emoney.el
+
+    new directories:
+     ChangeLog.d ChangeLog.d/.arch-ids
+
+
+2005-01-01 00:24:51 GMT        Steve Youngs <steve@sxemacs.org>        base-0
+
+    Summary:
+      tag of steve@sxemacs.org--2004/emoney--main--0.1--patch-1
+    Revision:
+      emoney--main--0.2--base-0
+
+    (automatically generated log message)
+
+    new patches:
+     steve@sxemacs.org--2004/emoney--main--0.1--base-0
+     steve@sxemacs.org--2004/emoney--main--0.1--patch-1
+
+
diff --git a/ChangeLog.d/ChangeLog-0.3 b/ChangeLog.d/ChangeLog-0.3
new file mode 100644 (file)
index 0000000..0f23891
--- /dev/null
@@ -0,0 +1,69 @@
+# do not edit -- automatically generated by arch changelog
+# non-id: automatic-ChangeLog--steve@sxemacs.org--2006/emoney--main--0.3
+#
+
+2006-09-21 04:38:09 GMT        Steve Youngs <steve@sxemacs.org>        patch-2
+
+    Summary:
+      Give the eMoney frame a name
+    Revision:
+      emoney--main--0.3--patch-2
+
+    * emoney.el (emoney): Give the eMoney frame a name property.  By
+      side-effect, this sets the X11 window class which in turn means easier
+      manipulation and control for WMs, for example, Sawfish's "matched
+      windows". 
+    
+
+    modified files:
+     emoney.el
+
+
+2005-12-26 14:06:32 GMT        Steve Youngs <steve@sxemacs.org>        patch-1
+
+    Summary:
+      Prepare for 0.3 release cycle
+    Revision:
+      emoney--main--0.3--patch-1
+
+    * Makefile (VER): Bump to 0.3
+    
+    * emoney.el (emoney-codename): Set to "Currency".
+    
+
+    new files:
+     ChangeLog.d/.arch-ids/ChangeLog-0.2.id
+     ChangeLog.d/ChangeLog-0.2
+
+    modified files:
+     Makefile emoney.el
+
+
+2005-12-26 03:43:41 GMT        Steve Youngs <steve@sxemacs.org>        base-0
+
+    Summary:
+      tag of steve@sxemacs.org--2005/emoney--main--0.2--version-0
+    Revision:
+      emoney--main--0.3--base-0
+
+    (automatically generated log message)
+
+    new patches:
+     steve@sxemacs.org--2004/emoney--main--0.1--base-0
+     steve@sxemacs.org--2004/emoney--main--0.1--patch-1
+     steve@sxemacs.org--2005/emoney--main--0.2--base-0
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-1
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-2
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-3
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-4
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-5
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-6
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-7
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-8
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-9
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-10
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-11
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-12
+     steve@sxemacs.org--2005/emoney--main--0.2--version-0
+
+
diff --git a/ChangeLog.d/ChangeLog-0.4 b/ChangeLog.d/ChangeLog-0.4
new file mode 100644 (file)
index 0000000..9460ece
--- /dev/null
@@ -0,0 +1,129 @@
+# do not edit -- automatically generated by arch changelog
+# non-id: automatic-ChangeLog--steve@sxemacs.org--2007/emoney--main--0.4
+#
+
+2007-08-04 07:38:20 GMT        Steve Youngs <steve@sxemacs.org>        patch-4
+
+    Summary:
+      Fix some font-locking issues.
+    Revision:
+      emoney--main--0.4--patch-4
+
+    This changeset fixes a couple of font-locking issues introduced in the
+    previous changeset.
+    
+    * emoney.el (emoney-build-type-regexp): Use #'append instead of #'push.
+      (emoney-credit-type-keywords): Add in `emoney-cr-transfer-transaction-type'.
+      (emoney-debit-type-keywords): Add in `emoney-db-transfer-transaction-type'.
+    
+
+    modified files:
+     emoney.el
+
+
+2007-08-04 05:07:56 GMT        Steve Youngs <steve@sxemacs.org>        patch-3
+
+    Summary:
+      Minor tidy up and fix bug in transfers
+    Revision:
+      emoney--main--0.4--patch-3
+
+    This changeset cleans up a bit of the code and fixes a bug in
+    transactions that transfer between a/c's.  The accounts buffer was
+    getting out of sync.
+    
+    * emoney.el (emoney-accounts-directory): Use #'user-home-directory
+      instead of environment variable, $HOME.
+      (emoney-history-directory): New.  Where previous years a/c files go.
+      (emoney-cheque-type): Typo fix.
+      (emoney-mode-map): Use [key] syntax.  I think it looks better. :-)
+      (emoney-accounts-buffer-map): Typo fix.
+      (emoney-calc): Typo fix.
+      (emoney-credit-transaction-types): Remove transfer types.
+      (emoney-debit-transaction-types): Ditto.
+      (emoney-cr-transfer-transaction-type): New.
+      (emoney-db-transfer-transaction-type): New.
+      (emoney-build-types-list): Include the new transfer types.
+      (emoney-build-type-regexp): Typo fix.
+      (emoney-append-transaction): Use new transfer types.
+      (emoney-transfer-funds): Use the new transfer types and fix the bug
+      that messed up the a/c's buffer whenever a transfer was done.
+    
+
+    modified files:
+     emoney.el
+
+
+2007-01-01 02:10:28 GMT        Steve Youngs <steve@sxemacs.org>        patch-2
+
+    Summary:
+      Improve UI a tiny bit
+    Revision:
+      emoney--main--0.4--patch-2
+
+    Hopefully this will help with the initial buffer/frame set up.
+    
+    * emoney.el (emoney-accounts-buffer-width): Increase to 30.
+    
+
+    modified files:
+     emoney.el
+
+
+2007-01-01 00:49:11 GMT        Steve Youngs <steve@sxemacs.org>        patch-1
+
+    Summary:
+      Prepare for 0.4 release cycle
+    Revision:
+      emoney--main--0.4--patch-1
+
+    Just the normal new release administrivia.  Plus a couple of makefile
+    improvements. 
+    
+    * emoney.el (emoney-codename): is now `Deficit'.
+    
+    * Makefile (VER): Bump.
+     (XEMACS): Default to `sxemacs'.
+     (PREFIX): Handle the differences between XEmacs and SXEmacs for
+     $PREFIX. 
+    
+
+    new files:
+     ChangeLog.d/.arch-ids/ChangeLog-0.3.id
+     ChangeLog.d/ChangeLog-0.3
+
+    modified files:
+     Makefile emoney.el
+
+
+2007-01-01 00:21:13 GMT        Steve Youngs <steve@sxemacs.org>        base-0
+
+    Summary:
+      tag of steve@sxemacs.org--2006/emoney--main--0.3--patch-2
+    Revision:
+      emoney--main--0.4--base-0
+
+    (automatically generated log message)
+
+    new patches:
+     steve@sxemacs.org--2004/emoney--main--0.1--base-0
+     steve@sxemacs.org--2004/emoney--main--0.1--patch-1
+     steve@sxemacs.org--2005/emoney--main--0.2--base-0
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-1
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-2
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-3
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-4
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-5
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-6
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-7
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-8
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-9
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-10
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-11
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-12
+     steve@sxemacs.org--2005/emoney--main--0.2--version-0
+     steve@sxemacs.org--2006/emoney--main--0.3--base-0
+     steve@sxemacs.org--2006/emoney--main--0.3--patch-1
+     steve@sxemacs.org--2006/emoney--main--0.3--patch-2
+
+
diff --git a/ChangeLog.d/ChangeLog-0.5 b/ChangeLog.d/ChangeLog-0.5
new file mode 100644 (file)
index 0000000..42b6fea
--- /dev/null
@@ -0,0 +1,40 @@
+# do not edit -- automatically generated by arch changelog
+# non-id: automatic-ChangeLog--steve@sxemacs.org--2008/emoney--main--0.5
+#
+
+2008-01-02 02:03:57 GMT        Steve Youngs <steve@sxemacs.org>        base-0
+
+    Summary:
+      tag of steve@sxemacs.org--2007/emoney--main--0.4--patch-4
+    Revision:
+      emoney--main--0.5--base-0
+
+    (automatically generated log message)
+
+    new patches:
+     steve@sxemacs.org--2004/emoney--main--0.1--base-0
+     steve@sxemacs.org--2004/emoney--main--0.1--patch-1
+     steve@sxemacs.org--2005/emoney--main--0.2--base-0
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-1
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-2
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-3
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-4
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-5
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-6
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-7
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-8
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-9
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-10
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-11
+     steve@sxemacs.org--2005/emoney--main--0.2--patch-12
+     steve@sxemacs.org--2005/emoney--main--0.2--version-0
+     steve@sxemacs.org--2006/emoney--main--0.3--base-0
+     steve@sxemacs.org--2006/emoney--main--0.3--patch-1
+     steve@sxemacs.org--2006/emoney--main--0.3--patch-2
+     steve@sxemacs.org--2007/emoney--main--0.4--base-0
+     steve@sxemacs.org--2007/emoney--main--0.4--patch-1
+     steve@sxemacs.org--2007/emoney--main--0.4--patch-2
+     steve@sxemacs.org--2007/emoney--main--0.4--patch-3
+     steve@sxemacs.org--2007/emoney--main--0.4--patch-4
+
+
diff --git a/ChangeLog.d/ChangeLog.SFCVS b/ChangeLog.d/ChangeLog.SFCVS
new file mode 100644 (file)
index 0000000..4bc0424
--- /dev/null
@@ -0,0 +1,206 @@
+This is the old ChangeLog from when eMoney was in SF.net CVS
+
+2004-06-28  Steve Youngs  <steve@youngs.au.com>
+
+       * eMoney 0.03 "Blue Chip" is released.
+
+       * Makefile (VER): 0.03
+
+       * emoney.el (emoney-days-to-time): New.
+       (emoney-time-add): New.
+       (emoney-append-transaction): Use them to specify dates that aren't
+       today.
+       (emoney-is-beta): Make it a `defconst'.
+       (emoney-mode-map): Add bindings for `emoney-quit' and
+       `emoney-recalc-and-exit'. 
+       (emoney-mode-menu): Move "New A/C" to top of menu.
+       Add entry for `emoney-recalc-and-exit'.
+       (emoney-check-transaction-type): Clarify doc string.
+       (emoney-recalc-and-exit): New.
+       (emoney-is-exiting): New.
+       (emoney-recalculate-buffer): Use it.
+       (emoney-quit): Ditto.
+       Use `emoney-use-new-frame'.
+       (emoney): Use `emoney-use-new-frame'.
+       (emoney-find-next-transaction): Don't untabify here.
+       (emoney-recalculate): Untabify the region.
+       (emoney-frame): New.
+       (emoney-version): 0.03
+
+2004-03-24  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * emoney.el (emoney-setup-control-buffer): Rearrange the version
+       string that is output from the "Version" button.        
+       (emoney-version): 0.03pre1
+       (emoney-mode-map): Bind `C-c C-x' to `emoney-transfer-funds'.
+       (emoney-mode-hooks): New.
+       (emoney-hooks): New custom group.
+       (emoney-switch-account-hook): New.
+       (emoney-switch-to-account): Use it.
+       (emoney-setup-accounts-buffer-hook): New.
+       (emoney-setup-accounts-buffer): Use it.
+       (emoney-setup-header-buffer-hook): New.
+       (emoney-setup-header-buffer): Use it.
+       (emoney-setup-control-buffer-hook): New.
+       (emoney-setup-control-buffer): Use it.
+       (emoney-transaction-hook): New.
+       (emoney-transaction-cheque-hook): New.
+       (emoney-append-next-cheque): Use them.
+       (emoney-transaction-transfer-hook): New.
+       (emoney-transfer-funds): Use it.
+       (emoney-append-transaction): Use `emoney-transaction-hook'.
+       (emoney-recalculate-before-hook): New.
+       (emoney-recalculate-after-hook): New.
+       (emoney-recalculate): Use them.
+       (emoney-summarise-cheques-hook): New.
+       (emoney-summarise-cheques): Use it.
+       (emoney-new-account-hook): New.
+       (emoney-new-account): Use it.
+       (emoney-quit-before-hook): New.
+       (emoney-quit-after-hook): New.
+       (emoney-quit): Use them.
+
+2004-03-23  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * eMoney 0.02 "Bankruptcy" is released.
+
+       * Makefile (VER): 0.02.
+
+       * emoney.el (emoney-transfer-account-history): New.
+       (emoney-transfer-funds): New.
+       (emoney-setup-control-buffer): Add a "Transfer" button.
+       (emoney-mode-menu): Add a "Transfer Funds" entry, and a "New A/C"
+       entry.  
+       (emoney-chart-of-accounts): Set sane defaults.
+       (emoney-version): Bump to 0.02.
+       (emoney-codename): "Bankruptcy".
+
+2004-01-29  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * emoney.el (emoney-version): 0.02pre7
+       (emoney-setup-control-buffer): Rename "Rec Trans" button to "End
+       Trans".
+       Add help-echo strings for each button.
+       (emoney-summarise-cheques): Use `switch-to-buffer' instead of
+       `pop-to-buffer'. 
+
+2004-01-21  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * emoney.el: Drag in `calc'.
+
+       * Makefile (dist): New target for creating source tarballs.
+
+2004-01-20  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * emoney.el (emoney-switch-to-account): Guard against inf-loops.
+       (emoney-setup-control-buffer): Add a "Exit" button.
+       (emoney-append-transaction): Add arguments so it can be called
+       non-interactively. 
+       (emoney-new-account): Write it.
+       (emoney-version): Bump to 0.02pre6
+
+2004-01-19  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * emoney.el (emoney-setup-control-buffer): Add a "Calculator"
+       button to invoke Emacs Calc.    
+       (emoney-old-window-config): New.
+       (emoney-quit): Use it.
+       (emoney): Ditto.
+       (emoney-version): Bump to 0.02pre5
+
+2004-01-17  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * emoney.el (emoney): Ensure that `emoney-current-account-name' is
+       always initialised to `emoney-default-account' when eMoney starts
+       up.     
+       (emoney-recalculate-buffer): Use `message-or-box' instead of
+       `message'. 
+       (emoney-recalculate-region): Ditto.
+       (emoney-switch-to-account): Guard against messing up the window
+       configuration regardless of which buffer point is in when this
+       function is called.  Always leave point in the "Account Register"
+       buffer. 
+       (emoney-accounts-buffer-map): Remove the binding for RET.
+       (emoney-version): Bump to 0.02pre4
+
+2004-01-16  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * Makefile (distclean): Remove TAGS files too.
+       (all): Build autoloads and custom-loads before byte-compiling
+       anything. 
+       (compile): Byte-compile all files from a single instance of
+       XEmacs. 
+       (auto-autoloads.el): Don't byte-compile here, do it at `compile'
+       target. 
+       (custom-load.el): Ditto.
+
+       * emoney.el: Require wid-edit. 
+       (emoney-switch-to-account): New.
+       (emoney-accounts-buffer-map): New.
+       (emoney-setup-accounts-buffer): Use them.
+       (emoney-new-account): New.  Empty function, to be written.
+       (emoney-setup-control-buffer):
+       s/emoney-current-account/emoney-current-account-name/ 
+       (emoney-version): Bump to 0.02pre3
+
+2004-01-15  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * emoney.el (emoney-show-buffers): Fix buffer layout.
+       (emoney-setup-accounts-buffer): Only turn off scrollbars and
+       modeline in this buffer, not globally.
+       (emoney-setup-header-buffer): Ditto.
+       (emoney-setup-control-buffer): Ditto.
+       (emoney-mode): Don't insert a header into the account file because
+       there is now a static buffer containing the header.
+       (emoney-setup-header-buffer): Insert blank line between a/c name
+       and header.     
+       (emoney-insert-header-maybe): Removed.
+       (emoney-codename): Update.
+       (emoney-version): Bump to 0.02pre2
+
+       * codenames: New file.
+
+2004-01-14  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * emoney.el (emoney-use-new-frame): New.
+       (emoney-accounts-buffer-width): New.
+       (emoney-accounts-buffer-height): New.
+       (emoney-header-buffer-height): New.
+       (emoney-accounts-buffer): New.
+       (emoney-control-buffer): New.
+       (emoney-header-buffer): New.
+       (emoney-setup-accounts-buffer): New.
+       (emoney-current-account-name): New.
+       (emoney-setup-header-buffer): New.
+       (emoney-setup-control-buffer): New.
+       (emoney-show-buffers): New.
+
+2004-01-14  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * emoney.el (emoney-version): Bump to 0.02pre1
+
+       * Makefile (compile): New target.
+       (all): Use it.
+       (distclean): Remove `core*' instead of just `core'.
+
+       * emoney.el (emoney): New.
+       (emoney-quit): New.
+       (emoney-recalculate-on-quit): New.
+       (emoney-mode-menu): Add `emoney-quit'.
+
+2004-01-13  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * emoney.el (emoney-accounts-directory): New.
+       (emoney-chart-of-accounts): New.
+       (emoney-default-account): New.
+
+2003-10-03  Steve Youngs  <sryoungs@bigpond.net.au>
+
+       * emoney.el: Update my email address.
+
+2003-06-04  Steve Youngs  <youngs@xemacs.org>
+
+       * Makefile: New.
+
+       * emoney.el: New.
+
diff --git a/Makefile b/Makefile
new file mode 100644 (file)
index 0000000..59f0175
--- /dev/null
+++ b/Makefile
@@ -0,0 +1,169 @@
+## Makefile for eMoney   -*-Makefile-*-
+## $Id: Makefile,v 1.6 2004/06/29 23:31:14 youngs Exp $
+##
+## Copyright (C) 2003 - 2007 Steve Youngs
+##
+## This file is part of eMoney.
+##
+## Redistribution and use in source and binary forms, with or without
+## modification, are permitted provided that the following conditions
+## are met:
+##
+## 1. Redistributions of source code must retain the above copyright
+##    notice, this list of conditions and the following disclaimer.
+##
+## 2. Redistributions in binary form must reproduce the above copyright
+##    notice, this list of conditions and the following disclaimer in the
+##    documentation and/or other materials provided with the distribution.
+##
+## 3. Neither the name of the author nor the names of any contributors
+##    may be used to endorse or promote products derived from this
+##    software without specific prior written permission.
+##
+## THIS SOFTWARE IS PROVIDED BY THE AUTHOR "AS IS" AND ANY EXPRESS OR
+## IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+## WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+## DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+## FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+## CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+## SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
+## BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+## WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
+## OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
+## IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+PACKAGE = emoney
+VER = 0.6
+
+# csh... yell no, we won't go!
+SHELL = /bin/sh
+
+# Programs and their flags.
+ifndef XEMACS
+  XEMACS = sxemacs
+endif
+XEMACS_FLAGS = -batch -no-autoloads
+INSTALL = install
+PKG_INSTALL = $(INSTALL)
+TAR = tar
+TAR_FLAGS = \
+       --create \
+       --owner=0 \
+       --group=0 \
+       --gzip \
+       --file
+
+
+# Our prefix.  Everything hangs off this.  
+ifndef PREFIX
+  ifeq ('$(XEMACS)','sxemacs')
+    PREFIX = /usr/local/share/sxemacs/site-packages
+  else
+    PREFIX = /usr/local/lib/xemacs/site-packages
+  endif
+endif
+
+# Where the lisp files go.
+LISP_DIR = $(PREFIX)/lisp/$(PACKAGE)
+
+# If you want to make a tarball that you can just unpack on all your
+# PC's you can 'make pkg'.  The 'pkg' target uses these directories to
+# build the tarball.
+STAGING = ../build-pkg
+INFO_STAGING = $(STAGING)/info
+LISP_STAGING = $(STAGING)/lisp/$(PACKAGE)
+
+
+############################################################################
+##                No User Configurable Items Below Here                   ##
+############################################################################
+
+SOURCES = $(wildcard ./emoney*.el)
+OBJECTS = $(SOURCES:.el=.elc)
+EXTRA_SRC =
+EXTRA_OBJ = $(wildcard ./auto-autoloads.el*) $(wildcard ./custom-load.el*)
+
+PRELOADS = -eval \("push default-directory load-path"\)
+AUTOLOAD_PACKAGE_NAME = (setq autoload-package-name \"$(PACKAGE)\")
+AUTOLOAD_FILE = (setq generated-autoload-file \"./auto-autoloads.el\")
+
+
+.SUFFIXES:
+.SUFFIXES: .elc .el
+
+all:: emoney-version.el autoloads customloads compile
+
+autoloads: auto-autoloads.el
+
+customloads: custom-load.el
+
+compile: $(SOURCES) auto-autoloads.el custom-load.el
+       $(XEMACS) $(XEMACS_FLAGS) $(PRELOADS) \
+               -l bytecomp \
+               -l byte-optimize \
+                -f batch-byte-compile $^
+
+auto-autoloads.el : $(SOURCES) emoney-version.el
+       $(XEMACS) $(XEMACS_FLAGS) $(PRELOADS) \
+               -eval "$(AUTOLOAD_PACKAGE_NAME)" \
+               -eval "$(AUTOLOAD_FILE)" \
+               -l autoload -f batch-update-autoloads $^
+       @rm -f $(AUTOLOAD_PATH)/auto-autoloads.el~
+
+custom-load.el : $(SOURCES)
+       $(XEMACS) $(XEMACS_FLAGS) $(PRELOADS) -l cus-dep \
+               -f Custom-make-dependencies ./
+       @touch ./custom-load.el
+       @rm -f ./custom-load.el~
+
+emoney-version.el:
+       echo ";;; Automatically generated file -- DO NOT EDIT OR DELETE" > $@
+       echo ";;;###autoload" >> $@
+       echo "(defconst emoney-version" >> $@
+       if [[ -d "./{arch}" && -x `which tla 2>/dev/null` ]]; then \
+               printf '  "%s"' `tla logs -f|tail -n1` >> $@; \
+       else \
+               echo -n '  "$(VER)"' >> $@; \
+       fi
+       echo ")" >> $@
+       echo "(provide 'emoney-version)" >> $@
+
+version: emoney-version.el
+
+install: all
+       $(INSTALL) -d $(LISP_DIR)
+       $(INSTALL) -m 644 $(SOURCES) $(EXTRA_SRC) $(OBJECTS) $(EXTRA_OBJ) \
+               $(LISP_DIR)
+
+pkg: all
+       $(PKG_INSTALL) -d $(STAGING) $(LISP_STAGING)
+       $(PKG_INSTALL) -m 644 $(SOURCES) $(EXTRA_SRC) $(OBJECTS) $(EXTRA_OBJ) \
+               $(LISP_STAGING)
+       (cd $(STAGING); \
+               $(TAR) $(TAR_FLAGS) $(PACKAGE)-$(VER)-pkg.tar.gz ./*)
+
+upgrade: uninstall install
+
+uninstall:: 
+       rm -rf $(LISP_DIR)
+        # rm -f $(INFO_DIR)/$(INFO_FILES)
+
+
+clean::
+       rm -f $(OBJECTS) $(INFO_FILES) \
+               auto-autoloads.el* custom-load.el*
+
+distclean: clean
+       rm -f core* *~ TAGS tags emoney-version.el*
+
+# Developer targets
+tags: TAGS
+
+TAGS: $(SOURCES)
+       etags $(SOURCES)
+
+dist: distclean
+       (cd ../ ; \
+               $(TAR) $(TAR_FLAGS) $(PACKAGE)-$(VER).tar.gz ./$(PACKAGE)/)
+
+.PHONY: emoney-version.el version
diff --git a/TODO b/TODO
new file mode 100644 (file)
index 0000000..ea3d49c
--- /dev/null
+++ b/TODO
@@ -0,0 +1,48 @@
+-*- outline -*-
+
+What appears here is a list of _possible_ additions/improvements to
+eMoney.  They are in no order of priority, and just because something
+is listed here, doesn't mean that it will one day become part of
+eMoney. 
+
+* Credit card a/c's.
+
+Credit a/c's should show the credit limit, available credit, and
+amount currently owing.
+
+* Recurring transactions.
+
+Probably use abbrevs to "remember" certain transactions.
+
+* Bank reconciliation.
+
+Something akin to the way Quicken does it... displaying a list of
+uncleared transactions that you mark as cleared from your bank
+statement.  BTW, you should know that the last time I used Quicken, it
+was the M$-DOS version (there wasn't a windoze version), so my memory
+could be a little hazy.
+
+* End of year stuff.
+
+For folks who want to keep each year's transactions in separate
+files. 
+
+* Simple reporting (P/L, balance sheet etc).
+
+This might turn into a simple "show transactions where foo=bar" type
+of thing.
+
+* Currency conversion.
+
+There's gotta be some web site we could hook into for this.
+
+* Stock quotes.
+
+See Currency conversion
+
+* Invoicing.
+
+* Import/Export to and from Gnucash format (maybe).
+
+* Import/Export to and from Quicken qif format (maybe).
+
diff --git a/codenames b/codenames
new file mode 100644 (file)
index 0000000..f8379e8
--- /dev/null
+++ b/codenames
@@ -0,0 +1,51 @@
+Accountant
+Actuary
+Bankruptcy
+Blue Chip
+Capital Gain
+Currency
+Deficit
+Depreciation
+Encumbrance
+Equity
+Finance
+Fiscal
+General Ledger
+Gross Domestic Product
+Homo Economicus
+Hostile Takeover
+Income Tax
+Inflation
+Joint Account
+Junk Bond
+Keogh Plan
+Kickback
+Letter of Credit
+Leveraged Buyout
+Managed Account
+Marginal Tax Rate
+Negative Gearing
+Nest Egg
+Offshore Mutual Fund
+Online Banking
+Paid-Up Capital
+Petty Cash
+Quality of Earnings
+Quid Pro Quo
+Real Rate of Return
+Red Chip
+Sales Tax
+Shotgun Clause
+Tangible Asset
+Tax Haven
+Undervalued
+Unlisted Security
+Variable Cost
+Vertical Market
+Wall Street
+White Elephant
+Xenocurrency
+Year To Date
+Yield
+Zero Balance
+Zombies
diff --git a/emoney.el b/emoney.el
new file mode 100644 (file)
index 0000000..b0fc78f
--- /dev/null
+++ b/emoney.el
@@ -0,0 +1,1676 @@
+;; emoney.el --- A home finance package.
+
+;; Copyright (C) 2003 - 2009 Steve Youngs
+
+;; Author:        Steve Youngs <steve@sxemacs.org>
+;; Maintainer:    Steve Youngs <steve@sxemacs.org>
+;; Created:       <2003-06-04>
+;; Keywords:      money finance banking cash
+
+;; This file is part of eMoney.
+
+;; Redistribution and use in source and binary forms, with or without
+;; modification, are permitted provided that the following conditions
+;; are met:
+;;
+;; 1. Redistributions of source code must retain the above copyright
+;;    notice, this list of conditions and the following disclaimer.
+;;
+;; 2. Redistributions in binary form must reproduce the above copyright
+;;    notice, this list of conditions and the following disclaimer in the
+;;    documentation and/or other materials provided with the distribution.
+;;
+;; 3. Neither the name of the author nor the names of any contributors
+;;    may be used to endorse or promote products derived from this
+;;    software without specific prior written permission.
+;;
+;; THIS SOFTWARE IS PROVIDED BY THE AUTHOR "AS IS" AND ANY EXPRESS OR
+;; IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+;; WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+;; DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+;; FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+;; CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+;; SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
+;; BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+;; WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
+;; OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
+;; IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+;;; Commentary:
+;;
+;;  eMoney is based on balance.el, originally by Jason Baietto
+;;  <jason@ssd.csd.harris.com> and later maintained by Bob Newell
+;;  <bnewell@alum.mit.edu>.
+;;
+;;  eMoney tries to give the user a reasonably self-contained finance
+;;  solution.  The target audience is the home user and possibly the
+;;  small (very small) business operator.  It probably will never be
+;;  compatible with any commercial finance packages available.
+;;
+;;  Right now, eMoney is nothing more than a very simple cash book
+;;  program.  Use it to balance your cheque book.  See the "Todo:"
+;;  section for a partial list of possible upcoming features.
+;;
+;;  Installation (from source):
+;;
+;;    tar zxf emoney-x.xx.tar.gz
+;;    cd emoney-x.xx
+;;    check the paths in Makefile
+;;    make
+;;    make install (you may need to be root for this)
+;;
+;;  Installation (from XEmacs package tarball):
+;;
+;;    cd /usr/local/share/sxemacs/site-packages
+;;     (/usr/local/lib/xemacs/site-packages for XEmacs)
+;;    tar zxf /path/to/emoney-x.xx-pkg.tar.gz
+;;
+;;  (Re)start (S)XEmacs and do `M-x emoney RET'
+;;
+;;  You can also invoke `emoney-mode' by simply visiting a file with a
+;;  `.emy' extension.
+;;
+;; Please note that I use SXEmacs exclusively, I have no idea whether
+;; or not this will run or even byte-compile with GNU/Emacs (it _will_
+;; work fine with XEmacs).  Also, I have no desire or intentions of
+;; making this package portable between XEmacs and GNU/Emacs.  Harsh
+;; words?  No, not really, I simply don't have the time or resources to
+;; invest in the extra work involved.  And also there is no way that
+;; I'd be able to support GNU/Emacs users because I'm not familiar with
+;; that flavour of Emacs.  If you want to port it, be my guest, this is
+;; an Open Source project.
+;;
+;; Another note: This package uses correct English spelling wherever
+;; possible.  For example, "cheque" instead of "check", "summarise"
+;; instead of "summarize".  Although I welcome and encourage _ALL_
+;; contributions, patches that s/que/ch/ or s/ise/ize/ will go straight
+;; to /dev/null.
+
+;;; ChangeLog:
+;;
+;;  This is just a place holder so `emoney-commentary' will work
+;;  properly.  See the ChangeLog file for changes.
+
+;;; Code:
+
+;; Drag in what we need.
+(eval-and-compile
+  (autoload 'calc "calc" nil t)
+  (autoload 'clear-rectangle "rect" nil t)
+  (autoload 'completing-read "minibuf")
+  (autoload 'customize-group "cus-edit")
+  (autoload 'lm-commentary "lisp-mnt")
+  (autoload 'sort-numeric-fields "sort" nil t)
+  (autoload 'untabify "tabify" nil t)
+  (autoload 'with-electric-help "ehelp")
+  (require 'wid-edit))
+
+(eval-when-compile
+  (autoload 'eval-when "cl-macs" nil nil 'macro)
+  (autoload 'calc-quit "calc" nil t)
+  (require 'advice)
+  (defvar calc-was-split)
+  (autoload 'browse-url "browse-url" nil t)
+  (autoload 'regexp-opt "regexp-opt"))
+
+;; Custom.
+(defgroup emoney nil
+  "Customisations for `emoney-mode'."
+  :prefix "emoney-"
+  :group 'tools)
+
+(defcustom emoney-accounts-buffer-width 30
+  "How wide in columns for the accounts buffer."
+  :type 'integer
+  :group 'emoney)
+
+(defcustom emoney-accounts-buffer-height 9
+  "How high in lines for the accounts buffer."
+  :type 'integer
+  :group 'emoney)
+
+(defcustom emoney-header-buffer-height 4
+  "How high in lines for the header buffer."
+  :type 'integer
+  :group 'emoney)
+
+(defcustom emoney-accounts-directory (file-name-as-directory
+                                     (expand-file-name ".emoney"
+                                                       (user-home-directory)))
+  "*The directory where your eMoney account files are located."
+  :type 'directory
+  :group 'emoney)
+
+(defcustom emoney-history-directory (file-name-as-directory
+                                    (expand-file-name "history"
+                                                      emoney-accounts-directory))
+  "*Directory containing previous years account files."
+  :type 'directory
+  :group 'emoney)
+
+(defcustom emoney-chart-of-accounts
+  (if (file-directory-p emoney-accounts-directory)
+      (directory-files emoney-accounts-directory nil "\\.emy$" nil t)
+    nil)
+  "*A list of eMoney accounts in `emoney-accounts-directory'."
+  :type '(repeat 
+         (string :tag "Account Name"))
+  :group 'emoney)
+
+(defcustom emoney-default-account (or (car emoney-chart-of-accounts)
+                                     "default.emy")
+  "*The default eMoney account to use.
+
+This is the account that has the focus when you start eMoney."
+  :type 'string
+  :group 'emoney)
+
+(defcustom emoney-credit-transaction-types
+  '("autotellcr" "atmcr" "bankcredit" "bcr" "deposit" "dep" "directcr"
+    "dcr" "internetcr" "netcr" "phonecr" "phcr")
+  "*List of valid credit transaction types.
+
+The default types are:
+
+          autotellcr -- Automatic Teller Machine deposit
+               atmcr -- short version of 'autotellcr'
+
+          bankcredit -- Bank initiated credits like interest etc
+                 bcr -- short version of 'bankcredit'
+
+             deposit -- Manual, non-direct deposits
+                 dep -- short version of 'deposit'
+
+            directcr -- Direct credit transactions
+                 dcr -- short version of 'directcr'
+
+          internetcr -- Internet credit transactions
+               netcr -- short version of 'internetcr'
+
+             phonecr -- Telephone credit transactions
+                phcr -- short version of 'phonecr'"
+  :type '(repeat string)
+  :group 'emoney)
+
+(defcustom emoney-debit-transaction-types
+  '("autotelldb" "atmdb" "bankfee" "fee" "directdb" "ddb" "eftpos"
+    "eft" "internetdb" "netdb" "phonedb" "phdb" "withdrawal" "wdl")
+  "*List of valid debit transaction types.
+
+The default types are:
+
+          autotelldb -- Automatic Teller Machine transaction
+               atmdb -- short version of 'autoteller'
+
+             bankfee -- Bank fees
+                 fee -- short version of 'bankfee'
+
+            directdb -- Direct debit transactions
+                 ddb -- short version of 'directdb'
+
+              eftpos -- Electronic Funds Transfer Point Of Sale
+                 eft -- short version of 'eftpos'
+
+          internetdb -- Internet transactions
+               netdb -- short version of 'internet'
+
+             phonedb -- Telephone transactions
+                phcr -- short version of 'phone'
+
+          withdrawal -- Over the counter withdrawal.
+                 wdl -- short version of 'withdrawal'"
+  :type '(repeat string)
+  :group 'emoney)
+
+(defcustom emoney-cr-transfer-transaction-type "xfrcr"
+  "*Credit transfer transaction types."
+  :type 'string
+  :group 'emoney)
+
+(defcustom emoney-db-transfer-transaction-type "xfrdb"
+  "*Debit transfer transaction type."
+  :type 'string
+  :group 'emoney)
+
+(defcustom emoney-date-format "%Y-%m-%d"
+  "*The format that `emoney-mode' uses for dates."
+  :type '(choice
+         (const :tag "yyyy-mm-dd"
+                :value "%Y-%m-%d")
+         (const :tag "yyyy/mm/dd"
+                :value "%Y/%m/%d")
+         (const :tag "mm/dd/yy"
+                :value "%m/%d/%y")
+         (const :tag "mm/dd/yyyy"
+                :value "%m/%d/%Y")
+         (const :tag "mm-dd-yy"
+                :value "%m-%d-%y")
+         (const :tag "mm-dd-yyyy"
+                :value "%m-%d-%Y")
+         (const :tag "dd/mm/yy"
+                :value "%d/%m/%y")
+         (const :tag "dd/mm/yyyy"
+                :value "%d/%m/%Y")
+         (const :tag "dd-mm-yy"
+                :value "%d-%m-%y")
+         (const :tag "dd-mm-yyyy"
+                :value "%d-%m-%Y")
+         (const :tag "yy/mm/dd"
+                :value "%y/%m/%d")
+         (const :tag "yy-mm-dd"
+                :value "%y-%m-%d"))
+  :group 'emoney)
+
+(defcustom emoney-uk-cheque-spelling t
+  "*When non-nil, use UK spelling: \"chq\" instead of \"chk\"."
+  :type 'boolean
+  :group 'emoney)
+
+(defcustom emoney-save-after-recalculate t
+  "*If non-nil, save the buffer after a recalculate.
+
+See `emoney-recalculate-buffer'."
+  :type 'boolean
+  :group 'emoney)
+
+(defcustom emoney-recalculate-on-quit nil
+  "*If non-nil, recalculate each eMoney account buffer when quitting eMoney."
+  :type 'boolean
+  :group 'emoney)
+
+(defcustom emoney-use-new-frame nil
+  "*If non-nil, eMoney will start in a new frame."
+  :type 'boolean
+  :group 'emoney)
+
+(defcustom emoney-bank-url "unset"
+  "The URL of your bank's web page."
+  :type 'string
+  :group 'emoney)
+
+;; Hooks
+(defgroup emoney-hooks nil
+  "Various hooks for eMoney."
+  :prefix "emoney-"
+  :group 'emoney)
+
+(defcustom emoney-mode-hooks nil
+  "*Hooks run after `emoney-mode' is entered."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-switch-account-hook nil
+  "*Hooks run after switching accounts."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-setup-accounts-buffer-hook nil
+  "*Hooks run after setting up the accounts buffer."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-setup-header-buffer-hook nil
+  "*Hooks run after setting up the header buffer."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-setup-control-buffer-hook nil
+  "*Hooks run after setting up the control buffer."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-transaction-hook nil
+  "*Hooks run after appending a new transaction.
+
+These hooks are run after any new transaction, including cheque
+and transfers.  If you want to do additional things with cheque or
+transfer transactions, see `emoney-transaction-cheque-hook' &
+`emoney-transaction-transfer-hook'."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-transaction-cheque-hook nil
+  "*Hooks run after appending a cheque transaction."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-transaction-transfer-hook nil
+  "*Hooks run after appending a transfer transaction."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-recalculate-before-hook nil
+  "*Hooks run just prior to recalculating an eMoney buffer.
+
+See `emoney-recalculate-after-hook' for doing things after recalculating."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-recalculate-after-hook nil
+  "*Hooks run just after recalculating an eMoney buffer.
+
+See `emoney-recalculate-before-hook' for doing things before recalculating."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-summarise-cheques-hook nil
+  "*Hooks run after doing `emoney-summarise-cheques'."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-new-account-hook nil
+  "*Hooks run after creating a new account."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-quit-before-hook nil
+  "*Hooks run just prior to eMoney exiting."
+  :type 'hook
+  :group 'emoney-hooks)
+
+(defcustom emoney-quit-after-hook nil
+  "*Hooks run as the last thing when eMoney exits."
+  :type 'hook
+  :group 'emoney-hooks)
+
+;; Faces
+(defgroup emoney-faces nil
+  "eMoney faces."
+  :prefix "emoney-"
+  :group 'emoney)
+
+(make-face 'emoney-account-name-face)
+(set-face-parent 'emoney-account-name-face 'font-lock-variable-name-face)
+
+(make-face 'emoney-debit-face)
+(set-face-parent 'emoney-debit-face 'font-lock-warning-face)
+
+(make-face 'emoney-credit-face)
+(set-face-parent 'emoney-credit-face 'font-lock-function-name-face)
+
+(make-face 'emoney-date-face)
+(set-face-parent 'emoney-date-face 'font-lock-keyword-face)
+
+(make-face 'emoney-clear-tran-face)
+(set-face-parent 'emoney-clear-tran-face 'font-lock-string-face)
+
+(make-face 'emoney-unclear-tran-face)
+(set-face-parent 'emoney-unclear-tran-face 'font-lock-comment-face)
+
+(make-face 'emoney-header-face)
+(set-face-parent 'emoney-header-face 'font-lock-comment-face)
+
+(defcustom emoney-account-name-face 'emoney-account-name-face
+  "Face for highlighting eMoney account names."
+  :type 'face
+  :group 'emoney-faces)
+
+(defcustom emoney-debit-face 'emoney-debit-face
+  "Face for highlighting debit amounts in eMoney."
+  :type 'face
+  :group 'emoney-faces)
+
+(defcustom emoney-credit-face 'emoney-credit-face
+  "Face for highlighting credit amounts in eMoney."
+  :type 'face
+  :group 'emoney-faces)
+
+(defcustom emoney-date-face 'emoney-date-face
+  "Face for highlighting dates in eMoney."
+  :type 'face
+  :group 'emoney-faces)
+
+(defcustom emoney-clear-tran-face 'emoney-clear-tran-face
+  "Face for highlighting cleared transactions in eMoney."
+  :type 'face
+  :group 'emoney-faces)
+
+(defcustom emoney-unclear-tran-face 'emoney-unclear-tran-face
+  "Face for highlighting uncleared transactions in eMoney."
+  :type 'face
+  :group 'emoney-faces)
+
+(defcustom emoney-header-face 'emoney-header-face
+  "Face for highlighting the column header in eMoney."
+  :type 'face
+  :group 'emoney-faces)
+
+;;; Internal variables
+(defconst emoney-codename "Equity"
+  "The codename of the current version of eMoney.")
+
+(defconst emoney-is-beta t
+  "Non-nil if the current version of eMoney is beta.")
+
+(eval-when (load eval)
+  (unless (file-directory-p emoney-accounts-directory)
+    (make-directory-path emoney-accounts-directory)))
+
+(require 'emoney-version)
+
+;;;###autoload
+(defun emoney-version (&optional arg)
+  "*Display the current version information for eMoney.
+
+Optional prefix Argument ARG, print version information at point
+in the current buffer."
+  (interactive "P")
+  (if emoney-is-beta
+      (if arg
+         (insert (format "eMoney: %s, \"%s\" [Beta]"
+                         emoney-version emoney-codename))
+       (message (format "eMoney: %s, \"%s\" [Beta]"
+                        emoney-version emoney-codename)))
+    (if arg
+       (insert (format "eMoney: %s, \"%s\""
+                       emoney-version emoney-codename))
+      (message (format "eMoney: %s, \"%s\""
+                      emoney-version emoney-codename)))))
+
+;;;###autoload
+(defun emoney-commentary ()
+  "*Display the commentary section of emoney.el."
+  (interactive)
+  (with-electric-help
+   '(lambda ()
+      (insert
+       (with-temp-buffer
+        (erase-buffer)
+        (insert (lm-commentary (locate-library "emoney.el")))
+        (goto-char (point-min))
+        (while (re-search-forward "^;+ ?" nil t)
+          (replace-match "" nil nil))
+        (buffer-string (current-buffer)))))
+   "*eMoney Commentary*"))
+
+;;;###autoload
+(defun emoney-copyright ()
+  "*Display the copyright notice for eMoney."
+  (interactive)
+  (with-electric-help
+   '(lambda ()
+      (insert
+       (with-temp-buffer
+        (erase-buffer)
+        (insert-file-contents (locate-library "emoney.el"))
+        (goto-char (point-min))
+        (re-search-forward ";;; Commentary" nil t)
+        (beginning-of-line)
+        (narrow-to-region (point-min) (point))
+        (while (re-search-backward "^;+ ?" nil t)
+          (replace-match "" nil nil))
+        (buffer-string (current-buffer)))))
+   "*eMoney Copyright Notice*"))
+
+(defvar emoney-frame nil
+  "The frame where eMoney is displayed, if in a new frame.")
+
+(defconst emoney-accounts-buffer "*eMoney A/C's*"
+  "The buffer that holds the list of eMoney accounts.")
+
+(defconst emoney-control-buffer "*eMoney Control*"
+  "The buffer containing the eMoney control buttons.")
+
+(defconst emoney-header-buffer "*eMoney Header*"
+  "The buffer for the eMoney account register header line.")
+
+(defvar emoney-current-account-name 
+  (file-name-sans-extension emoney-default-account))
+
+(defun emoney-switch-to-account (&optional account)
+  "Switch to account, ACCOUNT."
+  (interactive)
+  (let ((switch-acc (or account
+                       (emoney-completing-read "Switch to A/C: "
+                                               emoney-chart-of-accounts nil t))))
+    (select-window (get-buffer-window
+                   (concat emoney-current-account-name ".emy")))
+    (switch-to-buffer switch-acc)
+    (goto-char (point-max))
+    (setq emoney-current-account-name
+         (file-name-sans-extension switch-acc))
+    (select-window (get-buffer-window emoney-header-buffer))
+    (emoney-setup-header-buffer)
+    (switch-to-buffer emoney-header-buffer)
+    (select-window (get-buffer-window
+                   (concat emoney-current-account-name ".emy")))
+    (run-hooks 'emoney-switch-account-hook)))
+
+(defun emoney-mouse-switch-to-account (event)
+  "Switch to account under EVENT."
+  (interactive "e")
+  (save-excursion
+    (set-buffer (window-buffer (event-window event)))
+    (let ((switch-acc (extent-string (extent-at-event event))))
+      (select-window (get-buffer-window
+                     (concat emoney-current-account-name ".emy")))
+      (switch-to-buffer (concat switch-acc ".emy"))
+      (goto-char (point-max))
+      (setq emoney-current-account-name switch-acc)
+      (select-window (get-buffer-window emoney-header-buffer))
+      (emoney-setup-header-buffer)
+      (switch-to-buffer emoney-header-buffer)))
+  (select-window (get-buffer-window
+                 (concat emoney-current-account-name ".emy")))
+  (run-hooks 'emoney-switch-account-hook))
+
+(defconst emoney-accounts-buffer-map
+  (let* ((map (make-sparse-keymap 'emoney-accounts-buffer-map)))
+    (define-key map [button2] #'emoney-mouse-switch-to-account)
+    map)
+  "A keymap for the extents in eMoney Accounts buffer.")
+
+(defconst emoney-largest-balance "999999999.99"
+  "This is only used for formatting purposes.")
+
+(defun emoney-setup-accounts-buffer ()
+  "Set up the eMoney \"Accounts\" buffer."
+  (let ((buf emoney-accounts-buffer)
+       (accounts emoney-chart-of-accounts)
+       help-msg cbal)
+    (save-excursion
+      (when (buffer-live-p (get-buffer-create buf))
+       (kill-buffer buf))
+      (set-buffer (get-buffer-create buf))
+      (while accounts
+       (setq help-msg (concat "Switch to A/C: "
+                              (file-name-sans-extension (car accounts))))
+       (insert (file-name-sans-extension (car accounts)))
+       (set-extent-properties
+        (make-extent (point-at-bol) (point))
+        `(face emoney-account-name-face
+               mouse-face highlight 
+               help-echo ,help-msg 
+               balloon-help ,help-msg
+               keymap ,emoney-accounts-buffer-map))
+       (with-current-buffer (car accounts)
+         (goto-char (point-max))
+         (re-search-backward "\\s-[\\+-=]\\s-" nil t)
+         (setq cbal (nth 2 (emoney-parse-transaction-data
+                            (buffer-substring (point) (point-at-eol))))))
+         (move-to-column 13 'force)
+       (if cbal
+           (insert-face
+            (format
+             (concat "%"
+                     (number-to-string (- (length emoney-largest-balance)
+                                          (length (format "%.2f" cbal))))
+                     "s$%.2f") "" cbal)
+            (if (< cbal 0)
+                'emoney-debit-face
+              'emoney-credit-face))
+         (insert " Needs Recalc"))
+       (insert "\n")
+       (setq cbal nil)
+       (setq accounts (cdr accounts)))
+      (set-specifier horizontal-scrollbar-visible-p nil (current-buffer))
+      (set-specifier has-modeline-p nil (current-buffer))
+      (run-hooks 'emoney-setup-accounts-buffer-hook))))
+
+(defconst emoney-header
+  "Date       Type       C Description                         Amount      Balance
+===============================================================================\n"
+  "The header inserted at the top of a `emoney-mode' buffer.")
+
+(defun emoney-setup-header-buffer ()
+  "Set up the eMoney \"Account Register Header\" buffer."
+  (let ((buf emoney-header-buffer))
+    (save-excursion
+      (when (buffer-live-p (get-buffer-create buf))
+       (kill-buffer buf))
+      (set-buffer (get-buffer-create buf))
+      (insert-face emoney-current-account-name 'emoney-account-name-face)
+      (insert "\n\n")
+      (insert-face emoney-header 'emoney-header-face)
+      (set-specifier horizontal-scrollbar-visible-p nil (current-buffer))
+      (set-specifier vertical-scrollbar-visible-p nil (current-buffer))
+      (set-specifier has-modeline-p nil (current-buffer))
+      (goto-char (point-min))
+      (run-hooks 'emoney-setup-header-buffer-hook))))
+
+;;;###autoload
+(defun emoney-customise ()
+  "*Convenience function to customise eMoney."
+  (interactive)
+  (customize-group 'emoney))
+
+;; Because lots of people in the world can't spell.
+;;;###autoload
+(defalias 'emoney-customize 'emoney-customise)
+
+(defvar emoney-transaction-types '("init" "")
+  "A list of valid transaction types.
+
+It is a combination of `emoney-credit-transaction-types',
+`emoney-debit-transaction-types', and a blank type.")
+
+(defconst emoney-cheque-type
+  (if emoney-uk-cheque-spelling
+      "chq[ \t]+\\([0-9]+\\)"
+    "chk[ \t]+\\([0-9]+\\)")
+  "Type field for cheque transactions.
+
+This is defined separately from the other transaction types because
+it is used by functions that perform special operations on cheque.
+transactions.")
+
+(defconst emoney-date-column 0
+  "Column where transaction date begins.")
+
+(defconst emoney-type-column 11
+  "Column where transaction type begins.")
+
+(defconst emoney-clear-column 22
+  "Column where status appears.")
+
+(defconst emoney-description-column 24
+  "Column where transaction description begins.")
+
+(defconst emoney-sign-column 52
+  "Column where transaction sign begins.")
+
+(defconst emoney-amount-column 54
+  "Column where transaction amount begins.")
+
+(defconst emoney-current-balance-column 65
+  "Column where current emoney begins.")
+
+(defconst emoney-tab-stop-list
+  (list
+   emoney-date-column
+   emoney-type-column
+   emoney-clear-column
+   emoney-description-column
+   emoney-sign-column
+   emoney-amount-column
+   emoney-current-balance-column)
+  "List of tab stops that define the start of all transaction fields.")
+
+(defvar emoney-mode-map
+  (let ((map (make-sparse-keymap 'emoney-mode-map)))
+    (define-key map [(control c) (control b)] #'emoney-backward-field)
+    (define-key map [(control c) (control c)] #'emoney-recalculate-buffer)
+    (define-key map [(control c) (control d)] #'emoney-clear-current-field)
+    (define-key map [(control c) (control f)] #'emoney-forward-field)
+    (define-key map [(control c) (control n)] #'emoney-append-next-cheque)
+    (define-key map [(control c) (control r)] #'emoney-summarise-cheques-region)
+    (define-key map [(control c) (control s)] #'emoney-summarise-cheques-buffer)
+    (define-key map [(control c) (control t)] #'emoney-append-transaction)
+    (define-key map [(control c) (control x)] #'emoney-transfer-funds)
+    (define-key map [tab]                     #'emoney-forward-field)
+    (define-key map [(control c) b]           #'emoney-go-to-bank)
+    (define-key map [(control c) c]           #'emoney-calc)
+    (define-key map [(control c) s]           #'emoney-switch-to-account)
+    (define-key map [(control c) q]           #'emoney-quit)
+    (define-key map [(control c) (control q)] #'emoney-recalc-and-exit)
+    map)
+  "Keymap for emoney buffer.")
+
+(defconst emoney-mode-menu
+  '("eMoney"
+    ["New A/C" emoney-new-account t]
+    "---"
+    [(concat "New "
+            (if emoney-uk-cheque-spelling
+                "Cheque "
+              "Check ")
+            "Transaction") emoney-append-next-cheque t]
+    ["New Transaction" emoney-append-transaction t]
+    ["Transfer Funds" emoney-transfer-funds t]
+    "---"
+    ["Next Field" emoney-forward-field t]
+    ["Previous Field" emoney-backward-field t]
+    ["Clear Current Field" emoney-clear-current-field t]
+    "---"
+    [(concat "Summary of "
+            (if emoney-uk-cheque-spelling
+                "cheques "
+              "checks ")
+            "(buffer)") emoney-summarise-cheques-buffer t]
+    [(concat "Summary of "
+            (if emoney-uk-cheque-spelling
+                "cheques "
+              "checks ")
+            "(region)") emoney-summarise-cheques-region t]
+    "---"
+    ["Recalculate Buffer" emoney-recalculate-buffer t]
+    "---"
+    ["Go To The Bank!" emoney-go-to-bank t]
+    ["Calculator" emoney-calc t]
+    "---"
+    ["Recalc All A/C's and Exit" emoney-recalc-and-exit t]
+    ["Exit eMoney" emoney-quit t])
+  "Menu for `emoney-mode' buffers.")
+
+(easy-menu-define
+ emoney-mode-easymenu nil "eMoney" emoney-mode-menu)
+
+(defvar emoney-credit-type-keywords
+  (regexp-opt (append emoney-credit-transaction-types
+                     (list emoney-cr-transfer-transaction-type)))
+  "eMoney font lock keywords for credit tran types")
+
+(defvar emoney-debit-type-keywords
+  (regexp-opt (append emoney-debit-transaction-types
+                     (list emoney-db-transfer-transaction-type)))
+  "eMoney font lock keywords for debit tran types")
+
+(defvar emoney-font-lock-keywords
+  `(("x\\s-\\(.*\\)[\\+-]\\s-" (1 emoney-clear-tran-face))
+    ("o\\s-\\(.*\\)[\\+-]\\s-" (1 emoney-unclear-tran-face))
+    (,emoney-credit-type-keywords . emoney-credit-face)
+    (,emoney-debit-type-keywords . emoney-debit-face)
+    ("\\(^[0-9]+\\(-\\|\\/\\)[0-9]+\\(-\\|\\/\\)[0-9]+\\)"
+     (1 emoney-date-face))
+    ("-\\s-+\\([0-9]+\\.[0-9][0-9]\\)" (1 emoney-debit-face))
+    ("-[0-9]+\\.[0-9]+" . emoney-debit-face)
+    ("[^-]\\([0-9]+\\.[0-9]+$\\)" (1 emoney-credit-face))
+    ("\\+\\s-+\\([0-9]+\\.[0-9][0-9]\\)" (1 emoney-credit-face)))
+  "Font lock keywords for `emoney-mode'.")
+
+
+;;;###autoload
+(defun emoney-mode ()
+  "Major mode for editing a buffer containing financial transactions.
+The following bindings provide the main functionality of this mode:
+
+\\{emoney-mode-map}
+
+Transactions occur on a single line and have the following fields (in
+order):
+
+ date          The transaction date.  See `emoney-date-format'.
+ type          This field must either be blank or match one of the
+               expressions defined in `emoney-credit-transaction-types'
+               and `emoney-debit-transaction-types'.
+ clear         Status of transaction, 'o' is open, 'x' is cleared.  New
+               transactions default to 'o'.
+ description   A possibly blank transaction description.
+ sign          This field must either be '+', '-' or '='.  '+' means
+               credit, '-' means debit, and '=' resets balance.  eMoney
+               will usually guess the correct sign to use.
+ amount        The transaction amount.
+ balance       The balance after this transaction.  This field will be
+               computed upon recalculation, you _don't_ need to fill it
+               in.  Just do: \\[emoney-recalculate-buffer].
+
+Any line in the buffer that does not begin with a date will be
+considered a comment and ignored.  Among other things, this allows
+the transaction description to span several lines.
+
+Changing any amount and recalculating again will update all visible
+balances.  Transactions may be commented out by putting a semi-colon
+\(or any other non-numerical character\) at the beginning of the line.
+
+Entering `emoney-mode' runs the `emoney-mode-hooks' if any exist."
+  (interactive)
+  (kill-all-local-variables)
+  (setq major-mode 'emoney-mode)
+  (setq mode-name "eMoney")
+  (use-local-map emoney-mode-map)
+  (easy-menu-add emoney-mode-easymenu)
+  (make-local-variable 'tab-stop-list)
+  (setq tab-stop-list emoney-tab-stop-list)
+  (make-local-variable 'indent-tabs-mode)
+  (setq indent-tabs-mode nil)
+  (setq indent-line-function 'emoney-forward-field)
+  (overwrite-mode 1)
+  (run-hooks 'emoney-mode-hooks))
+
+(defun emoney-current-line ()
+  "Return the current buffer line at point."
+  (save-excursion
+    (beginning-of-line)
+    (count-lines (point-min) (point))))
+
+(defun emoney-completing-read (prompt table &optional predicate require-match
+                              initial-contents history default)
+  "Like `completing-read', but also accepts strings.
+
+Arguments PROMPT, TABLE, PREDICATE, REQUIRE-MATCH, INITIAL-CONTENTS,
+HISTORY, DEFAULT are as per `completing-read'."
+  (completing-read
+   prompt
+   (if (vectorp table)
+       table
+     (mapcar 'list table))
+   predicate require-match initial-contents history default))
+
+(defun emoney-forward-field ()
+  "Move the cursor to the next field on the current line."
+  (interactive)
+  (move-to-tab-stop))
+
+(defun emoney-go-to-bank (&optional url)
+  "Open your bank's URL with `browse-url'."
+  (interactive)
+  (let ((url (or url
+                emoney-bank-url)))
+    (if (or (equal url "unset")
+           (not url))
+       (message-or-box "Please customise `emoney-bank-url'.")
+      (browse-url url))))
+
+(defun emoney-calc ()
+  "Wrapper around `calc' to get around \"window-edges bug\"."
+  (interactive)
+  (add-hook 'calc-end-hook #'(lambda ()
+                              (setq calc-was-split nil)))
+  (calc))
+
+(defun emoney-last (list)
+  "Return last element in LIST."
+  (cond
+   ((null list)
+    '())
+   ((null (cdr list))
+    (car list))
+   (t (emoney-last (cdr list)))))
+
+(defun emoney-find-largest-less-than (list item)
+  "Search a sorted LIST of numbers, return the largest number that is < ITEM."
+  (let ((list-car (car list))
+       (list-cdr (cdr list))
+       (last nil))
+    (while (and list-car (< list-car item))
+      (setq last list-car)
+      (setq list-car (car list-cdr))
+      (setq list-cdr (cdr list-cdr)))
+    last))
+
+(defun emoney-find-largest-less-than-equal (list item)
+  "Return cdr of LIST starting @ the largest number that is <= to ITEM."
+  (let ((list-car (car list))
+       (list-cdr (cdr list))
+       (last nil))
+    (while (and list-car (<= list-car item))
+      (setq last (cons list-car list-cdr))
+      (setq list-car (car list-cdr))
+      (setq list-cdr (cdr list-cdr)))
+    last))
+
+(defun emoney-find-field (column)
+  "Return a list of the start and end of the field around COLUMN.
+
+End may be nil if column is after the last defined tab stop."
+  (let ((field (emoney-find-largest-less-than-equal
+               emoney-tab-stop-list column)))
+    (if (equal 1 (length field))
+       (list (car field) nil)
+      (list (nth 0 field) (nth 1 field)))))
+
+(defun emoney-backward-field ()
+  "Move the cursor to the previous entry field on the current line."
+  (interactive)
+  (let* ((col (current-column))
+        (prev (emoney-find-largest-less-than emoney-tab-stop-list col)))
+    (if prev
+       (move-to-column prev)
+      (move-to-column (emoney-last emoney-tab-stop-list)))))
+
+(defun emoney-clear-current-field ()
+  "Fill the field around point with spaces, leave point at start of field."
+  (interactive)
+  (let* ((field (emoney-find-field (current-column)))
+         (line-start (progn (beginning-of-line) (point)))
+         (line-end (progn
+                    (end-of-line)
+                    (untabify line-start (point))
+                    (point)))
+         (field-start (+ line-start (nth 0 field)))
+         (field-end (if (nth 1 field)
+                        (+ line-start (nth 1 field))
+                     line-end)))
+    (clear-rectangle field-start field-end)
+    (goto-char field-start)))
+
+(defsubst emoney-build-types-list ()
+  "Dynamically build a list of transaction types.
+
+This is done dynamically so that the user can change or add to the
+list of transaction types without having to reload eMoney."
+  ;; Initialise to ("init" "").
+  (setq emoney-transaction-types '("init" ""))
+  ;; Load the debit and credit transaction types.
+  (setq emoney-transaction-types
+       (append emoney-transaction-types
+               emoney-debit-transaction-types
+               emoney-credit-transaction-types
+               (list emoney-cr-transfer-transaction-type)
+               (list emoney-db-transfer-transaction-type))))
+
+;; Stolen from Gnus' time-date.el
+(defun emoney-days-to-time (days)
+  "Convert DAYS into a time value."
+  (let* ((seconds (* 1.0 days 60 60 24))
+        (rest (expt 2 16))
+        (ms (condition-case nil (floor (/ seconds rest))
+              (range-error (expt 2 16)))))
+    (list ms (condition-case nil (round (- seconds (* ms rest)))
+              (range-error (expt 2 16))))))
+
+;; Stolen from Gnus' time-date.el
+(defun emoney-time-add (t1 t2)
+  "Add two time values.  One should represent a time difference."
+  (let ((high (car t1))
+       (low (if (consp (cdr t1)) (nth 1 t1) (cdr t1)))
+       (micro (if (numberp (car-safe (cdr-safe (cdr t1))))
+                  (nth 2 t1)
+                0))
+       (high2 (car t2))
+       (low2 (if (consp (cdr t2)) (nth 1 t2) (cdr t2)))
+       (micro2 (if (numberp (car-safe (cdr-safe (cdr t2))))
+                   (nth 2 t2)
+                 0)))
+    ;; Add
+    (setq micro (+ micro micro2))
+    (setq low (+ low low2))
+    (setq high (+ high high2))
+
+    ;; Normalize
+    ;; `/' rounds towards zero while `mod' returns a positive number,
+    ;; so we can't rely on (= a (+ (* 100 (/ a 100)) (mod a 100))).
+    (setq low (+ low (/ micro 1000000) (if (< micro 0) -1 0)))
+    (setq micro (mod micro 1000000))
+    (setq high (+ high (/ low 65536) (if (< low 0) -1 0)))
+    (setq low (logand low 65535))
+
+    (list high low micro)))
+
+(defun emoney-append-transaction (&optional trans-type description amount)
+  "Add a transaction to the end of current buffer using today's date."
+  (interactive)
+  (goto-char (point-max))
+  (if (not (equal 0 (current-column)))
+      (newline))
+  (let* ((date-variance
+         (read-number "Date (RET for current; -DAYS past; DAYS future): "
+                      'integers-only "0"))
+        (tran-date
+         (format-time-string emoney-date-format
+                             (emoney-time-add
+                              (current-time)
+                              (emoney-days-to-time date-variance)))))
+    (insert tran-date))
+  (move-to-tab-stop)
+  (emoney-build-types-list)
+  (let* ((type (or trans-type
+                  (emoney-completing-read "Transaction type: "
+                                          emoney-transaction-types))))
+    (insert type)
+    (move-to-tab-stop)
+    (insert "o")
+    (move-to-tab-stop)
+    (let ((before-descript (point))
+         (start-column (current-column))
+         (fill-column (- emoney-sign-column
+                         emoney-description-column
+                         1)))
+      (save-excursion
+       (insert (or description
+                   (read-string "Description: ")))
+       (save-restriction
+         (narrow-to-region before-descript (point))
+         (goto-char before-descript)
+         (while (progn (move-to-column fill-column) (not (eobp)))
+           (search-forward " " nil t)
+           (insert "\n"))
+         (fill-paragraph 1)
+         (goto-char before-descript)
+         (forward-line 1)
+         (while (progn (beginning-of-line) (not (eobp)))
+           (indent-to-column start-column)
+           (forward-line 1)))))
+    (move-to-tab-stop)
+    (cond ((or (member type emoney-credit-transaction-types)
+              (string= type emoney-cr-transfer-transaction-type))
+          (insert "+"))
+         ((or (member type emoney-debit-transaction-types)
+              (string= type emoney-db-transfer-transaction-type))
+          (insert "-"))
+         ((string= type "init")
+          (insert "="))
+         (t (if (y-or-n-p "Is this a credit transaction? ")
+                (insert "+")
+              (if (y-or-n-p "Is this a debit transaction? ")
+                  (insert "-")
+                (if (y-or-n-p "Is this an initialising transaction? ")
+                    (insert "=")
+                  (warn "Couldn't determine +/-/=, leaving blank"))))))
+    (move-to-tab-stop)
+    (insert (if amount
+               (number-to-string amount)
+             (read-string "Amount: ")))
+    (run-hooks 'emoney-transaction-hook)))
+
+(defun emoney-append-next-cheque ()
+  "Add a cheque transaction to the end of the current buffer using today's date.
+
+Inserts the cheque number following the last cheque number written into the
+transaction type column.  Loses if you write cheques out of order."
+  (interactive)
+  (goto-char (point-max))
+  (if (not (equal 0 (current-column)))
+      (newline))
+  (insert (format-time-string emoney-date-format))
+  (move-to-tab-stop)
+  (let (cheque cheque-number noinit)
+    (save-excursion
+      (if (search-backward-regexp emoney-cheque-type 0 t)
+         (progn
+           (setq cheque (buffer-substring (match-beginning 1) (match-end 1)))
+           (setq noinit nil))
+       (move-to-column emoney-type-column)
+       (if (< (current-column) emoney-type-column)
+           (indent-to-column emoney-type-column))
+       (if emoney-uk-cheque-spelling
+           (insert "chq 000001")
+         (insert "chk 000001"))
+       (setq noinit t)))
+    (unless noinit
+      (setq cheque-number (1+ (string-to-number cheque)))
+      (move-to-column emoney-type-column)
+      (if (< (current-column) emoney-type-column)
+         (indent-to-column emoney-type-column))
+      (if emoney-uk-cheque-spelling
+         (insert (format "chq %06d" cheque-number))
+       (insert (format "chk %06d" cheque-number))))
+    (move-to-tab-stop)
+    (insert "o")
+    (move-to-tab-stop)
+    (let ((before-descript (point))
+         (start-column (current-column))
+         (fill-column (- emoney-sign-column
+                         emoney-description-column
+                         1)))
+      (save-excursion
+       (insert (read-string "Payable To: "))
+       (save-restriction
+         (narrow-to-region before-descript (point))
+         (goto-char before-descript)
+         (while (progn (move-to-column fill-column) (not (eobp)))
+           (search-forward " " nil t)
+           (insert "\n"))
+         (fill-paragraph 1)
+         (goto-char before-descript)
+         (forward-line 1)
+         (while (progn (beginning-of-line) (not (eobp)))
+           (indent-to-column start-column)
+           (forward-line 1)))))
+    (move-to-tab-stop)
+    (insert "-")
+    (move-to-tab-stop)
+    (insert (read-string "Amount: "))
+    (run-hooks 'emoney-transaction-hook)
+    (run-hooks 'emoney-transaction-cheque-hook)))
+
+(defvar emoney-transfer-account-history nil)
+
+(defun emoney-transfer-funds (&optional from to amount)
+  "Transfer funds from one eMoney account to another.
+
+Argument FROM is the account to transfer from.
+Argument To is the account to transfer to.
+Argument AMOUNT is how much to transfer."
+  (interactive)
+  (let ((from (or from
+                 (emoney-completing-read "Transfer from: "
+                                         emoney-chart-of-accounts
+                                         nil
+                                         t
+                                         (concat emoney-current-account-name
+                                                 ".emy")
+                                         emoney-transfer-account-history)))
+       (to (or to
+               (emoney-completing-read "Transfer to: "
+                                       emoney-chart-of-accounts nil t nil
+                                       emoney-transfer-account-history)))
+       (amount (or amount
+                   (read-number "Amount: ")))
+       (current-ac (concat emoney-current-account-name ".emy")))
+    (with-current-buffer from
+      (emoney-append-transaction 
+       emoney-db-transfer-transaction-type
+       (concat "T'fer to " (file-name-sans-extension to))
+       amount))
+    (with-current-buffer to
+      (emoney-append-transaction
+       emoney-cr-transfer-transaction-type
+       (concat "T'fer from " (file-name-sans-extension from))
+       amount))
+    (loop for buf in '(from to)
+      do (emoney-switch-to-account (symbol-value buf))
+      do (emoney-recalculate-buffer))
+    (run-hooks 'emoney-transaction-transfer-hook)
+    (emoney-switch-to-account current-ac)))
+
+(defsubst emoney-build-type-regexp ()
+  "Return a regular expression that will match any valid transaction type.
+
+This is done dynamically so users can redefine the valid transactions in
+their `user-init-file' even after this file has been loaded."
+  (emoney-build-types-list)
+  (let ((types (append emoney-transaction-types
+                      (list emoney-cheque-type))))
+    (concat
+     "^\\("
+     (mapconcat
+      #'(lambda(x) x) types "\\|")
+     "\\)[ \t]*$")))
+
+(defun emoney-check-transaction-type (line-start)
+  "Check to make sure a valid transaction type has been used.
+
+Argument LINE-START is the starting point.
+
+Please note that the word \"check\" here means \"verify\" and it has
+nothing to do with the American spelling of the word \"cheque\"."
+  (let* ((type-regexp (emoney-build-type-regexp))
+         (type-start (+ line-start emoney-type-column))
+         (type-end (+ line-start emoney-clear-column))
+         (type-string (buffer-substring type-start type-end)))
+    (if (string-match type-regexp type-string)
+       nil
+      (error "Line %d, invalid type: %s"
+            (1+ (emoney-current-line)) type-string))))
+
+(defun emoney-find-next-transaction ()
+  "Find the next line that is a complete transaction.
+
+Return a list of the line start, numeric data start and line end
+points."
+  (let ((found nil)
+       (line-regexp
+        "^\\([0-90-9]\\)+.*$")
+       line-start
+       line-end
+       data-start)
+    (while (and
+           (not found)
+           (search-forward-regexp line-regexp (point-max) t))
+      (setq line-start (match-beginning 0))
+      (setq line-end (progn (end-of-line) (point)))
+      (setq data-start (+ line-start emoney-sign-column))
+      (if (> line-end data-start)
+         (setq found t)))
+    (if found
+       (list line-start data-start line-end)
+      nil)))
+
+(defun emoney-parse-transaction-data (data)
+  "Return a list of floating point numbers from DATA.
+
+DATA is a string representing the sign, amount and optionally balance of a
+transaction.  Balance is nil if not present."
+  (let ((data-regexp "\\([-+=]\\)[ \t]*\\([0-9.]+\\)?[ \t]*\\([-]?[0-9.]+\\)?")
+       (balance nil)
+       (reset nil)
+       string sign amount)
+    (string-match data-regexp data)
+    (if (match-beginning 1)
+       (setq sign (substring data (match-beginning 1) (match-end 1)))
+      (error "Line %d, missing sign" (1+ (emoney-current-line))))
+    (if (equal "=" sign)
+       (progn
+         (setq sign "+")
+         (setq reset t)))
+    (if (match-beginning 2)
+       (progn
+         (setq string (substring data (match-beginning 2) (match-end 2)))
+         (setq amount (string-to-number (concat sign string))))
+      (error "Line %d, missing amount" (1+ (emoney-current-line))))
+    (if (match-beginning 3)
+       (progn
+         (setq string (substring data (match-beginning 3) (match-end 3)))
+         (setq balance (string-to-number string))))
+    (if reset (setq sign "="))
+    (list sign amount balance)))
+
+(defun emoney-same (amount1 amount2)
+  "Compare two dollar amounts, AMOUNT1 AMOUNT2, for equivalence."
+  (let ((string1 (format "%10.2f" amount1))
+       (string2 (format "%10.2f" amount2)))
+    (equal string1 string2)))
+
+(defun emoney-form-transaction-data (sign amount balance)
+  "Given SIGN, AMOUNT and a BALANCE, return a string.
+
+The string is suitable for placing in the numeric region of a
+transaction, based on the defined input columns."
+  (let* ((amount (abs amount))
+         (width1 (- emoney-amount-column emoney-sign-column))
+         (width2 (- emoney-current-balance-column emoney-amount-column))
+         (len (length emoney-largest-balance))
+         (gap (- width2 len))
+         (value (concat "%" (number-to-string len) ".2f"))
+         (format-string (concat "%-" (number-to-string width1)
+                               "s" value
+                               "%" (number-to-string gap) "s" value)))
+    (format format-string sign amount "" balance)))
+
+(defun emoney-recalculate (start end)
+  "Recalculate the balances for region START END.
+
+The final balance, uncleared total, and the number of balances that
+changed, and the transaction count are returned in a list."
+  (run-hooks 'emoney-recalculate-before-hook)
+  (let ((current-balance 0)
+       (changes 0)
+       (uncleared 0)
+       (transactions 0)
+       line-points)
+    (save-excursion
+      (save-restriction
+       (narrow-to-region start end)
+       (untabify (point-min) (point-max))
+       (goto-char (point-min))
+       (while (setq line-points (emoney-find-next-transaction))
+         (setq transactions (1+ transactions))
+         (let* ((line-start (nth 0 line-points))
+                (data-start (nth 1 line-points))
+                (data-end (nth 2 line-points))
+                (clear-flag (buffer-substring
+                             (+ line-start emoney-clear-column)
+                             (+ 1 line-start emoney-clear-column)))
+                (data-string (buffer-substring data-start data-end))
+                (data-values (emoney-parse-transaction-data data-string))
+                (sign (nth 0 data-values))
+                (amount (nth 1 data-values))
+                (balance (nth 2 data-values))
+                (new-balance (if (equal sign "=")
+                                 amount
+                               (+ current-balance amount)))
+                (new-uncleared (if (equal clear-flag "x")
+                                   uncleared
+                                 (+ uncleared amount)))
+                (new-string
+                 (emoney-form-transaction-data sign amount new-balance)))
+           (emoney-check-transaction-type line-start)
+           (setq current-balance new-balance)
+           (setq uncleared new-uncleared)
+           (if (or (null balance) (not (emoney-same balance new-balance)))
+               (setq changes (1+ changes)))
+           (if (not (equal data-string new-string))
+               (progn
+                 (delete-region data-start data-end)
+                 (goto-char data-start)
+                 (insert new-string)))))
+       (widen)))
+    (run-hooks 'emoney-recalculate-after-hook)
+    (list current-balance uncleared changes transactions)))
+
+(defvar emoney-is-exiting nil
+  "Non-nil when eMoney is in the process of quitting.")
+
+(defun emoney-update-acc-buf-bal (account balance)
+  "Update ACCOUNT BALANCE in accounts buffer."
+  (with-current-buffer emoney-accounts-buffer
+    (goto-char (point-min))
+    (search-forward account)
+    (kill-line)
+    (move-to-column 13 'force)
+    (insert-face
+     (format (concat "%"
+                    (number-to-string (- (length emoney-largest-balance)
+                                         (length (format "%.2f" balance))))
+                    "s$%.2f") "" balance)
+     (if (< balance 0)
+        'emoney-debit-face
+       'emoney-credit-face))))
+
+(defun emoney-recalculate-buffer ()
+  "Recalculate the current buffer.
+
+See `emoney-recalculate'."
+  (interactive)
+  (let* ((result (emoney-recalculate (point-min) (point-max)))
+         (balance (nth 0 result))
+        (uncleared (nth 1 result))
+         (changes (nth 2 result))
+         (total (nth 3 result)))
+    (when emoney-save-after-recalculate
+      (save-buffer (current-buffer)))
+    (emoney-update-acc-buf-bal emoney-current-account-name balance)
+    (if emoney-is-exiting
+       (message
+        (format "book bal %.2f unclrd %.2f bank bal %.2f (%d/%d recalcs)"
+                balance uncleared (- balance uncleared) changes total))
+      (message-or-box
+       (format "book bal %.2f unclrd %.2f bank bal %.2f (%d/%d recalcs)"
+              balance uncleared (- balance uncleared) changes total)))
+    (if (> changes 0)
+       (end-of-line))))
+
+(defun emoney-recalculate-region (start end)
+  "Recalculate the current region, START END.
+
+See `emoney-recalculate'."
+  (interactive "r")
+  (let* ((result (emoney-recalculate start end))
+         (balance (nth 0 result))
+        (uncleared (nth 1 result))
+         (changes (nth 2 result))
+         (total (nth 3 result)))
+    (message-or-box (format "Region balance %.2f uncleared %.2f (%d/%d recalcs)"
+                           balance uncleared changes total))
+    (if (> changes 0)
+       (end-of-line))))
+
+(defun emoney-summarise-cheques (start end)
+  "Create a buffer that lists only the cheques in the specified region.
+
+The region is denoted by START END.
+
+The list is sorted on cheque number.  Breaks in sequence are denoted by lines
+containing an asterisk between the cheques where the break occurs.  The buffer
+is also recalculated, thus showing to total of the cheques summarised."
+  (let ((emoney-buffer (current-buffer))
+       (summary-buffer (get-buffer-create "*cheque summary*"))
+       (cheque-count 0)
+       (sequence-breaks 0)
+       line-points)
+    (save-excursion
+      (save-restriction
+       (set-buffer summary-buffer)
+       (delete-region (point-min) (point-max))
+       (set-buffer emoney-buffer)
+       (narrow-to-region start end)
+       (goto-char (point-min))
+       (while (setq line-points (emoney-find-next-transaction))
+         (let* ((line-start (nth 0 line-points))
+                (line-end (nth 2 line-points))
+                (type-start (+ line-start emoney-type-column))
+                (type-end (+ line-start emoney-description-column))
+                (type-string (buffer-substring type-start type-end)))
+           (if (string-match emoney-cheque-type type-string)
+               (progn
+                 (append-to-buffer
+                  summary-buffer line-start (1+ line-end))
+                 (setq cheque-count (1+ cheque-count))))))
+       (widen)
+       (set-buffer summary-buffer)
+       (sort-numeric-fields 3 (point-min) (point-max))
+       (setq sequence-breaks (emoney-find-sequence-breaks))
+       (goto-char (point-max))
+       (insert (format "\n%d cheque%s summarised, %d sequence break%s\n"
+                       cheque-count
+                       (if (equal 1 cheque-count) "" "s")
+                       sequence-breaks
+                       (if (equal 1 sequence-breaks) "" "s")))
+       (set-buffer emoney-buffer)))
+    (with-electric-help
+     '(lambda ()
+       (insert
+        (with-temp-buffer
+          (erase-buffer)
+          (insert-buffer summary-buffer)
+          (buffer-string (current-buffer)))))
+     "*cheque summary*"))
+  (run-hooks 'emoney-summarise-cheques-hook))
+
+(defun emoney-find-sequence-breaks ()
+  "Find cheque sequence breaks in the current cheque summary buffer.
+
+Mark breaks in sequence by inserting a line with an asterisk between
+the offending cheques.  Return the count of sequence breaks found."
+  (let ((last-cheque nil)
+       (sequence-breaks 0))
+    (goto-char (point-min))
+    (while (search-forward-regexp
+           (concat "\\([0-9/]+\\)[ \t]+" emoney-cheque-type)
+           (point-max) t)
+      (let* ((cheque-start (match-beginning 2))
+            (cheque-end (match-end 2))
+            (cheque-string (buffer-substring cheque-start cheque-end))
+            (cheque-number (string-to-int cheque-string)))
+       (if (not last-cheque)
+            (setq last-cheque cheque-number)
+         (if (not (equal cheque-number (1+ last-cheque)))
+             (progn
+               (setq sequence-breaks (1+ sequence-breaks))
+               (beginning-of-line)
+               (open-line 1)
+               (insert "*")
+               (next-line 2)))
+         (setq last-cheque cheque-number))))
+    sequence-breaks))
+
+(defun emoney-summarise-cheques-buffer ()
+  "Summarise the cheque transactions in the current buffer."
+  (interactive)
+  (emoney-summarise-cheques (point-min) (point-max))
+  (emoney-recalculate (point-min) (point-max)))
+
+(defun emoney-summarise-cheques-region (start end)
+  "Summarise the cheque transactions in region START - END."
+  (interactive "r")
+  (emoney-summarise-cheques start end)
+  (emoney-recalculate (point-min) (point-max)))
+
+(defun emoney-new-account (&optional name balance)
+  "*Create a new A/C named NAME for use with eMoney."
+  (interactive)
+  (let ((new-acc (concat (or name
+                            (read-string "New A/C Name: ")) ".emy"))
+       (bal (or balance
+                (read-number "Initial Balance: " nil 0))))
+    (find-file-noselect 
+     (expand-file-name new-acc emoney-accounts-directory))
+    (setq emoney-chart-of-accounts
+         (push new-acc emoney-chart-of-accounts))
+    (select-window (get-buffer-window 
+                   (concat emoney-current-account-name ".emy")))
+    (switch-to-buffer new-acc)
+    (setq emoney-current-account-name 
+         (file-name-sans-extension new-acc))
+    (emoney-append-transaction "init" "Opening Balance" bal)
+    (emoney-recalculate-buffer)
+    (emoney-show-buffers)
+    (switch-to-buffer new-acc)
+    (goto-char (point-max))
+    (run-hooks 'emoney-new-account-hook)))
+
+(defun emoney-setup-control-buffer ()
+  "Set up the eMoney \"Control\" buffer."
+  (let ((buf emoney-control-buffer))
+    (save-excursion
+      (when (buffer-live-p (get-buffer-create buf))
+       (kill-buffer buf))
+      (set-buffer (get-buffer-create buf))
+      (widget-create 'push-button
+                    :notify (lambda (&rest ignore)
+                              (emoney-new-account))
+                    :help-echo "Create a new eMoney account."
+                    " New A/C ")
+      (widget-insert " ")
+      (widget-create 'push-button
+                    :notify (lambda (&rest ignore)
+                              (save-excursion
+                                (set-buffer
+                                 (concat emoney-current-account-name ".emy"))
+                                (emoney-append-transaction)))
+                    :help-echo "Add a new transaction\n
+If you want to add a cheque transaction
+use \"Add Chq\" instead."
+                    "Add Trans")
+      (widget-insert " ")
+      (widget-create 'push-button
+                    :notify (lambda (&rest ignore)
+                              (save-excursion
+                                (set-buffer
+                                 (concat emoney-current-account-name ".emy"))
+                                (emoney-append-next-cheque)))
+                    :help-echo (if emoney-uk-cheque-spelling
+                                   "Add a new cheque transaction."
+                                 "Add a new check transaction.")
+                    (if emoney-uk-cheque-spelling
+                        " Add Chq "
+                      " Add Chk "))
+      (widget-insert " ")
+      (widget-create 'push-button
+                    :notify (lambda (&rest ignore)
+                              (save-excursion
+                                (set-buffer
+                                 (concat emoney-current-account-name ".emy"))
+                                (emoney-recalculate-buffer)))
+                    :help-echo "Record the last transaction.\n
+Also recalculates the buffer."
+                    "End Trans")
+      (widget-insert "\n\n")
+      (widget-create 'push-button
+                    :notify (lambda (&rest ignore)
+                              (save-excursion
+                                (set-buffer
+                                 (concat emoney-current-account-name ".emy"))
+                                (emoney-transfer-funds)))
+                    :help-echo "Transfer funds between accounts."
+                    "Transfer ")
+      (widget-insert " ")
+      (widget-create 'push-button
+                    :notify (lambda (&rest ignore)
+                              (save-excursion
+                                (set-buffer
+                                 (concat emoney-current-account-name ".emy"))
+                                (emoney-summarise-cheques-buffer)))
+                    :help-echo (if emoney-uk-cheque-spelling
+                                   "Display a summary of cheques."
+                                 "Display a summary of checks.")
+                    (if emoney-uk-cheque-spelling
+                        " Chq Sum "
+                      " Chk Sum "))
+      (widget-insert " ")
+      (widget-create 'push-button
+                    :notify (lambda (&rest ignore)
+                              (emoney-calc))
+                    :help-echo "Start the Emacs Calculator.\n
+So you can count up all
+of your millions!"
+                    "  Calc   ")
+      (widget-insert " ")
+      (widget-create 'push-button
+                    :notify (lambda (&rest ignore)
+                              (if emoney-is-beta
+                                  (message-or-box
+                                   "eMoney: %s, \"%s\" [Beta]"
+                                   emoney-version emoney-codename)
+                                (message-or-box
+                                 "eMoney: %s, \"%s\""
+                                 emoney-version emoney-codename)))
+                    :help-echo "Display eMoney version info."
+                    " Version ")
+      (widget-insert "\n\n")
+      (widget-create 'push-button
+                    :notify (lambda (&rest ignore)
+                              (emoney-go-to-bank))
+                    :help-echo "Open your bank's web site in your browser."
+                    "  Bank   ")
+      (widget-insert " ")
+      (widget-create 'push-button
+                    :notify (lambda (&rest ignore)
+                              (emoney-quit))
+                    :help-echo "Exit eMoney."
+                    "  Exit   ")
+      (set-specifier horizontal-scrollbar-visible-p nil (current-buffer))
+      (set-specifier vertical-scrollbar-visible-p nil (current-buffer))
+      (set-specifier has-modeline-p nil (current-buffer))
+      (run-hooks 'emoney-setup-control-buffer-hook))))
+
+(defun emoney-show-buffers ()
+  "Display all the eMoney buffers."
+  (emoney-setup-accounts-buffer)
+  (emoney-setup-control-buffer)
+  (emoney-setup-header-buffer)
+  (delete-other-windows nil)
+  (switch-to-buffer emoney-accounts-buffer)
+  (split-window nil emoney-accounts-buffer-height)
+  (split-window nil emoney-accounts-buffer-width t)
+  (other-window 1)
+  (switch-to-buffer emoney-control-buffer)
+  (other-window 1)
+  (switch-to-buffer emoney-header-buffer)
+  (split-window nil emoney-header-buffer-height)
+  (other-window 1))
+
+(defun emoney-quit ()
+  "*Exit from eMoney, optionally recalculating all accounts first.
+
+To have all of your accounts recalculated before eMoney exits set
+`emoney-recalculate-on-quit' to `t'
+
+If `emoney-save-after-recalculate' is also `t' the account buffers
+will be saved before eMoney exits."
+  (interactive)
+  (run-hooks 'emoney-quit-before-hook)
+  (let ((accounts emoney-chart-of-accounts))
+    (setq emoney-is-exiting t)
+    (dolist (buf accounts)
+      (when emoney-recalculate-on-quit
+       (set-buffer buf)
+       (emoney-recalculate-buffer))
+      (kill-buffer buf))
+    (kill-buffer emoney-accounts-buffer)
+    (kill-buffer emoney-control-buffer)
+    (kill-buffer emoney-header-buffer)
+    (run-hooks 'emoney-quit-after-hook)
+    (when (and emoney-use-new-frame
+              (frame-live-p emoney-frame))
+      (delete-frame emoney-frame))
+    (setq emoney-frame nil)
+    (unless emoney-use-new-frame
+      (jump-to-register ?\$))
+    (setq emoney-is-exiting nil)))
+
+(defun emoney-recalc-and-exit ()
+  "*Exit form eMoney, recalculating all accounts first."
+  (interactive)
+  (let ((old-recalc-val emoney-recalculate-on-quit))
+    (setq emoney-recalculate-on-quit t)
+    (emoney-quit)
+    (setq emoney-recalculate-on-quit old-recalc-val)))
+
+;;;###autoload
+(defun emoney ()
+  "*Start a new eMoney session."
+  (interactive)
+  (unless emoney-use-new-frame
+    (window-configuration-to-register ?\$))
+  (unless (frame-live-p emoney-frame)
+    (setq emoney-frame
+         (if emoney-use-new-frame
+             (make-frame '((name . "eMoney")))
+           (selected-frame))))
+  (select-frame emoney-frame)
+  (let ((accounts emoney-chart-of-accounts)
+       (dir emoney-accounts-directory))
+    (while accounts
+      (find-file (expand-file-name (car accounts) dir))
+      (unless (eq major-mode 'emoney-mode)
+       (emoney-mode))
+      (setq accounts (cdr accounts)))
+    (setq emoney-current-account-name 
+         (file-name-sans-extension emoney-default-account))
+    (emoney-show-buffers)
+    (switch-to-buffer emoney-default-account)
+    (goto-char (point-max)))
+  (focus-frame emoney-frame))
+
+;; Work around a problem with Emacs calc.  If you start calc in a
+;; frame with multiple buffers visible when calc exits it doesn't
+;; return point to the place it was when you called calc.  These
+;; advices overcome that.
+(defadvice calc (before em-calc-win-save first activate)
+  "Before starting calc, save the window config.
+This is so we can restore the window config when calc exits because
+calc doesn't DTRT in this regard by itself."
+  (push-window-configuration))
+
+(defadvice calc-quit (after em-calc-win-restore last activate)
+  "Restore the \"pre calc\" window config on calc exit."
+  (pop-window-configuration))
+
+
+;;;###autoload(add-to-list 'auto-mode-alist '("\\.emy$" . emoney-mode))
+
+(provide 'emoney)
+
+;;; emoney.el ends here