diff options
author | Tino Calancha <tino.calancha@gmail.com> | 2018-09-29 18:40:46 +0900 |
---|---|---|
committer | Tino Calancha <tino.calancha@gmail.com> | 2018-09-29 18:40:46 +0900 |
commit | 2296bf188fc99d66306e71e6decd3d2e176b7ae6 (patch) | |
tree | bfc6c4d8afad29ee0204ce56801583ea7d97e403 /lisp/ibuf-macs.el | |
parent | 3bbe9e609138ae88a4c98bcee0da8fcf8b4a3e80 (diff) | |
download | emacs-2296bf188fc99d66306e71e6decd3d2e176b7ae6.tar.gz |
Ibuffer filter by modes: Accept several mode names
Extend all mode filters so that they handle >1 mode.
For instance, if the users want to filter all buffers in
C or C++ mode, then they can call the filter interactively
with input: 'c-mode,c++-mode' (Bug#32731).
* lisp/ibuf-macs.el(define-ibuffer-filter): Add key :accept-list.
If the value of this key is non-nil, then the filter accepts
either a single qualifier or a list of them; in the latter case,
the resultant filter is the `or' composition of the individual ones.
* lisp/ibuf-ext.el (ibuffer-filter-by-used-mode)
(ibuffer-filter-by-mode, ibuffer-filter-by-derived-mode)
Set :accept-list value non-nil.
Interactively, accept a comma separated list of mode names.
* etc/NEWS(Ibuffer): Announce this change.
Co-authored-by: Noam Postavsky <npostavs@gmail.com>
Diffstat (limited to 'lisp/ibuf-macs.el')
-rw-r--r-- | lisp/ibuf-macs.el | 65 |
1 files changed, 40 insertions, 25 deletions
diff --git a/lisp/ibuf-macs.el b/lisp/ibuf-macs.el index 6a70a8341a2..72a35a53315 100644 --- a/lisp/ibuf-macs.el +++ b/lisp/ibuf-macs.el @@ -280,14 +280,18 @@ buffer object. ;;;###autoload (cl-defmacro define-ibuffer-filter (name documentation - (&key - reader - description) - &rest body) + (&key + reader + description + accept-list) + &rest body) "Define a filter named NAME. DOCUMENTATION is the documentation of the function. READER is a form which should read a qualifier from the user. DESCRIPTION is a short string describing the filter. +ACCEPT-LIST is a boolean; if non-nil, the filter accepts either +a single condition or a list of them; in the latter +case the filter is the `or' composition of the conditions. BODY should contain forms which will be evaluated to test whether or not a particular buffer should be displayed or not. The forms in BODY @@ -296,30 +300,41 @@ bound to the current value of the filter. \(fn NAME DOCUMENTATION (&key READER DESCRIPTION) &rest BODY)" (declare (indent 2) (doc-string 2)) - (let ((fn-name (intern (concat "ibuffer-filter-by-" (symbol-name name))))) + (let ((fn-name (intern (concat "ibuffer-filter-by-" (symbol-name name)))) + (filter (make-symbol "ibuffer-filter")) + (qualifier-str (make-symbol "ibuffer-qualifier-str"))) `(progn (defun ,fn-name (qualifier) - ,(or documentation "This filter is not documented.") - (interactive (list ,reader)) - (if (null (ibuffer-push-filter (cons ',name qualifier))) - (message "%s" - (format ,(concat (format "Filter by %s already applied: " description) - " %s") - qualifier)) - (message "%s" - (format ,(concat (format "Filter by %s added: " description) - " %s") - qualifier)) - (ibuffer-update nil t))) + ,(or documentation "This filter is not documented.") + (interactive (list ,reader)) + (let ((,filter (cons ',name qualifier)) + (,qualifier-str qualifier)) + ,(when accept-list + `(progn + (unless (listp qualifier) (setq qualifier (list qualifier))) + ;; Reject equivalent filters: (or f1 f2) is same as (or f2 f1). + (setq qualifier (sort (delete-dups qualifier) #'string-lessp)) + (setq ,filter (cons ',name (car qualifier))) + (setq ,qualifier-str + (mapconcat (lambda (m) (if (symbolp m) (symbol-name m) m)) + qualifier ",")) + (when (cdr qualifier) ; Compose individual filters with `or'. + (setq ,filter `(or ,@(mapcar (lambda (m) (cons ',name m)) qualifier)))))) + (if (null (ibuffer-push-filter ,filter)) + (message ,(format "Filter by %s already applied: %%s" description) + ,qualifier-str) + (message ,(format "Filter by %s added: %%s" description) + ,qualifier-str) + (ibuffer-update nil t)))) (push (list ',name ,description - (lambda (buf qualifier) - (condition-case nil - (progn ,@body) - (error (ibuffer-pop-filter) - (when (eq ',name 'predicate) - (error "Wrong filter predicate: %S" - qualifier)))))) - ibuffer-filtering-alist) + (lambda (buf qualifier) + (condition-case nil + (progn ,@body) + (error (ibuffer-pop-filter) + (when (eq ',name 'predicate) + (error "Wrong filter predicate: %S" + qualifier)))))) + ibuffer-filtering-alist) :autoload-end))) (provide 'ibuf-macs) |