興味を持つものだけに興味を持つ暮らし

とある企業に勤める坊主

xyzzy

全角と半角の間に半角スペースを空ける
こんな感じ。

わたしは Hello といいました。

auto-space.l †

;;; -*- Mode: Lisp; Package: editor -*-
;;;
;;; auto-space.l
;;;
;;; Last updated: <2002/08/28 14:46:52 +0900>
;;;

;;; Author
;;; 室園真一郎

;;; Overview
;;; 全角と半角の間に自動的に半角スペースを空けるマイナーモードです。

;;; Install
;;;
;;; 1. ~/site-lisp に本ファイル(auto-space.l)をコピー。
;;;
;;; 2. 必要ならバイトコンパイル
;;; M-x byte-compile-file
;;;
;;; 3. .xyzzy か siteinit.l に以下のコードを追加。
;;; (require "auto-space")
;;;
;;; 4. 更に特定の状況で起動させたい場合は以下のような感じで各ファイルに
;;; 追加して下さい。自分が使ってる例です。他にもっといい方法があるの
;;; かもしれないけど自分は知らないです。
;;;
;;; ; .xyzzy に以下のコードを追加
;;; (add-hook '*text-mode-hook*
;;; #'(lambda ()
;;; (auto-space-mode t)))
;;;
;;; ; .kamail に以下のコードを追加
;;; (add-hook 'km::*kamail-draft-mode-hook*
;;; #'(lambda ()
;;; (auto-space-mode t)))
;;;
;;; 5. 以下のシンボルはちゃんと機能するかどうか甚だ怪しいです。
;;;
;;; *auto-space-nop-next* に設定した文字の後にはスペースを空けません。
;;; *auto-space-nop-prev* はその逆です。
;;; 以下みたいな感じで文字単位で設定できます。
;;; (pushnew #\あ *auto-space-nop-next*)

;;; ToDo
;;; ・意図的に空ける文字を設定できるようにする (,. とか)。
;;; ・yank 後も空けるようにする (kill-ring に入ってるものには関知し
;;; ない)。
;;; ・*auto-space-nop-next* とかを複数設定できるようにする。
;;; string で設定できるようにする(つか多分方法知らないだけだと思う)。

;;; Changes
;;; [2002/08/28]
;;; ・初版

(provide "auto-space")

(in-package "editor")

(export '(*auto-space-nop-next* *auto-space-nop-prev*
auto-space-mode *auto-space-mode*))

(defvar-local *auto-space-mode* nil)

(defvar inhibit-chars-list '(#\SPC #\TAB #\RET #\LFD #\NUL))
; 意図的に空けない文字
(defvar *auto-space-nop-next*
'(#\・ #\( #\) #\、 #\。 #\. #\( #\) #\「 #\」 #\{ #\} #\【 #\】 #\『 #\』
#\: #\↑ #\↓ #\← #\→ #\@ #\?))
(defvar *auto-space-nop-prev*
'(#\・ #\( #\) #\、 #\。 #\. #\( #\) #\「 #\」 #\{ #\} #\【 #\】 #\『 #\』
#\: #\↑ #\↓ #\← #\→ #\@ #\?))

(defun do-auto-space ()
(interactive "*")
(unless (or (not (eq *this-command* 'self-insert-command))
(member *last-command-char* inhibit-chars-list)
(minibuffer-window-p (selected-window)))
(let *1
(prev (char-before (1- (point))))
(next (following-char)))
; 前
(unless (or (member cur (append *auto-space-nop-prev* inhibit-chars-list))
(member prev (append *auto-space-nop-next* inhibit-chars-list))
(= (char-columns cur) (char-columns prev)))
(save-excursion
(goto-char (1- (point)))
(insert #\SPC)))
; 後
(unless (or (member cur (append *auto-space-nop-next* inhibit-chars-list))
(member next (append *auto-space-nop-prev* inhibit-chars-list))
(= (char-columns cur) (char-columns next)))
(save-excursion
(insert #\SPC))))))

(defun auto-space-mode (&optional (arg nil sv))
(interactive "p")
(toggle-mode '*auto-space-mode* arg sv)
(update-mode-line t)
(make-local-variable '*post-command-hook*)
(if *auto-space-mode*
(add-hook '*post-command-hook* 'do-auto-space)
(delete-hook '*post-command-hook* 'do-auto-space))
t)

(pushnew '(*auto-space-mode* . "Space") *minor-mode-alist* :key #'car)

*1:cur (preceding-char