2009年11月30日月曜日

[Emacs]eldocをほんの少し便利にする

LISPファイルの編集時に関数の引数を表示するマイナーモードとして、Emacsではeldoc-mode、CLではslime-autodoc-modeがあるんですが、両者の表示形式が微妙に異なることが気になったのでついカッとなってeldocの方を軽く改造しました。反省はしていない。

gist: 244937 - GitHub

参考画像を見れば分かると思いますが、ポイント位置の引数の強調方法がデフォル トでは太字ではなくハイライトになってます。

Eldocの表示デモ

その他、関数・変数ともにdocstringの表示が可能です。

ソースコードはGistに置いておくのでinstall-elispからインストールすればCL(SLIME)使いは幸せになれるかもしれません。

(install-elisp-from-gist 244937 "eldoc.el")

動作環境

Emacs22以上で動作確認。

無駄にCLのマクロを使っていますがバイトコンパイルすれば (require 'cl) がない状態でも使えるので安心です。


ここまで書いておいてあれですが、このeldoc.elの改造はミニバッファ表示方法がちょこっと変わった位のものなので特に目新しい機能はありません。

単に表示色を変更したいだけなら本来のeldocのfaceを弄ればそれっぽくなります。

(set-face-background 'eldoc-highlight-function-argument "darkseagreen2")
(set-face-bold-p 'eldoc-highlight-function-argument nil)

2009年11月11日水曜日

[Emacs]そんなことよりeval-after-load使おうぜ

もっと使われてもいいのにと思うEmacsの設定周りのメモ。

[関数] (eval-after-load FILE FORM)

この関数は、指定されたライブラリFILEがロードされているときにのみ2番目の引数FORMを評価するというもの。

例えばmigemoをロードする時の自分の設定はこんな感じ。

;; migemoを読み込む。存在しない場合はnilを返す
(load "migemo" 'noerror)

(eval-after-load "migemo"
 (quote
  (progn
    ;; この辺がmigemoをロードした後に評価される
    (defadvice isearch-mode (before migemo-off activate)
      "初期状態は常にnil"
      (setq migemo-isearch-enable-p nil))
    (fset 'toggle-migemo #'migemo-toggle-isearch-enable)
    (define-key isearch-mode-map (kbd "C-t") 'migemo-isearch-toggle-migemo)
    )))

この関数の利点は

  • ライブラリが存在しない場合はeval-after内のフォームが評価されない。
    つまりエラーにならない。
  • emacsの標準関数である (emacs/lisp/subr.el内で定義)。
    つまり自前で関数を用意しなくて良い。
  • 一度eval-after-loadが評価されれば、後からライブラリが読み込まれてもフォーム内部を評価してくれる。
    これは各種メジャーモードのフックに関数を引っ掛けて、フォームの評価を遅らせるのと同様の手段となる。
    例: (add-hook 'emacs-lisp-mode-hook 'turn-on-eldoc-mode)

逆に不便な点、気にくわない点は

  • 評価できるフォームが1つしか指定できない。
    => (progn ...) を使えば複数フォームを指定できる
  • 関数なので引数が必ず評価される。そのためにフォームをquoteするのが嫌。おまけにシングルクオート '(...) を使うとフォーム内のインデントが崩れる。
    => 代わりに (quote FORM) を使えば長いフォームもそれなりにインデントされる。

この辺は一応マクロを使えば解決するが...なんで関数なんでしょうね、これ。

(defmacro eval-after-load-1 (file &rest args)
 `(eval-after-load ,file
    (quote (progn ,@args))))
(put 'eval-after-load-1 'lisp-indent-function 1)

参考URL