On 2010-04-27 11:49 +0800, Stefan Monnier wrote:
Actually, having tried it now for a while I do have an objection: it
makes it harder to add entries to an abbrev-table if that table
is empty.
So I think a better option is to sort the tables such that empty tables
are pushed to the end.
Stefan
Hello Stefan,
I propose we allow C-u M-x edit-abbrevs to include all abbrev tables but
default to include only nonempty tables.
Here is an updated patch.
=== modified file 'lisp/abbrev.el'
--- lisp/abbrev.el 2011-03-22 15:38:40 +0000
+++ lisp/abbrev.el 2011-03-27 04:56:22 +0000
@@ -104,7 +104,7 @@
prefix arg, display only local, i.e. mode-specific, abbrevs.
Otherwise display all abbrevs."
(interactive "P")
- (display-buffer (prepare-abbrev-list-buffer local)))
+ (display-buffer (prepare-abbrev-list-buffer (and local 'local))))
(defun abbrev-table-name (table)
"Value is the name of abbrev table TABLE."
@@ -116,14 +116,28 @@
(setq tables (cdr tables)))
found))
-(defun prepare-abbrev-list-buffer (&optional local)
- (let ((local-table local-abbrev-table))
+(defun abbrev-nonempty-table-names (&optional ignore-system)
+ "Return a list of nonempty abbrev table names.
+If IGNORE-SYSTEM is non-nil, system definitions are ignored."
+ (delete nil
+ (mapcar (lambda (tn)
+ (unless (abbrev-table-empty-p
+ (symbol-value tn) ignore-system)
+ tn))
+ abbrev-table-name-list)))
+
+;; HOW takes value: nil, local or all.
+(defun prepare-abbrev-list-buffer (&optional how)
+ (let ((local-table local-abbrev-table)
+ (tables (if (eq how 'all)
+ abbrev-table-name-list
+ (abbrev-nonempty-table-names))))
(with-current-buffer (get-buffer-create "*Abbrevs*")
(erase-buffer)
- (if local
+ (if (eq how 'local)
(insert-abbrev-table-description
(abbrev-table-name local-table) t)
- (dolist (table abbrev-table-name-list)
+ (dolist (table tables)
(insert-abbrev-table-description table t)))
(goto-char (point-min))
(set-buffer-modified-p nil)
@@ -140,10 +154,11 @@
(use-local-map edit-abbrevs-map)
(run-mode-hooks 'edit-abbrevs-mode-hook))
-(defun edit-abbrevs ()
+(defun edit-abbrevs (&optional all)
"Alter abbrev definitions by editing a list of them.
Selects a buffer containing a list of abbrev definitions.
-You can edit them and type \\<edit-abbrevs-map>\\[edit-abbrevs-redefine] to
redefine abbrevs
+Use \\[universal-argument] to include empty abbrev tables. You can edit
+them and type \\<edit-abbrevs-map>\\[edit-abbrevs-redefine] to redefine abbrevs
according to your editing.
Buffer contains a header line for each abbrev table,
which is the abbrev table name in parentheses.
@@ -152,8 +167,8 @@
where NAME and EXPANSION are strings with quotes,
USECOUNT is an integer, and HOOK is any valid function
or may be omitted (it is usually omitted)."
- (interactive)
- (switch-to-buffer (prepare-abbrev-list-buffer)))
+ (interactive "P")
+ (switch-to-buffer (prepare-abbrev-list-buffer (and all 'all))))
(defun edit-abbrevs-redefine ()
"Redefine abbrevs according to current buffer contents."
@@ -225,7 +240,8 @@
abbrev-file-name)))
(or (and file (> (length file) 0))
(setq file abbrev-file-name))
- (let ((coding-system-for-write 'utf-8))
+ (let ((coding-system-for-write 'utf-8)
+ (tables (abbrev-nonempty-table-names t)))
(with-temp-buffer
(dolist (table
;; We sort the table in order to ease the automatic
@@ -234,10 +250,9 @@
;; user keeps their home directory in a revision
;; control system, and is therefore keeping multiple
;; slightly-differing copies loosely synchronized.
- (sort (copy-sequence abbrev-table-name-list)
- (lambda (s1 s2)
- (string< (symbol-name s1)
- (symbol-name s2)))))
+ (sort tables (lambda (s1 s2)
+ (string< (symbol-name s1)
+ (symbol-name s2)))))
(insert-abbrev-table-description table nil))
(when (unencodable-char-position (point-min) (point-max) 'utf-8)
(setq coding-system-for-write
@@ -420,6 +435,18 @@
(and (vectorp object)
(numberp (abbrev-table-get object :abbrev-table-modiff))))
+(defun abbrev-table-empty-p (object&optional ignore-system)
+ "Return nil if there are no abbrev symbols in OBJECT.
+If IGNORE-SYSTEM is non-nil, system definitions are ignored."
+ (unless (abbrev-table-p object)
+ (error "Non abbrev table object"))
+ (not (catch 'some
+ (mapatoms (lambda (abbrev)
+ (unless (or (zerop (length (symbol-name abbrev)))
+ (and ignore-system (abbrev-get abbrev
:system)))
+ (throw 'some t)))
+ object))))
+
(defvar global-abbrev-table (make-abbrev-table)
"The abbrev table whose abbrevs affect all buffers.
Each buffer may also have a local abbrev table.
Leo