Icicles - Other Search Commands

Previous: Icicles - Search-And-ReplaceIciclesIciclesIndexNext: Icicles - Bookmark Enhancements

Other Icicles Search Commands

Function ‘icicle-search’ is very general. As is explained in Icicles - Search Commands, Overview, command ‘icicle-occur’ is defined trivially using ‘icicle-search’ – it is basically ‘icicle-search’ with a regexp of `.*’, to match entire lines. Similarly, ‘icicle-search-word’ (`C-c $’) uses a regexp of `\b WORD \b’, where `WORD ‘ is the word to look for, and ‘icicle-search-keywords’ (`C-c ^’) uses a regexp of `\( KW1 \| KW2 \| KW2\| KWn \)’, where the ‘KWm’ are the keywords (regexps) to look for.

Still other Icicles commands are available that make use of ‘icicle-search’. And you can define your own, specialized search commands along the same lines. To do that, it is instructive to look at the source code of the commands described in this section; they can serve as a model for defining your own search commands.

Two of the commands described here, ‘icicle-compilation-search’ and ‘icicle-comint-search’, are specialized versions of ‘icicle-search’ that work only in particular buffers where there is little need for ‘icicle-search’ itself. For this reason, these commands reuse the key sequence, `C-c `’ (backquote), that is normally bound to ‘icicle-search’. This shadow binding occurs if the current major mode is a compilation mode (for ‘icicle-compilation-search’) or an interactive interpreter mode such as ‘shell-mode’ or Lisp interactive mode (for ‘icicle-comint-search’).

[Programmer Note: Actually, the way this works is that `C-c `’ and ‘M-s M-s M-s’ are bound to ‘icicle-search-generic’, which calls the command that is the value of internal variable ‘icicle-search-command’. You can use this mechanism to provide custom Icicles search commands for particular buffers.]

Besides the commands described on this page, there are Icicles search commands for navigating TagsFile definitions and searching their associated source files. These are described in section Icicles - Emacs Tags Enhancements.

If you use ‘M-g’ in the minibuffer to toggle option `icicle-use-C-for-actions-flag’, then you can use just ‘next’ instead of ‘C-next’ to navigate when using any Icicles search command. See icicle-use-C-for-actions-flag.

Searching Text with Properties

Instead of providing a context regexp, for commands ‘icicle-search-char-property’, ‘icicle-search-overlay-property’, and ‘icicle-search-text-property’ (`C-c “’) you provide a text or overlay property (e.g. ‘face’) and its value (e.g. ‘font-lock-function-name-face’). All zones of text that have that property with that value become the completion candidates (search hits). As always, you can filter this set of candidates by typing input in the minibuffer.

‘icicle-search-char-property’ searches either or both kinds of property: text or overlay; ‘icicle-search-overlay-property’ searches only overlay properties; ‘icicle-search-text-property’ (`C-c "’) searches only text properties.

For example, if you use ‘icicle-search-char-property’ with a ‘face’ property value ‘highlight’, then the text searched includes text with that overlay value and text with that text-property value. With a ‘face’ property value of ‘font-lock-string-face’, you can browse or search doc strings, and so on.

If the property chosen is ‘face’, then you can in fact choose multiple faces, in multi-command fashion (e.g. ‘C-mouse-2’), and the text that is searched has at least one of the faces you choose. If you choose no face value (empty input), then the target is text that has any face at all. The search hits are zones of text that are distinguished by their ‘face’ values.

As with other Icicles search commands, a prefix argument controls whether these property-searching commands search the current buffer, selected bookmarks, selected files, or selected buffers. However, keep in mind that, since in this case you are searching text or overlay properties, you will find search hits only for buffers that already have such properties, for example, buffers that have been fontified.

Icicles Imenu: `icicle-imenu'

Command ‘icicle-imenu’, which is bound to `C-c =’, is an Imenu browser. It lets you use Icicles completion to navigate among or search the content of definitions of functions, variables, macros, keys, and so on in a programming language (any language that Imenu handles). As always in Icicles, your current input (e.g. a regexp) filters the set of available candidates. That is, you can match against parts of an Imenu entry – any parts. That’s particularly useful if there are many entries in the Imenu menu; you do not need to read/scan the whole list.

Here’s a screenshot of using ‘icicle-imenu’ to find function definitions (Imenu submenu Functions) that match the regexp ‘kill’:


If you look at the definition of ‘icicle-imenu’ you’ll see that it simply lets you choose an Imenu submenu (Functions, Options, and so on) that is appropriate for the current buffer type, and then it calls ‘icicle-search’, passing it the appropriate Imenu regexp.

You can similarly define your own specialized search commands using ‘icicle-search’ to browse regexp matches. You get all of the features of ‘icicle-search’ when you do that. For example, ‘icicle-imenu’ gives you these advantages over a standard Imenu menu:

When you use an Icicles Imenu command, first you choose a submenu for a given object type (e.g. submenu Functions for functions), and then you choose an object definition from that submenu. But multiple regexps can be used for a given Imenu submenu, such as Function. Icicles Imenu commands use these regexps separately, so they present multiple completion candidates with the same name when you choose the object type.

For example, if two different regexps are used to gather function definitions then there might be two corresponding Functions candidates (depending on whether there are matches for each of the regexps). Choosing one or the other of these submenu candidates then gives you different function choices. (Remember that you can cycle to choose among multiple candidates that have the same name.)

Type-Specific Imenu Commands

In addition, Icicles provides specializations of ‘icicle-imenu’ to find only definitions of particular types:

All of these commands use only the Imenu regexps that match entities of different types. Because these regexps were designed (for Imenu) only to locate the start of a definition, they generally do not match full definitions. This makes them OK for use by an Icicles multi-command as a browser, to navigate among definitions. But it does not make them useful for searching the content of definitions.

Imenu Commands that Search Full Definitions

Icicles also provides a similar set of commands, with the same names but with suffix ‘-full’, which do use full definitions as the completion candidates, so you can search those bodies. When you only want to navigate, you will generally use the non ‘-full’ commands because the candidates are simpler. When you want to search you will generally use the ‘-full’ commands.

Be aware that “full” really means what it says only for definitions in languages like Lisp. These commands in fact first match the Imenu regexp, then use the text between the regexp match beginning and one sexp forward. In the case of Lisp sexps, that means they use the full sexp for the definition. But in the case of other languages, such as C, the “full” definitions can in fact be shorter than the simple regexp matches.

Icicles Imenu Combines Benefits of Imenu and Emacs Tags

Like Emacs tags, Icicles Imenu commands let you navigate among definitions in multiple files – and also multiple bookmarks and multiple non-file buffers. Like Imenu, you need not build a tags file. Unlike Imenu, Icicles provides regexp completion that lets you filter Imenu hits that you want to visit.

Another difference from Emacs tags, besides the need for a tags file, is that, since Icicles locates definitions using Imenu regexps, you can only navigate among definitions in buffers that you are visiting. This is both an advantage and a disadvantage: you can narrow the search to certain files, but you must know which files to search. And if you want to search all files, then you must open them all (e.g. by matching a project regexp),

The differences mean that Icicles Imenu commands do not provide a substitute for Emacs tags; they provide some similar functionality. They add another tool to your tool belt, handier in some situations than using tags, and less useful in some other situations.

See Also: Icicles - Emacs Tags Enhancements

Searching Thing-At-Point Things

Command ‘icicle-search-thing’ lets you search the content of buffer zones whose text represents things of a particular kind: `sexp’, ‘defun’, `sentence’, `paragraph’, and so on.

Library ThingAtPoint+ provides many enhancements and some bug fixes for the basic ‘thing-at-point’ functionality provided by vanilla library thingatpt.el. I strongly recommend that you use it if you use command ‘icicle-search-thing’.

Be aware that the thing-at-point functions have as their main purpose to let you retrieve a textual thing at point. In many cases they rely on ‘forward-THING’ functions that do not move past the thing if point is already inside it.

One result of this is that in some cases the thing returned is composed only of whitespace. That can sometimes be what you want: whitespace text is non-empty text. But in other cases you are not interested in whitespace-only targets. (This is not specific to Icicles search.)

Quiz: How would you remove whitespace-only completion candidates? By matching them and then complementing that match. A regexp such as this matches most of them: \` \n\t]\'. (You could also include \r, \f, and \v.) To get that you would hit these keys:

    \ ` [ SPC C-q C-j C-q TAB ] + \ '

Then, to match the whitespace-only candidates and remove them you would hit `S-TAB C-~ S-TAB’.

(Be aware, BTW, that character class [:space:] does not match newline or carriage-return characters in some common Emacs modes. For example, in Emacs-Lisp mode, a newline character has syntax class ‘comment ender’, and a carriage return character has syntax class ‘symbol’. Character class [:space:] corresponds only to characters with syntax class ‘whitespace’.)

Compile/Grep Search: `icicle-compilation-search'

In a compilation-results buffer, such as ‘*Compilation*’ or ‘*grep*’, you can use command ‘icicle-compilation-search’, bound to `C-c `’, to search among the result set (search hits). This is similar to ‘icicle-search’, but when you use ‘C-RET’, ‘C-mouse-2’, ‘C-down’, ‘C-up’, ‘C-next’, ‘C-prior’, ‘C-end’, or ‘C-home’, it visits the source code that corresponds to the current line in the compilation buffer. Just as for ‘icicle-search’, you can narrow the set of search contexts by typing a regexp.

Using ‘icicle-compilation-search’ with ‘grep’ gives you two levels of regexp searching: 1) the ‘grep’ regexp and 2) your current input regexp. And you can of course use progressive completion (‘M-*’ or ‘S-SPC’) to add any number of additional levels. (And, starting with Emacs 22, you can pipe to other ‘grep’ commands in the same ‘M-x grep’.)

Use `grep' and Compilation Output for Search-and-Replace

In Emacs 22 and later, you can also replace search-hit text. You can replace the entire ‘grep’ regexp match or just the part of it that matches your current input, depending on the value of option `icicle-search-replace-whole-candidate-flag’ (which you can toggle with `M-_’). Replacement acts here just as it does for ‘icicle-search’.

You can also use a non-‘grep’ compilation buffer to perform search and replace. Use it, for example, to correct errors in source files.

Icicles thus gives you several ways to perform search-and-replace throughout multiple files: ‘grep’/compilation, ‘icicle-occur’, and ‘icicle-search’. The latter is of course not limited to line-by-line search.

See Also: Icicles - Search-And-Replace.

Input Reuse in Interactive Interpreter Modes: `icicle-comint-search'

In an interactive interpreter mode such as ‘shell-mode’ or interactive Lisp mode, you can search for and reuse a previous input, possibly editing it first. Command ‘icicle-comint-search’, bound to `C-c `’, lets you use Icicles completion and cycling to access your previous (shell or Lisp) inputs; it uses ‘icicle-search’, so it highlights your regexp input matches, and so on. You can use `C-$’ at any time to toggle removal of duplicate past inputs as completion candidates; by default, duplicates are removed.

Being a search command, however, ‘icicle-comint-search’ has access only to the commands that are visible in the buffer. It does not use the ‘comint-input-ring’, so it cannot, for instance, give you access to commands used in a previous session, which might have been recorded in a history file.

Another Icicles command, ‘icicle-comint-command’, which is not a search command, does use ‘comint-input-ring’ and does give you completion and cycling against previous inputs that might not have come from the current session. It is bound to ‘C-c TAB’ in ‘comint-mode’ and derived modes.

Define Your Own Icicles Search Commands

Function ‘icicle-search’ is not only a useful user command; it is also a framework for you to define your own Icicles search commands. Consult the source code for the commands presented above for models. And consult the doc string of ‘icicle-search’ for more information about calling it non-interactively. In particular, note that:

By using your own function to define the search contexts, either from scratch or by limiting regexp matches using a predicate, you can perform semantic-based searching. That is, your search command can use information besides syntax to define search hits. For instance, commands ‘icicle-imenu-command’ and ‘icicle-imenu-non-interactive-function’ use the semantic predicate ‘commandp’ to distinguish EmacsLisp commands from non-interactive functions.

See Also:

Previous: Icicles - Search-And-ReplaceIciclesIciclesIndexNext: Icicles - Bookmark Enhancements

DrewsElispLibraries referenced here: Lisp:icicles.el

CategoryCommands CategoryCompletion CategoryRegexp CategoryModes CategoryProgrammerUtils CategoryCode CategorySearchAndReplace CategoryShell CategoryNavigation