ctrlpvim / ctrlp.vim

Active fork of kien/ctrlp.vim—Fuzzy file, buffer, mru, tag, etc finder.
ctrlpvim.github.com/ctrlp.vim
Other
5.57k stars 260 forks source link

Custom Mode API #67

Open LFDM opened 9 years ago

LFDM commented 9 years ago

Just a little feature idea, was thinking about this after reading about vim-projectionist. Forgive me if this is all in vain and there is actually something implemented to enable this or something similar already.

I often repeat myself typing specific strings when I want to reach a file, that is named or placed in a structured way.

Let's say I am working with angularJS and I want to open a specific template file, which is stored in somewhere in a folder that is called templates and is definetely an .html file. (there are other and probably better ways to place template files in angular projects, but this is just an example to clarify my point). Let's say the full filename of this template starting from the project root is app/templates/my_module/confirmation_dialog.html

In this case I would probably hit <ctrl>-p and type tplconfirmahtml to make use of fuzzy matching and get there somewhat accurately.

The idea now would be to add an API to define custom modes on a project basis to make this more accurate and faster, enabling us to enter just the part of the filename we really care about.

E.g., I add a dictionary to my project root, named .ctrlp_custom_modes.json with the following content

{
  "templates": "app/templates/@@input@@.html"
}

On vim's startup, this file would be read in and add a templates mode to ctrlp, which we could probably also directly access through a shortcut.

This custom mode would simply wrap the input of a user when he tries to fuzzy-match a file with the string given in this dictionary, where @@input@@ is a placeholder for the user input.

If I bring up this mode and type mm/co, ctrlp would really search as if I had typed app/templates/mm/co.html which would almost be a sure match (that is if i don't add any typos...).

As this is a quite unsophisticated way of implementing it and just using the regular fuzzy-matching routines, some false positives might show up, but I guess this is ok - especially since this is also very powerful and could in fact be considered a feature.

A second example, again Angular specific: Another way to declare filenames is by suffixing them according to what kind of structure they contain. A path to a directive might look like /client/my_module/my_feature/user_list.directive.js

The custom mode definition would be

{
  "directives" : "client/@@input@@.directive.js"
}

to add a directives mode that looks for a .directive.js file anywhere inside the client directory.

The file could probably also specify the shortcuts to bring up ctrlp in a custom mode by predefining a couple of plugs (which you then define in your .vimrc). One would probably never have a use for more than 5 (or let's say 10, if people want to get crazy), so we could predefine ctrlp_custom_mode plugs 1-10 and a project based shortcut list could look like:

{
  "directives" : "1"
  "templates" : "2"
}

to start ctrp in the directives mode through the ctrlp_custom_mode1 plug and the templates mode through the ctrlp_custom_mode2 plug.

So guys, what do you think? Would you think this is useful to have? I think this would be quite easy to implement as well - when one knows where to start. I'd be very grateful for any pointers to the code from people who know the ctrlp codebase a bit, which would save lots of time in case I start to implement this myself ;)

Thanks!

rburny commented 9 years ago

You can use mappings to pass some initial input into CtrlP window, and even position your cursor properly. The following:

map <C-n> <C-p>plugin/.cc<Left><Left><Left>

makes C-n open CtrlP window, enter "plugin/.cc", and leave cursor before the dot. It should be a pretty simple way of achieving what you want.

LFDM commented 9 years ago

Thanks @rburny, a nice and simple idea!

Actually also did a little bit of code reading - and am almost there, producing a plugin that generates ctrlp extensions dynamically. This extension system is really well done. Just need one more function within ctrlp to make this work - will follow up on this in the new year and add a PR for it.

LFDM commented 9 years ago

This is available now at https://github.com/LFDM/ctrlp_custom_modes

It awaits a json file in a project's root called .ctrlp_custom_modes.json with the following markup:

[
  [ "snippets", "snippets/ultisnips/@@input@@.snippets" ]
]

Will add documentation to it soon. One slight change to CtrlP was needed to do this, PR coming in a couple of minutes.