defcustom ¶ を用いた変数の指定defcustom を使って変数を指定すれば、自分や他のユーザーが Emacs の customize 機能を用いてその値を設定できるようになります。(customize を使って関数定義を書くことはできませんが、.emacs ファイルに defuns
を書くことは可能です。実際、.emacs ファイルには任意の Lisp 式を書くことができます。)
customize 機能は defcustom
マクロに依存しています。ユーザーが設定する変数には defvar や setq も使用できますが、defcustom
マクロはこの用途向けに設計されています。
defvarに関する知識を活かして、defcustomの最初の3つの引数を記述できます。defcustomの第1引数は変数名です。第2引数は、変数の初期値(もしあれば)であり、この値はまだ設定されていない場合にのみ設定されます。第3引数はドキュメントです。
defcustom の4番目以降の引数では型やオプションを指定しますが、これらは defvar では指定しません。(これらの引数は省略可能です。)
これらの引数はそれぞれ、キーワードとそれに続く値で構成されています。各キーワードは、コロン文字 ‘:’ で始まります。
例えば、カスタマイズ可能なユーザーオプション変数 text-mode-hook
は次のようになります。
(defcustom text-mode-hook nil "Normal hook run when entering Text mode and many related modes." :type 'hook :options '(turn-on-auto-fill flyspell-mode) :group 'wp)
変数名は text-mode-hook
で、デフォルト値はなく、ドキュメント文字列にその機能が記載されています。
:type キーワードは、text-mode-hook に設定すべきデータの種類と、カスタマイズバッファ内でその値をどのように表示するかを
Emacs に指示します。
:options キーワードは、変数に推奨される値のリストを指定します。通常、:options
はフックに適用されます。このリストはあくまで提案であり、排他的なものではありません。変数を設定する人は、他の値を設定することも可能です。:options キーワードに続いて表示されるリストは、ユーザーに便利な選択肢を提供することを目的としています。
最後に、:group キーワードは Emacs の Customization
コマンドに対し、変数がどのグループに属しているかを伝えます。これにより、変数の場所が特定されます。
defcustom マクロは12種類以上のキーワードを認識します。詳細については、The GNU Emacs Lisp Reference Manual の Writing
Customization Definitions を参照してください。
text-mode-hookを例に考えてみましょう。
この変数をカスタマイズする方法は2通りあります。カスタマイズコマンドを使用するか、適切な式を自身で記述することができます。
カスタマイズコマンドを使用すると、次のように入力できます。
M-x customize
そして、テキストファイルの編集用グループが ‘Text’
と呼ばれていることがわかります。そのグループをクリックするか、RET
と入力してグループに入ります。Text Mode Hook
はそのグループのメンバーの一つです。その左側にある三角形のボタン(または、テキスト専用端末でそれに代わる ‘Show Value’
ボタン)をクリックすると、さまざまなオプションが表示されます。次に、turn-on-auto-fill などのオプションをクリック(テキスト専用端末を使用している場合は RET と入力)して、値を設定またはリセットできます。‘State’ ボタンをクリック(または RET
と入力)して ‘Save for Future Sessions’
を選択すると、Emacs が .emacs ファイルに式を書き込みます。それは次のようになります:
(custom-set-variables ;; custom-set-variables was added by Custom. ;; If you edit it by hand, you could mess it up, so be careful. ;; Your init file should contain only one such instance. ;; If there is more than one, they won't work right. '(text-mode-hook '(turn-on-auto-fill text-mode-hook-identify)))
(text-mode-hook-identify 関数は、どのバッファがテキストモードであるかを
toggle-text-mode-auto-fill に通知します。これは自動的に実行されます。)
custom-set-variables 関数は、setq とは多少動作が異なります。その違いを詳しく学んだことはありませんが、私は .emacs ファイル内の custom-set-variables
式を手作業で修正しています。自分なりに妥当と思われる方法で変更を加えていますが、特に問題は起きていません。カスタマイズコマンドを使用して、Emacs
に処理を任せることを好む人もいます。
もう一つのcustom-set-…関数にcustom-set-facesがあります。この関数は、さまざまなフォントフェイスを設定します。これまで、かなりの数のフェイスを設定してきました。時にはcustomizeを使って再設定し、またある時は.emacsファイル自体のcustom-set-faces式を単純に編集することもあります。
text-mode-hookをカスタマイズする2つ目の方法は、custom-set-…関数とは全く関係のないコードを用いて、.emacsファイル内で直接設定することです。
このようにして、後で customize を使用すると、次のようなメッセージが表示されます。
CHANGED outside Customize; operating on it here may be unreliable.
このメッセージはあくまで警告です。ボタンをクリックすると、
Save for Future Sessions
Emacsは、.emacsファイルの末尾付近にcustom-set-…式を書き込みます。これは、手書きの式よりも後に評価されます。したがって、手書きの式を上書きすることになります。特に問題はありません。ただし、この操作を行う際は、どの式が有効になっているかを忘れずに確認してください。忘れてしまうと、混乱を招く恐れがあります。
値の設定箇所さえ覚えていれば、困ることはありません。いずれにせよ、値は常に初期化ファイル(通常は .emacs と呼ばれます)で設定されます。
私自身、customizeを使うことはほとんどありません。大抵は自前で式を書いています。
ちなみに、definesについてより詳しく述べると、defsubstはインライン関数を定義します。構文はdefunと同様です。defconstはシンボルを定数として定義します。これは、プログラムもユーザーも、defconstで設定された値を決して変更しないようにすることを意図したものです。(変更は可能です。設定された値は変数ですが、どうか変更しないでください。)