2019-03-18 10:51:41 +01:00
|
|
|
;; TODO: Since Helm 3.1, we can pop up buffers in other window/frame.
|
2019-03-03 11:38:06 +01:00
|
|
|
(defun ambrevar/helm-source-buffer-not-found (&optional mode new-fn)
|
|
|
|
"See `helm-source-buffer-not-found'."
|
|
|
|
(helm-build-dummy-source
|
|
|
|
"Create buffer"
|
|
|
|
:action `(("Create buffer (C-u choose mode)" .
|
|
|
|
(lambda (candidate)
|
|
|
|
(if (not ,new-fn)
|
|
|
|
(let ((mjm (or (and helm-current-prefix-arg
|
|
|
|
(intern-soft (helm-comp-read
|
|
|
|
"Major-mode: "
|
|
|
|
helm-buffers-favorite-modes)))
|
|
|
|
,mode
|
|
|
|
(cl-loop for (r . m) in auto-mode-alist
|
|
|
|
when (string-match r candidate)
|
|
|
|
return m)))
|
|
|
|
(buffer (get-buffer-create candidate)))
|
|
|
|
(if mjm
|
|
|
|
(with-current-buffer buffer (funcall mjm))
|
|
|
|
(set-buffer-major-mode buffer))
|
|
|
|
(switch-to-buffer buffer))
|
2019-03-10 11:29:51 +01:00
|
|
|
(let ((new-buffer (save-window-excursion (funcall ',new-fn candidate)
|
|
|
|
(current-buffer))))
|
|
|
|
(switch-to-buffer new-buffer))))))))
|
2019-02-22 17:55:23 +01:00
|
|
|
|
2019-03-03 17:20:07 +01:00
|
|
|
(defmacro helm-deflister (name predicate new-fn &optional extra-sources)
|
2019-02-22 17:55:23 +01:00
|
|
|
(let ((buffer-source-name (format "%s buffers" name)))
|
|
|
|
(add-to-list 'helm-source-names-using-follow buffer-source-name)
|
|
|
|
`(defun ,(intern (format "helm-%s-buffers" (downcase name))) ()
|
|
|
|
(interactive)
|
2019-03-03 11:38:06 +01:00
|
|
|
(helm
|
|
|
|
:sources
|
|
|
|
(list (helm-make-source ,(format "%s buffers" name) 'helm-source-buffers
|
|
|
|
:buffer-list (lambda ()
|
|
|
|
(cl-loop for b in (buffer-list)
|
|
|
|
when (funcall ,predicate b)
|
|
|
|
collect (buffer-name b))))
|
|
|
|
,@(let ((mode (intern (format "%s-mode" (downcase name)))))
|
2019-03-10 11:29:26 +01:00
|
|
|
(unless (fboundp mode)
|
|
|
|
;; For cased mode names like `Info-mode'.
|
|
|
|
(setq mode (intern (format "%s-mode" name))))
|
2019-03-03 11:38:06 +01:00
|
|
|
(when (fboundp mode)
|
2019-03-03 11:59:11 +01:00
|
|
|
`((ambrevar/helm-source-buffer-not-found
|
2019-03-03 12:22:23 +01:00
|
|
|
',mode
|
2019-03-03 17:20:07 +01:00
|
|
|
,new-fn))))
|
|
|
|
,@extra-sources)
|
|
|
|
:buffer ,(format "*helm-%s-buffers*" name)))))
|
2019-02-22 17:55:23 +01:00
|
|
|
|
2019-03-03 11:59:27 +01:00
|
|
|
(defmacro helm-defswitcher (name predicate new-fn &optional helm-lister &rest extra-sources)
|
2019-03-03 11:38:06 +01:00
|
|
|
"Create an interactive buffer switcher for NAME.
|
|
|
|
When current buffer is not of NAME, switch to last NAME session if any.
|
2019-02-22 18:26:57 +01:00
|
|
|
Otherwise create a new one and switch to it.
|
2019-03-03 11:38:06 +01:00
|
|
|
If current buffer is of NAME, show the buffer list."
|
|
|
|
(let ((switch (intern (format "helm-%s-switch" (downcase name)))))
|
2019-02-22 18:26:57 +01:00
|
|
|
`(progn
|
|
|
|
(helm-deflister ,name ,predicate ,new-fn ,extra-sources)
|
2019-03-03 11:38:06 +01:00
|
|
|
(defun ,switch (&optional menu other-window)
|
2019-02-22 18:26:57 +01:00
|
|
|
(interactive "P")
|
2019-03-03 11:38:06 +01:00
|
|
|
(if (or menu (funcall ,predicate (current-buffer)))
|
2019-02-22 18:26:57 +01:00
|
|
|
;; TODO: Funcall the return value of helm-deflister.
|
2019-03-03 11:59:27 +01:00
|
|
|
(funcall ',(or helm-lister
|
|
|
|
(intern (format "helm-%s-buffers" (downcase name)))))
|
2019-02-22 18:26:57 +01:00
|
|
|
(let ((last (cl-loop for buffer in (buffer-list)
|
|
|
|
when (funcall ,predicate buffer)
|
|
|
|
return buffer)))
|
|
|
|
(if last
|
2019-02-25 18:19:51 +01:00
|
|
|
(if (get-buffer-window last)
|
|
|
|
(select-window (get-buffer-window last))
|
|
|
|
(funcall (if other-window 'switch-to-buffer-other-window 'switch-to-buffer) last))
|
2019-03-08 09:47:36 +01:00
|
|
|
;; First buffer:
|
2019-04-08 10:40:39 +02:00
|
|
|
(let ((first-buffer (save-window-excursion (funcall #',new-fn) (current-buffer))))
|
2019-03-08 09:47:36 +01:00
|
|
|
(funcall (if other-window 'switch-to-buffer-other-window 'switch-to-buffer)
|
|
|
|
first-buffer))))))
|
2019-02-25 18:19:51 +01:00
|
|
|
(defun ,(intern (format "helm-%s-switch-other-window" (downcase name))) (&optional menu)
|
|
|
|
(interactive "P")
|
2019-03-03 11:38:06 +01:00
|
|
|
(funcall ',switch menu 'other-window)))))
|
2019-02-22 17:55:23 +01:00
|
|
|
|
|
|
|
(provide 'patch-helm)
|