Codebase list browse-kill-ring-el / 0e76495
New upstream snapshot. Debian Janitor 2 years ago
4 changed file(s) with 156 addition(s) and 124 deletion(s). Raw diff Collapse all Expand all
0 2015-10-16 Andrew Burgess <andrew.burgess@embecosm.com>
1 Make C-g quit browse-kill-ring mode.
2
3 2015-05-18 Andrew Burgess <andrew.burgess@embecosm.com>
4 Restore the mode name to "Kill Ring" if the filter regexp is
5 removed.
6
7 2015-05-18 Andrew Burgess <andrew.burgess@embecosm.com>
8 The default for `browse-kill-ring-occur' is now to remove the
9 regexp that is currently in place, restoring all item in the
10 kill-ring to the display. Previous regexp are still available in
11 the history ring if needed.
12
13 2015-04-27 Andrew Burgess <andrew.burgess@embecosm.com>
14 Remove `browse-kill-ring-no-duplicates'. This functionality was
15 never related to browsing the kill-ring, and would be better moved
16 in to a different package.
17
18 2015-01-02 Andrew Burgess <andrew.burgess@embecosm.com>
19 Unify tail of `browse-kill-ring-finish' and
20 `browse-kill-ring-abort' to increase code reuse. Improve use of
21 `brose-kill-ring-edit-target' to track when the user is making an
22 edit.
23
024 2014-11-04 Toon Claes <toon@tonotdo.com>
125 v2.0 release:
226 Legacy code is removed, README is converted and
1616 (add-to-list 'load-path "~/emacs.d/vendor")
1717 (require 'browse-kill-ring)
1818 ```
19
20 ### Marmalade
21
22 If you're an Emacs 24 user or you have a recent version of package.el
23 you can install browse-kill-ring from the [Marmalade](http://marmalade-repo.org/) repository.
2419
2520 ### MELPA
2621
4848 ;;; Code:
4949
5050 (eval-when-compile
51 (require 'cl)
52 (require 'derived))
51 (require 'cl-lib))
52 (require 'delsel)
5353
5454 (defgroup browse-kill-ring nil
5555 "A package for browsing and inserting the items in `kill-ring'."
172172 "When `browse-kill-ring-display-duplicates' nil,
173173 if non-nil, then display leftmost(last) duplicate items in `kill-ring'."
174174 :type 'boolean
175 :group 'browse-kill-ring)
176
177 (defadvice kill-new (around browse-kill-ring-no-kill-new-duplicates)
178 "An advice for not adding duplicate elements to `kill-ring'.
179 Even after being \"activated\", this advice will only modify the
180 behavior of `kill-new' when `browse-kill-ring-no-duplicates'
181 is non-nil."
182 (if browse-kill-ring-no-duplicates
183 (setq kill-ring (delete (ad-get-arg 0) kill-ring)))
184 ad-do-it)
185
186 (defcustom browse-kill-ring-no-duplicates nil
187 "If non-nil, then the `b-k-r-no-kill-new-duplicates' advice will operate.
188 This means that duplicate entries won't be added to the `kill-ring'
189 when you call `kill-new'.
190
191 If you set this variable via customize, the advice will be activated
192 or deactivated automatically. Otherwise, to enable the advice, add
193
194 B (ad-enable-advice 'kill-new 'around 'browse-kill-ring-no-kill-new-duplicates)
195 (ad-activate 'kill-new)
196
197 to your init file."
198 :type 'boolean
199 :set (lambda (symbol value)
200 (set symbol value)
201 (if value
202 (ad-enable-advice 'kill-new 'around
203 'browse-kill-ring-no-kill-new-duplicates)
204 (ad-disable-advice 'kill-new 'around
205 'browse-kill-ring-no-kill-new-duplicates))
206 (ad-activate 'kill-new))
207175 :group 'browse-kill-ring)
208176
209177 (defcustom browse-kill-ring-depropertize nil
319287 (point)
320288 quit))
321289
290 (defun browse-kill-ring-insert-new (insert-action post-action &optional quit)
291 "Insert the kill ring item at point into the last selected buffer.
292 `insert-action' can be 'insert 'append 'prepend.
293 `post-action' can be nil 'move 'delete.
294 If optional argument QUIT is non-nil, close the *Kill Ring* buffer as
295 well."
296 (interactive "P")
297 (let* ((buf (current-buffer))
298 (pt (point))
299 (str (browse-kill-ring-current-string buf pt)))
300 (cl-case insert-action
301 ('insert (browse-kill-ring-do-insert buf pt nil))
302 ('append (browse-kill-ring-do-append-insert buf pt nil))
303 ('prepend (browse-kill-ring-do-prepend-insert buf pt nil))
304 (t (error "Unknown insert-action: %s" insert-action)))
305 (cl-case post-action
306 ('move
307 (browse-kill-ring-delete)
308 (kill-new str))
309 ('delete (browse-kill-ring-delete))
310 (t (error "Unknown post-action: %s" post-action)))
311 (if quit
312 (browse-kill-ring-quit)
313 (browse-kill-ring-update))))
314
322315 (defun browse-kill-ring-insert-and-delete (&optional quit)
323316 "Insert the kill ring item at point, and remove it from the kill ring.
324317 If optional argument QUIT is non-nil, close the *Kill Ring* buffer as
349342 (defun browse-kill-ring-insert-move-and-quit ()
350343 "Like `browse-kill-ring-insert-and-move', but close the *Kill Ring* buffer."
351344 (interactive)
352 (browse-kill-ring-insert-and-move t))
345 (browse-kill-ring-insert-new 'insert 'move t))
353346
354347 (defun browse-kill-ring-prepend-insert (&optional quit)
355348 "Like `browse-kill-ring-insert', but it places the entry at the beginning
393386 (warn "Unable to load `pulse' library")
394387 (setq browse-kill-ring-highlight-inserted-item 'solid)))
395388
396 (case browse-kill-ring-highlight-inserted-item
389 (cl-case browse-kill-ring-highlight-inserted-item
397390 ((pulse t)
398391 (let ((pulse-delay .05) (pulse-iterations 10))
399 (pulse-momentary-highlight-region
400 start end browse-kill-ring-inserted-item-face)))
392 (with-no-warnings
393 (pulse-momentary-highlight-region
394 start end browse-kill-ring-inserted-item-face))))
401395 ('solid
402396 (let ((o (make-overlay start end)))
403397 (overlay-put o 'face browse-kill-ring-inserted-item-face)
486480 (inhibit-read-only t))
487481 (delete-region (overlay-start over) (1+ (overlay-end over)))
488482 (setq kill-ring (delete target kill-ring))
483 (if (equal target (car kill-ring-yank-pointer))
484 (setq kill-ring-yank-pointer
485 (delete target kill-ring-yank-pointer)))
489486 (cond
490487 ;; Don't try to delete anything else in an empty buffer.
491488 ((and (bobp) (eobp)) t)
499496 ((get-text-property (point) 'browse-kill-ring-extra)
500497 (let ((prev (previous-single-property-change (point) 'browse-kill-ring-extra))
501498 (next (next-single-property-change (point) 'browse-kill-ring-extra)))
502 (when prev (incf prev))
503 (when next (incf next))
499 (when prev (cl-incf prev))
500 (when next (cl-incf next))
504501 (delete-region (or prev (point-min)) (or next (point-max))))))))
505502 (browse-kill-ring-resize-window)
506503 (browse-kill-ring-forward 0))
509506 (defun browse-kill-ring-target-overlay-at (position &optional no-error)
510507 "Return overlay at POSITION that has property `browse-kill-ring-target'.
511508 If no such overlay, raise an error unless NO-ERROR is true, in which
512 case retun nil."
509 case return nil."
513510 (let ((ovs (overlays-at (point))))
514511 (catch 'browse-kill-ring-target-overlay-at
515512 (dolist (ov ovs)
546543
547544 (defun browse-kill-ring-clear-highlighed-entry ()
548545 (when browse-kill-ring-previous-overlay
549 (assert (overlayp browse-kill-ring-previous-overlay))
546 (cl-assert (overlayp browse-kill-ring-previous-overlay))
550547 (overlay-put browse-kill-ring-previous-overlay 'face nil)))
551548
552549 (defun browse-kill-ring-update-highlighed-entry-1 ()
553550 (let ((current-overlay (browse-kill-ring-target-overlay-at (point) t)))
554 (case current-overlay
551 (cl-case current-overlay
555552 ;; No overlay at point. Just clear all current highlighting.
556553 ((nil) (browse-kill-ring-clear-highlighed-entry))
557554 ;; Still on the previous overlay.
559556 ;; Otherwise, we've changed overlay. Clear current
560557 ;; highlighting, and highlight the new overlay.
561558 (t
562 (assert (overlay-get current-overlay
559 (cl-assert (overlay-get current-overlay
563560 'browse-kill-ring-target) t)
564561 (browse-kill-ring-clear-highlighed-entry)
565562 (setq browse-kill-ring-previous-overlay current-overlay)
574571 (let ((o (browse-kill-ring-target-overlay-at (point) t)))
575572 (if (< arg 0)
576573 (progn
577 (incf arg)
574 (cl-incf arg)
578575 (when o
579576 (goto-char (overlay-start o))
580577 (setq o nil))
582579 (goto-char (previous-overlay-change (point)))
583580 (setq o (browse-kill-ring-target-overlay-at (point) t))))
584581 (progn
585 (decf arg)
582 (cl-decf arg)
586583 ;; We're on a browse-kill-ring overlay, skip to the end of it.
587584 (when o
588585 (goto-char (overlay-end o))
598595 (interactive "p")
599596 (browse-kill-ring-forward (- arg)))
600597
601 (defun browse-kill-ring-read-regexp (msg)
598 (defun browse-kill-ring-read-regexp (msg &optional empty-is-nil-p)
602599 (let* ((default (car regexp-history))
603600 (input
604601 (read-from-minibuffer
605 (if default
602 (if (and default (not empty-is-nil-p))
606603 (format "%s for regexp (default `%s'): "
607604 msg
608605 default)
610607 nil
611608 nil
612609 nil
613 'regexp-history)))
610 'regexp-history
611 (if empty-is-nil-p default nil))))
614612 (if (equal input "")
615 default
613 (if empty-is-nil-p nil default)
616614 input)))
617615
618616 (defun browse-kill-ring-search-forward (regexp &optional backwards)
650648 "Take the action specified by `browse-kill-ring-quit-action'."
651649 (interactive)
652650 (browse-kill-ring-cleanup-on-exit)
653 (case browse-kill-ring-quit-action
651 (cl-case browse-kill-ring-quit-action
654652 (save-and-restore
655653 (if (< emacs-major-version 24)
656654 (let (buf (current-buffer))
676674 `browse-kill-ring' instead.
677675
678676 \\{browse-kill-ring-mode-map}"
677 ;; Later versions of emacs reduced the number of arguments to
678 ;; font-lock-defaults, at least version 24 requires 5 arguments
679 ;; before setting up buffer local variables.
679680 (set (make-local-variable 'font-lock-defaults)
680681 '(nil t nil nil nil
681682 (font-lock-fontify-region-function . browse-kill-ring-fontify-region)))
682683 (define-key browse-kill-ring-mode-map (kbd "q") 'browse-kill-ring-quit)
684 (define-key browse-kill-ring-mode-map (kbd "C-g") 'browse-kill-ring-quit)
683685 (define-key browse-kill-ring-mode-map (kbd "U") 'browse-kill-ring-undo-other-window)
684686 (define-key browse-kill-ring-mode-map (kbd "d") 'browse-kill-ring-delete)
685687 (define-key browse-kill-ring-mode-map (kbd "s") 'browse-kill-ring-search-forward)
734736 (define-key browse-kill-ring-edit-mode-map
735737 (kbd "C-c C-c") 'browse-kill-ring-edit-finish)
736738 (define-key browse-kill-ring-edit-mode-map
737 (kbd "C-c C-k") 'browse-kill-ring-edit-abort))
739 (kbd "C-c C-k") 'browse-kill-ring-edit-abort)
740 (define-key browse-kill-ring-edit-mode-map
741 (kbd "C-g") 'browse-kill-ring-edit-abort))
738742
739743 (defvar browse-kill-ring-edit-target nil)
740744 (make-variable-buffer-local 'browse-kill-ring-edit-target)
764768 'browse-kill-ring-preview-update-for-edit nil t))
765769 (setq browse-kill-ring-edit-target target-cell)))
766770
771 (defun browse-kill-ring-edit-finalise (entry)
772 "Common code called after `browse-kill-ring-edit' has finished
773
774 This common code is called after `browse-kill-ring-edit-finish'
775 and `browse-kill-ring-edit-abort'. It kills the edit buffer, and
776 reselects ENTRY in the `*Kill Ring*' buffer."
777 ;; Kill the edit buffer. Maybe we should do more to keep track of
778 ;; the edit buffer so we can kill it even if we're not in it?
779 (when (eq major-mode 'browse-kill-ring-edit-mode)
780 (kill-buffer))
781 ;; The user might have rearranged the windows
782 (when (eq major-mode 'browse-kill-ring-mode)
783 (browse-kill-ring-setup (current-buffer)
784 browse-kill-ring-original-buffer
785 browse-kill-ring-original-window
786 nil
787 browse-kill-ring-original-window-config)
788 (browse-kill-ring-resize-window)
789 (when entry
790 (browse-kill-ring-find-entry entry))))
791
767792 (defun browse-kill-ring-edit-finish ()
768 "Commit the changes to the `kill-ring'."
769 (interactive)
793 "Commit the edit changes to the `kill-ring'."
794 (interactive)
795 (unless browse-kill-ring-edit-target
796 (error "Not editing a kill-ring item"))
770797 (let* ((updated-entry (buffer-string))
771798 (delete-entry? (string= updated-entry ""))
799 (current-entry browse-kill-ring-edit-target)
772800 (select-entry nil))
773 (if browse-kill-ring-edit-target
774 (if delete-entry?
775 ;; Find the previous entry in the list to select, then
776 ;; delete the entry that was just edited to empty.
777 (progn
778 (setq select-entry
779 (cadr browse-kill-ring-edit-target))
780 (setq kill-ring
781 (delete (car browse-kill-ring-edit-target) kill-ring))
782 (unless select-entry
783 (setq select-entry (car (last kill-ring)))))
784 ;; Update the entry that was just edited, and arrange to
785 ;; select it.
786 (setcar browse-kill-ring-edit-target updated-entry)
787 (setq select-entry updated-entry))
788 (unless delete-entry?
789 (when (y-or-n-p "The item has been deleted; add to front? ")
790 (push updated-entry kill-ring)
791 (setq select-entry updated-entry))))
792 (kill-buffer)
793 ;; The user might have rearranged the windows
794 (when (eq major-mode 'browse-kill-ring-mode)
795 (browse-kill-ring-setup (current-buffer)
796 browse-kill-ring-original-buffer
797 browse-kill-ring-original-window
798 nil
799 browse-kill-ring-original-window-config)
800 (browse-kill-ring-resize-window)
801 (when select-entry
802 (browse-kill-ring-find-entry select-entry)))))
801 (setq browse-kill-ring-edit-target nil)
802 (if delete-entry?
803 ;; Find the previous entry in the list to select, then
804 ;; delete the entry that was just edited to empty.
805 (progn
806 (setq select-entry
807 (cadr current-entry))
808 (setq kill-ring
809 (delete (car current-entry) kill-ring))
810 (unless select-entry
811 (setq select-entry (car (last kill-ring)))))
812 ;; Update the entry that was just edited, and arrange to select
813 ;; it.
814 (setcar current-entry updated-entry)
815 (setq select-entry updated-entry))
816 (browse-kill-ring-edit-finalise select-entry)))
803817
804818 (defun browse-kill-ring-edit-abort ()
805819 "Abort the edit of the `kill-ring' item."
807821 (let ((current-entry (if browse-kill-ring-edit-target
808822 (car browse-kill-ring-edit-target)
809823 nil)))
810 (kill-buffer)
811 ;; The user might have rearranged the windows
812 (when (eq major-mode 'browse-kill-ring-mode)
813 (browse-kill-ring-setup (current-buffer)
814 browse-kill-ring-original-buffer
815 browse-kill-ring-original-window
816 nil
817 browse-kill-ring-original-window-config)
818 (browse-kill-ring-resize-window))
819 (if current-entry
820 (browse-kill-ring-find-entry current-entry))))
824 (setq browse-kill-ring-edit-target nil)
825 (browse-kill-ring-edit-finalise current-entry)))
821826
822827 (defmacro browse-kill-ring-add-overlays-for (item &rest body)
823 (let ((beg (gensym "browse-kill-ring-add-overlays-"))
824 (end (gensym "browse-kill-ring-add-overlays-")))
828 (let ((beg (cl-gensym "browse-kill-ring-add-overlays-"))
829 (end (cl-gensym "browse-kill-ring-add-overlays-")))
825830 `(let ((,beg (point))
826831 (,end
827832 (progn
883888 (defun browse-kill-ring-occur (regexp)
884889 "Display all `kill-ring' entries matching REGEXP."
885890 (interactive
886 (list
887 (browse-kill-ring-read-regexp "Display kill ring entries matching")))
888 (assert (eq major-mode 'browse-kill-ring-mode))
891 (list (browse-kill-ring-read-regexp
892 "Display kill ring entries matching" t)))
893 (cl-assert (eq major-mode 'browse-kill-ring-mode))
889894 (browse-kill-ring-setup (current-buffer)
890895 browse-kill-ring-original-buffer
891896 browse-kill-ring-original-window
912917 (let ((buffer-read-only nil))
913918 (browse-kill-ring-fontify-on-property 'browse-kill-ring-extra 'bold beg end)
914919 (browse-kill-ring-fontify-on-property 'browse-kill-ring-separator
915 browse-kill-ring-separator-face beg end))
920 browse-kill-ring-separator-face beg end)
921 (font-lock-fontify-keywords-region beg end verbose))
916922 (when verbose (message "Fontifying...done")))
917923
918924 (defun browse-kill-ring-update ()
919925 "Update the buffer to reflect outside changes to `kill-ring'."
920926 (interactive)
921 (assert (eq major-mode 'browse-kill-ring-mode))
927 (cl-assert (eq major-mode 'browse-kill-ring-mode))
922928 (browse-kill-ring-setup (current-buffer)
923929 browse-kill-ring-original-buffer
924930 browse-kill-ring-original-window)
927933 (defun browse-kill-ring-preview-update-text (preview-text)
928934 "Update `browse-kill-ring-preview-overlay' to show `PREVIEW-TEXT`."
929935 ;; If preview-text is nil, replacement should be nil too.
930 (assert (overlayp browse-kill-ring-preview-overlay))
936 (cl-assert (overlayp browse-kill-ring-preview-overlay))
931937 (let ((replacement (when preview-text
932938 (propertize preview-text 'face 'highlight))))
933939 (overlay-put browse-kill-ring-preview-overlay
10621068 ;; display leftmost or rightmost duplicate.
10631069 ;; if `browse-kill-ring-display-leftmost-duplicate' is t,
10641070 ;; display leftmost(last) duplicate.
1065 (require 'cl)
1066 (delete-duplicates items
1071 (cl-delete-duplicates items
10671072 :test #'equal
10681073 :from-end browse-kill-ring-display-leftmost-duplicate))
10691074 (when (stringp regexp)
11091114 (set-buffer-modified-p nil)
11101115 (goto-char (point-min))
11111116 (browse-kill-ring-forward 0)
1112 (when regexp
1113 (setq mode-name (concat "Kill Ring [" regexp "]")))
1117 (setq mode-name (if regexp
1118 (concat "Kill Ring [" regexp "]")
1119 "Kill Ring"))
11141120 (run-hooks 'browse-kill-ring-hook)))
11151121 (progn
11161122 (setq buffer-read-only t)))))
11441150 "Display items in the `kill-ring' in another buffer."
11451151 (interactive)
11461152 (if (eq major-mode 'browse-kill-ring-mode)
1147 (message "Already viewing the kill ring")
1148 (let* ((orig-win (selected-window))
1149 (orig-buf (window-buffer orig-win))
1150 (buf (get-buffer-create "*Kill Ring*"))
1151 (kill-ring-yank-pointer-string
1152 (if kill-ring-yank-pointer
1153 (substring-no-properties (car kill-ring-yank-pointer)))))
1154 (browse-kill-ring-setup buf orig-buf orig-win)
1155 (pop-to-buffer buf)
1156 (browse-kill-ring-resize-window)
1157 (unless (eq kill-ring kill-ring-yank-pointer)
1158 (browse-kill-ring-find-entry kill-ring-yank-pointer-string)))))
1153 (error "Already viewing the kill ring"))
1154
1155 (let* ((orig-win (selected-window))
1156 (orig-buf (window-buffer orig-win))
1157 (buf (get-buffer-create "*Kill Ring*"))
1158 (kill-ring-yank-pointer-string
1159 (if kill-ring-yank-pointer
1160 (substring-no-properties (car kill-ring-yank-pointer)))))
1161 (browse-kill-ring-setup buf orig-buf orig-win)
1162 (pop-to-buffer buf)
1163 (browse-kill-ring-resize-window)
1164 (unless (eq kill-ring kill-ring-yank-pointer)
1165 (browse-kill-ring-find-entry kill-ring-yank-pointer-string))))
11591166
11601167 (provide 'browse-kill-ring)
11611168
0 browse-kill-ring-el (2.0.0+git20201101.1.c7a188a-1) UNRELEASED; urgency=low
1
2 * New upstream snapshot.
3
4 -- Debian Janitor <janitor@jelmer.uk> Wed, 21 Jul 2021 20:51:14 -0000
5
06 browse-kill-ring-el (2.0.0-3) unstable; urgency=medium
17
28 * Team upload