ctrlf
ctrlf copied to clipboard
Request: Emulating macOS's Find Next/Previous Commands
There are some very useful standard Mac finding commands/behaviors that I'd love to be able to emulate in ctrlf
. The relevant commands (in almost any Mac app) can be found in the menubar under "Edit > Find":
-
Find... — This is pretty much what ctrlf does, however the Mac doesn't start with an empty search, it starts with the last thing you searched for.
This is possible to emulate with
(ctrlf-forward 'fuzzy nil ctrlf--last-input)
. However, I have no idea if this is robust or a "bad idea" in some way.Also, it doesn't seem that
ctrlf-backward
allows for theinitial-contents
argument. -
Find Next/Previous — This command jumps directly to the next/previous occurrence of your last search without activating the Find interface. This, admittedly, isn't all that different from typing
C-s C-s
but there are circumstances when jumping to the next occurrence without the find interface is nice, and faster since you don't need to exit the interface. -
Use Selection For Find — This command simply uses the selected text for the next Find command. So you can select some text, type
command-E
, thencommand-G
to jump to the next occurrence of that text (no find interface). Alternatively, you might want to select some text, hitcommand-E
, and then call up the find interface withcommand-F
so you can edit the search term.I don't know if this is the proper and complete way to do this, but it should be possible with something like:
(defun ctrlf-push-region-to-history ()
(interactive)
(if (use-region-p)
(setq ctrlf--last-input (buffer-substring (region-beginning) (region-end)))
(error "No active region")))
So my proposal is:
- Provide a user-facing variable that makes ctrlf commands start with the
last-input
by default. Or perhaps alternate functions which do this. - Provide functions for jumping (forward and back) to the
last-input
without activating ctrlf. - Provide a function for pushing the region to
last-input
.
These all seem like reasonable proposals. My thoughts:
- I am not sure why
initial-contents
is not supported inctrlf-backward
; that feature was added in https://github.com/raxod502/ctrlf/pull/48. I suspect it would be straightforward to port. - Rather than
ctrlf--last-input
, you can use(car ctrlf-search-history)
. That should work better. (I am not sure your code forctrlf-push-region-to-history
would actually work, as I thinkctrlf--last-input
is reset to nil when starting a search.)
It might be best to start by seeing if you can implement these user commands using the existing CTRLF public interface, and then if others express interest in the same feature, we could add them to CTRLF.
I have sort of implemented this just with my configuration. There are two issues:
- there may be a bug in search-backward in that it isn't accepting a search query
- For some reason, ctrlf-mode-map has precedence over ctrlf-minibuffer-mode-map, so I don't get the "s-g" to go to next candidate to work
(use-package ctrlf
:preface
(defun bsp-ctrlf-region-forward ()
(interactive)
(if (use-region-p)
(let ((beg (region-beginning))
(end (region-end)))
(deactivate-mark)
(ctrlf-forward ctrlf-default-search-style nil
(buffer-substring-no-properties beg end)))
(ctrlf-forward-default)))
(defun bsp-ctrlf-search-last ()
(interactive)
(ctrlf-forward ctrlf-default-search-style nil
(car ctrlf-search-history)))
(defun bsp-ctrlf-search-last-backward ()
(interactive)
(ctrlf-backward ctrlf-default-search-style nil
(car ctrlf-search-history)))
:init
(ctrlf-mode +1)
:bind (:map ctrlf-mode-map
("s-f" . ctrlf-forward-default)
("s-F" . ctrlf-backward-default)
("s-g" . bsp-ctrlf-search-last)
("s-G" . bsp-ctrlf-search-last-backward)
("s-e" . bsp-ctrlf-region-forward)
:map ctrlf-minibuffer-mode-map
("s-g" . ctrlf-forward-default)
("s-G" . ctrlf-backward-default)))
Edit: had pasted wrong version of code prior