Monthly Archives: October 2013

My Emacs init.el

I will join the hoards of Emacs people and put up my Emacs init.el file here.  This should be compatible with the tutorial I posted.  Even though I was first exposed to Emacs over 20 years ago, I didn’t really start using it until about last year.  So I truly still consider myself a newbie.  Everything I learned here is basically just recapping stuff I found online.  There is nothing original here.  My goal is to try to present something that would have helped me when I started out learning Clojure with Emacs.  This is cobbled together and modified from the main home (or github) page of each package, and here:

http://clojure.jr0cket.co.uk/perfect-environment/2—configure-emacs-for-clojure

http://ergoemacs.org/emacs/emacs_useful_user_keybinding.html

http://stackoverflow.com/questions/88399/how-do-i-duplicate-a-whole-line-in-emacs

Also, I apologize for the syntax highlighting. I’m not sure how to get elisp syntax highlighting to work in WordPress. I’m currently using SyntaxHighlighter Evolved V3.17.

;; Add Marmalade package archive for Emacs starter kit and other Emacs packages
;; This allows ALT-x package-list-packages to return a big list of useful packages
(require 'package)
(add-to-list 'package-archives
	     '("marmalade" . "http://marmalade-repo.org/packages/") )
(package-initialize)

;; Add Clojure and other supporting packages to the Emacs environment
;; Packages are installed if they are not already present
;; The list includes packages for the starter kit, Clojure and markdown files (used by github)
;; This can be avoided if you have manually installed the packages eg via
;; ALT-x package-list-packages
(when (not package-archive-contents)
 	(package-refresh-contents))

(defvar my-packages '(clojure-mode          ;; the major mode for clojure
		      clojure-test-mode     ;; not sure -- I still haven't learned how to write test code
		      paredit               ;; keeps parentheses balanced
		      nrepl                 ;; IDE and REPL for clojure
		      fuzzy                 ;; needed for nrepl
		      popup                 ;; popup tooltips
		      auto-complete         ;; used for ac-nrepl
		      ac-nrepl              ;; autocomplete for nrepl
		      eldoc                 ;; shows argument completion in the echo area for elisp
		      rainbow-delimiters    ;; colors parentheses, etc.
		      undo-tree             ;; undo/redo sanity restored
		      tabbar                ;; tabs at top of window
		      linum))               ;; Line numbers in the border

(dolist (p my-packages)
  (when (not (package-installed-p p))
    (package-install p)))

(add-hook 'nrepl-interaction-mode-hook 'nrepl-turn-on-eldoc-mode ) ;enables eldoc when in nrepl (not sure why this is needed)
(add-hook 'clojure-mode-hook           'turn-on-eldoc-mode)        ;enables eldoc when writing clojure (not sure why this is needed)
(add-hook 'emacs-lisp-mode-hook        'turn-on-eldoc-mode)        ;enables eldoc when writing elisp
(add-hook 'lisp-interaction-mode-hook  'turn-on-eldoc-mode)        ;enables eldoc for scratch buffer

;; Enable paredit mode for clojure, elisp, and nrepl
(add-hook 'clojure-mode-hook    'paredit-mode)
(add-hook 'emacs-lisp-mode-hook 'paredit-mode)
(add-hook 'nrepl-repl-mode-hook 'paredit-mode)

(require 'auto-complete-config)
(ac-config-default)
(define-key ac-completing-map "M-/" 'ac-stop) ; use ALT-/ to stop completion

;; Enable ac-nrepl -- this looks like a mess and doesn't quite work right
;; Not sure how this relates to popup
(require 'auto-complete)
(require 'ac-nrepl)
(global-auto-complete-mode t)
(add-hook 'nrepl-mode-hook             'ac-nrepl-setup)
(add-hook 'nrepl-interaction-mode-hook 'ac-nrepl-setup)
(add-hook 'clojure-nrepl-mode-hook     'ac-nrepl-setup)
(eval-after-load "auto-complete" '(add-to-list 'ac-modes 'nrepl-mode))
;; This doesn't look like http://blog.worldcognition.com/2012/07/setting-up-emacs-for-clojure-programming.html

;; colors nearest parentheses
(require 'highlight-parentheses)
(define-globalized-minor-mode global-highlight-parentheses-mode
  highlight-parentheses-mode
  (lambda ()
    (highlight-parentheses-mode t)))
(global-highlight-parentheses-mode t)

;; enable rainbow delimiters
(require 'rainbow-delimiters)
(global-rainbow-delimiters-mode)

;; These allow me to move cursor around using the keys that
;; are naturally under my right hand, while using Dvorak keyboard
(global-set-key (kbd "M-h") 'backward-char) ;; sets ALT-h to left arrow, replaces emacs mail help
(global-set-key (kbd "M-t") 'next-line)     ;; sets ALT-t to down arrow, replaces emacs transpose
(global-set-key (kbd "M-n") 'forward-char)  ;; sets ALT-n to right arrow, replaces down in minibuffer history
(global-set-key (kbd "M-c") 'previous-line) ;; sets ALT-c to up arrow, replaces nothing

;; buffer and tab management
(require 'tabbar)
(tabbar-mode 1) ;; shows tabs at the top
(global-set-key [C-tab]   'next-buffer)       ;; CTRL-tab goes to next buffer
(global-set-key [C-S-tab] 'previous-buffer) ;; CTRL-SHIFT-tab goes to previous buffer

;; Duplicate line function
;; From http://stackoverflow.com/questions/88399/how-do-i-duplicate-a-whole-line-in-emacs
(defun duplicate-line-or-region (&optional n)
  "Duplicate current line, or region if active.
With argument N, make N copies.
With negative N, comment out original line and use the absolute value."
  (interactive "*p")
  (let ((use-region (use-region-p)))
    (save-excursion
      (let ((text (if use-region        ;Get region if active, otherwise line
                      (buffer-substring (region-beginning) (region-end))
                    (prog1 (thing-at-point 'line)
                      (end-of-line)
                      (if (< 0 (forward-line 1)) ;Go to beginning of next line, or make a new one
                          (newline))))))
        (dotimes (i (abs (or n 1)))     ;Insert N times, or once if not specified
          (insert text))))
    (if use-region nil                  ;Only if we're working with a line (not a region)
      (let ((pos (- (point) (line-beginning-position)))) ;Save column
        (if (> 0 n)                             ;Comment out original with negative arg
            (comment-region (line-beginning-position) (line-end-position)))
        (forward-line 1)
        (forward-char pos)))))
;; Set duplicate line to CTRL-c d
(global-set-key (kbd "C-c d") 'duplicate-line-or-region)

;; Other stuff
(electric-indent-mode 1)             ;; enables auto indentation
(show-paren-mode 1)                  ;; shows paren matching cursor location
(setq show-paren-delay 0)            ;; ... with zero delay
(global-linum-mode 1)                ;; shows line numbers
(column-number-mode 1)               ;; shows cursor row,col at bottom of window
(global-set-key (kbd "C-z") 'undo)   ;; Sets CTRL-z to undo
(global-set-key [f9] 'nrepl-jack-in) ;; Sets F9 to start nrepl
(setq inhibit-startup-message t)     ;; No splash screen
(setq initial-scratch-message nil)   ;; No scratch message
(load-theme 'solarized-dark t)       ;; Change colors
(setq solarized-contrast 'low)       ;; Change contrast

 

Setting up Emacs/Clojure environment for Windows

This particular set of steps is done using a freshly-installed version of 64-bit Windows 8.1.  The concepts are largely stolen from here, but I removed anything about really old versions of Windows.

Install Emacs

1. Download Emacs for Windows from the Big Page.  As of this writing (Oct 19, 2013), the current version is 24.3.  Yes, this is “precompiled”.  Why would I want anything else?  Yes I know, yada yada.  I’m more about the gratis than the libre.

2. Unzip it someplace and just keep the inner directory emacs-24.3.  In keeping with other Windows programs, you should put it in C:\Program Files (x86)\.  I’m guessing there is probably some risk in having spaces and stuff in the directory name.  I wouldn’t be surprised if Emacs had a problem with this under some condition, but it seems to work for me. So now your directory tree looks like this, minus the scribbles.

EmacsTree

3. At this point you’re supposed to select a “home” where Emacs stores its config information, elisp code that gets downloaded, etc.  My recommendation is to leave your HOME variable undefined.  Normally this would involve setting the HOME environment variable to some directory, but in the absence of this, Emacs picks other locations based on what version of Windows you’re running.  It’s convoluted, so read here.  If you have some other program that defines a HOME variable (such as any of the Unix-based tools running on Windows), you are fucked.  Emacs will pick this location first because it exists and you will be stuck putting your .emacs (or init.el or whatever) file in that location.  I have not found a way to force Emacs to pick another location since HOME is the first place it checks.

Quick tip: In Emacs terminology CTRL-x or C-x means press the CTRL key and x at the same time.  The - is a dash not a minus, and the instruction would be the same if there were  a + as in normal computer text instructions, ie CTRL+x; however using the dash is typical for Emacs instructions so I’ll use it here.  If there is no dash in the instruction, then press the keys in sequence.  So CTRL-x k means press CTRL-x first, then press k.  In this case, this is the sequence to “kill” the buffer, ie close the file.  In this case, Emacs will prompt you at the bottom of the screen to check if you want to save any unsaved changes.

Quick tip: Don’t try using the menus and expect to find anything useful.  It’s the most convoluted piece of junk ever created.  I’ve only ever been able to open/close a file, save-as, and change fonts from there, and sometimes get a keystroke reminder for compiling stuff from the source buffer.  Everything else is complete nonsense if you are trying to use the menu to do normal editor stuff, or explore what’s out there.  Google is your friend for discovering Emacs.

Quick tip: if you are stuck in some Emacs state/mode and you can’t get out of it, press CTRL-G a bunch of times.  This is like pressing ESC in most modern applications, in that it will get you out of whatever thing you’re in and take you back to normal mode.  Pressing ESC usually works too, but this is an after-thought in Emacs history.  In Emacs terminology you will see “Meta-x” or M-x a lot.  This is historic, based on an ancient keyboard that had a “meta” key, and is completely irrelevant in this day and age.  This means “press ESC then press x“, or equivalently it can mean ALT-x, which is preferred.  So if you accidentally press ESC then some other key, you are inadvertently doing the same thing as pressing ALT-<that other key>.  So just press CTRL-G to quit out of whatever state you’re stuck in.

Quick tip: ALT-x is different from most of the other C-<whatever> key sequences.  ALT-x puts you in the little command buffer at the bottom of the screen.  From here you can tell Emacs to do stuff, such as start nrepl so you can live a live Clojure session from the editor (nrepl-jack-in), change how the line wrap works (toggle-truncate-lines), turn on paredit (paredit-mode), etc.  While in this state, you can use the normal Emacs cursor keys (C-f, C-b, C-e, C-k) and recall previous commands  (ALT-p).  You can quit/cancel the current command from here as described above, with C-g, or just complete the command with Enter.

Quick tip: You will be using the CTRL key a lot.  Best to remap your useless caps-lock key to be an additional CTRL key.  Here is the page.  Here is the zip file.  Open up the zip file and double click on ChangeCapsToControl.reg.  This probably needs a reboot to kick in.  Now your pinkie won’t be extra muscular by trying to reach down to the lower left all the time.

Quick tip: You can use the normal arrow keys, backspace, delete, mouse, etc., to edit in Emacs.  This was not always the case, but it’s pretty standard nowadays for modern users.  I tried once setting Emacs to use CUA keystrokes (common user accessibility), but this screws things up as all the other commands have to get rearranged; I don’t recommend this.  Just train your brain.  It doesn’t take long, and once you’re used to moving the cursor around and deleting stuff, compiling, changing buffers, windows, etc., without moving your hands, you’ll be annoyed at other editors for not having this functionality.  I have also switched to Dvorak layout and I find it extremely comfortable and easy to use; you may wish to do the same, although the Emacs keys become a little weirder in terms of the neuromuscular distortions you need to encode in your mind.  Now go out and try to make friends by telling them you write Clojure using Emacs with a Dvorak keyboard.  Observe the funny looks you get.  The requisite xkcd links are here and here.

capstocontrol

4.  You can find which location emacs wants to use as its home by starting up emacs directly ("C:\Program Files (x86)\emacs-24.3\bin\runemacs.exe") and then typing CTRL-x d ~\  The CTRL-x d tells Emacs to open a directory.  The ~\ resets the search path back to what it thinks is the home directory.  Forward slash or backward slash doesn’t matter.  (Honestly I’m not sure what the differences are among runemacs.exe, emacs.exe, emacsw.exe, etc.  My fingers like to type emacs at the command line since that’s what I learned in college 100 years ago on Unix machines, but evidently on a Windows machine you’re supposed to use emacsw.exe or runemacs.exe.  Sometimes a client/server thing pops up too.)  At the bottom of the Emacs window you should see this:

cx-f-tilde

Press Enter and you get something like this.  Yes I’m doing this as Admin, but do as I say and not as I do, and run all this stuff from a normal user account.

homedir

So in this case Emacs is using the c:/users/Admin/AppData/Roaming directory as the home directory.  This is just FYI; we won’t be using this view now.  Since this is a new install, you don’t have an init file yet.

5. Create a new init file in this home directory.  Traditionally this is called .emacs, but it can also be called .emacs.d/init.el, or other variants.  So type CTRL-x CTRL-f ~/.emacs.d/init.el, and you should see the following at the bottom of  the screen.

openinit

Press enter and you get the new blank file in the editing “buffer”.

openinit2

Type C-x C-s to save the (blank) file.  You don’t actually need to release the CTRL key.  Verify its existence with C-x d Enter.  The correct directory should automatically populate in the little command line area.  If not, add ~/ before pressing enter.

initexistence

Emacs junks up your directory with #init.el# and init.el~ .  These are backups. 5.  Add the following to your init.el file, then restart Emacs or type ALT-x eval-buffer (From the gitub site)

(require 'package)
 (add-to-list 'package-archives
 '("marmalade" . "http://marmalade-repo.org/packages/"))
 (package-initialize)

5. Start downloading stuff for Clojure mode support.  Type ALT-x package-list-packages  For long commands like this you can press TAB in the middle and it’ll complete, or show you a list of possible completions in the little command line area.  You get a list of packages to download. Use the arrow keys and i to select packages for install, then x to install them.  You can search for a packages with CTRL-s <package name>, then CTRL-s repeatedly to search again.  Select the following: clojure-mode, cljdoc, ac-nrepl, nrepl, paredit. After downloading, you can see these packages in the ~/.emacs.d/elpa directory.  Elpa is the emacs library system.  I really don’t know anything more than that.

elpacontents

6.  At this point emacs will do syntax highlighting on clojure files and probably other stuff based on the above stuff you downloaded.  Create a file called junk.clj  by typing C-f c:\users\Admin\code\junk.clj  (it will give you instructions on creating the code directory) and put in the following:

(println "hi")

This should result in coloring like this:

printlnhi

Install Java

6.  Download and install the JDK and add the bin directory to your path.  As of this writing the JDK version is 7u45.  Actually the installation by itself adds java.exe and some other executables to your Windows/System32 directory, so strictly speaking I don’t think you need to change your path.  However at some point you’ll want javac.exe and other developer stuff which is not in Windows/System32, so best to just get it over with.  I’m guessing that Lein and some of  the Emacs support for Clojure will also want a real home location for Java.

On an unadulterated Windows 8 machine, changing the path is done through the search in the main tile page.  Press the Windows key WindowsKey to bring up the start page (or CTRL+ESC), then just start typing “environment” and the selection will pop up, then select it.  In reality I skip this altogether as I have installed StartIsBack which returns sanity back to the Windows 8 user experience.  Make sure to select “Edit the system environmentvariables” not “Edit environment variables for your account”.

environmentsearch

Click Environment Variables, then double click path in System Variables, and edit in the box:

environmentchange pathchange

You’ll probably also want to set up JAVA_HOME, which is done in a similar manner.

javahome

Verify the new Java installation works:

verifyjava

Install Lein

7.  Install Lein by downloading lein.bat and placing it in c:\Program Files (x86)\Leiningen, and adding this location to your path.

pathchange2

Then open up a command prompt and run lein self-install.

leininstall

8. Create a new project with Lein.  Change to your code directory and create a Clojure project with lein new temp_project. leinnew

9.  Update the project so it knows the namespace.  Change to the project directory and open the project.clj file.  Be sure to use tab completion so it doesn’t hurt your brain.  You can of course just start up emacs with the mouse and open the file that way (C-x C-f c:\users\admin\code\clojure\temp_project\project.clj).  And of course I’d recommend putting the emacs bin directory in your path so you can call it up immediately from the command line.

editproject

emacsopenproject

Add a single line to the bottom of project.clj, then C-x C-s to save it.  Notice there is a dash, not an underscore, in the namespace.  This matches the namespace in the source file.

(defproject temp_project "0.1.0-SNAPSHOT"
 :description "FIXME: write description"
 :url "http://example.com/FIXME"
 :license {:name "Eclipse Public License"
 :url "http://www.eclipse.org/legal/epl-v10.html"}
 :dependencies [[org.clojure/clojure "1.5.1"]]
 :main temp-project.core)

10.  Update the source file so it has a -main function.  Open up the test file left by Lein:  C-x C-f src/temp_project/core.clj

opencore

Add the following highlighted function definition, then C-x C-s to save.

(ns temp-project.core)
(defn foo
 "I don't do a whole lot."
 [x]
 (println x "Hello, World!"))

(defn -main []
 (foo 3.14159))

11. Run the program from the command line. Change to the project directory (doesn’t matter how deep in the directory tree) and say lein run.
leinrun

Use Emacs to run Clojure

12. Now that Lein works, open up the source file again in Emacs.  C-x C-f c:/Users/Admin/code/clojure/temp_project/src/temp_project/core.clj

13.  Start up nrepl with ALT-x nrepl-jack-in (again use tab-completion).  Remember the M-x shown below is Emacs’ interpretation of  ALT-x for modern users.

startnrepl

This will open up a new window with the REPL.

freshrepl

14.  Compile the source code.  Change window focus back to the source code by clicking in the source window (or press C-x o) so the bottom of the source window is dark gray, then compile everything with C-c C-k.  This gives you something like this.  Press y.

compilesave

Then you get something like

compiledone

15. Press C-c C-z to jump back to the REPL (you could also do C-x o.  The former takes you to the REPL from any window; the latter only jumps to the “next” window, which works when you only have 2 windows open).  Your program is now “in” the REPL, ie the functions have been compiled and are ready to run, except they’re stored in the temp-project.core namespace.

16.  Change to the correct namespace with (in-ns 'temp-project.core).  You can use tab completion with this too.  Then run the main function with (-main):

runmain

17.  You can of course run the other function too, with (foo 2.781828) or (foo "You Jerk!").

jerk

Congratulations!

You have just completed what took me a few weeks of hard labor to figure out.  I obviously didn’t invent this stuff, but I haven’t really seen a direct step by step procedure yet on how to do this; I’ve only found little bits and pieces around the web.  There is a ton more to do.  Specifically, I haven’t set up the Emacs init.el file.  This is almost like getting a PhD in itself.  Since I recently wiped my computer without saving the file, I have to create it again from scratch, so that will take some time.  But in general, I like to enable all the fancy editing features for lisp, specifically paredit mode, enabling the auto documentation for both the editor window and the REPL, changing front and color size, getting rid of the stupid splash screen that comes up, and some other stuff I came across which actually involved some elisp in the init.el file.  Kind of annoying, but it makes the overall usage a little better.

In a future post I will show a simple JavaFX app.

Emacs rant before the tutorial

I originally started in Clojure using JetBrains’ IntelliJ IDEA IDE with the clojure plugins.  This was great for a few hello-world types of programs, but I felt I was missing out after reading what you could do with Emacs.  For example in IDEA I could start a REPL, but I couldn’t figure out how to compile and run stuff from the editor in the REPL, thus keeping a live running version of all my functions and variables.  I didn’t see how to get the IDE to format and manipulate  the parentheses correctly a la Paredit, etc.  There are probably ways to do this, but I didn’t take the time to figure it out, and there wasn’t much documentation available.

I realize now after having “really” used Emacs for some time that Emacs really is (currently) the best tool for lispy programs.  I could easily imagine a more modern GUI/IDE that maintains the lispy support of Emacs, but brings the tool up to the modern era. My first experiences with Emacs were in undergrad (’92-’96), and I hated it.  In fact, in the intervening ~20 years, each and every single time I ventured into Emacs for one reason or another, I really just couldn’t stand the backwards way it did everything, from nomenclature, to discoverability, to the sheer bone-headedness of the concepts involved, when compared to a modern “normal” text editor.

The smug, bearded-birkenstocked-guru “self-documenting” DNA present in Emacs is such a huge turn off that I almost want to vomit.  In fact I have never found anything “self documenting” about it; my best sources for Emacs documentation are Google and StackOverflow. As to functionality, my biggest issues were the logical-vs-physical line breaks, line numbering, text wrapping, etc.  For instance, Yes I get that you can have a hard line break, but when I hit the CTRL-N key, I really just want to move the cursor physically down one line on the screen, not logically down one line, which could be multiple physical lines, for example for a long paragraph.  Oh, wait… what?  I’m typing text? not code?  Oooh, I”m sorry sir (“brother”), you have to change modes.  Major mode?  Minor mode?  Not sure, don’t care.  I really don’t have time for this, but evidently I’m a moron for not figuring it out, and I’m a Windows fanboy if I decide I just want a normal editor with equal accessibility between mouse and keyboard ways of doing things and simple menus for choosing word wrap options.  FWIW, my favorite “normal” text editor is EditPlus.

Finally I always hated how Emacs’ “customizability” meant that there are a dozen ways to do any given thing so everyone’s always trying to send you their .emacs file which you then have to decipher and figure out what parts from it you want to use and whether what they’re doing is compatible with what you’re already doing, and to make emacs usable you really have to set it up first, rather than it just working out of the box.  For example, there have been a handful of line-numbering add-ons… really?  Every other text editor has this built-in, and  and it appears that proper line numbering (with the line numbers in the left margin) didn’t work properly until some very recent version.  I’m not an expert at all; I don’t know Emacs version numbers.  I know there are a lot of them.  This is my point of view as a user from the 21st century, not an Emacs hacker or evangelist; I have better things to waste my time on.

Anyway, now that I’ve been using Emacs for Clojure, and I finally have it setup somewhat customized, it’s not too bad.  I can navigate quite quickly within a file, compile code under the cursor, jump to the REPL, and manipulate parentheses like nobody’s business.  It’s still not as nice for some of the intelligent (ie context-sensitive or type-aware)  help you get with IDEA or Visual Studio, but I suspect this is more about the dynamic typing of Clojure vs. the statically typed languages one normally sees with IDEA (Java) or Visual Studio (C#), than about Emacs itself necessarily or the inline help that is somewhat available.

Currently I have found absolutely zero help with step-by-step debugging.  Yes there are macro tricks and libraries available, but to me it  just adds more noise to my brain.  Actually the best debugging I’ve found for lispy programs has been in PLT Scheme’s IDE, as it has a way of displaying the results of each s-exp as you step through, but I’m pretty sure this has as much to do with Clojure’s current state of development as with Emacs’ support for graphical debugging (both pretty much nonexistent).  Debugging Clojure from IDEA sorta worked, in that I could step through a program, but it would always step me through the Java source, which, while mildly entertaining, is completely useless for actually debugging a Clojure program.  This was my experience with CDT also.  I would like to see something like PLT’s method (which is similar to debugging cells in Excel), where each expression is replaced by its result as you step through.

Anyway, on to the tutorial.