diff options
author | James McCoy <jamessan@jamessan.com> | 2016-04-25 23:07:51 -0400 |
---|---|---|
committer | James McCoy <jamessan@jamessan.com> | 2016-07-08 01:38:16 -0400 |
commit | e902a172ef1a58e93eeae0919bddb3578a2142a2 (patch) | |
tree | e470a251718addb6dd89657a3ddcd38de461252a | |
parent | 6cee9d1a17177f4ccdf34283c6ed3ffaa98b32cc (diff) | |
download | rneovim-e902a172ef1a58e93eeae0919bddb3578a2142a2.tar.gz rneovim-e902a172ef1a58e93eeae0919bddb3578a2142a2.tar.bz2 rneovim-e902a172ef1a58e93eeae0919bddb3578a2142a2.zip |
vim-patch:7.4.1384
Problem: It is not easy to use a set of plugins and their dependencies.
Solution: Add packages, ":loadopt", 'packpath'.
https://github.com/vim/vim/commit/f6fee0e2d4341c0c2f5339c1268e5877fafd07cf
-rw-r--r-- | runtime/doc/options.txt | 9 | ||||
-rw-r--r-- | runtime/doc/repeat.txt | 76 | ||||
-rw-r--r-- | runtime/doc/starting.txt | 6 | ||||
-rw-r--r-- | runtime/optwin.vim | 4 | ||||
-rw-r--r-- | src/nvim/eval.c | 1 | ||||
-rw-r--r-- | src/nvim/ex_cmds.lua | 6 | ||||
-rw-r--r-- | src/nvim/ex_cmds2.c | 115 | ||||
-rw-r--r-- | src/nvim/main.c | 3 | ||||
-rw-r--r-- | src/nvim/option.c | 1 | ||||
-rw-r--r-- | src/nvim/option_defs.h | 1 | ||||
-rw-r--r-- | src/nvim/options.lua | 10 | ||||
-rw-r--r-- | src/nvim/version.c | 2 |
12 files changed, 206 insertions, 28 deletions
diff --git a/runtime/doc/options.txt b/runtime/doc/options.txt index 8c2b7786a7..99b9ca0eb1 100644 --- a/runtime/doc/options.txt +++ b/runtime/doc/options.txt @@ -1,4 +1,4 @@ -*options.txt* For Vim version 7.4. Last change: 2016 Feb 20 +*options.txt* For Vim version 7.4. Last change: 2016 Feb 21 VIM REFERENCE MANUAL by Bram Moolenaar @@ -4499,6 +4499,13 @@ A jump table for the options with a short description can be found at |Q_op|. This option cannot be set from a |modeline| or in the |sandbox|, for security reasons. + *'packpath'* *'pp'* +'packpath' 'pp' string (default: see 'runtimepath') + {not in Vi} + {not available without the |+packages| feature} + Directories used to find packages. See |packages|. + + *'paragraphs'* *'para'* 'paragraphs' 'para' string (default "IPLPPPQPP TPHPLIPpLpItpplpipbp") global diff --git a/runtime/doc/repeat.txt b/runtime/doc/repeat.txt index 5b382f95f2..c41d79214a 100644 --- a/runtime/doc/repeat.txt +++ b/runtime/doc/repeat.txt @@ -1,4 +1,4 @@ -*repeat.txt* For Vim version 7.4. Last change: 2016 Feb 12 +*repeat.txt* For Vim version 7.4. Last change: 2016 Feb 21 VIM REFERENCE MANUAL by Bram Moolenaar @@ -12,8 +12,9 @@ Chapter 26 of the user manual introduces repeating |usr_26.txt|. 2. Multiple repeats |multi-repeat| 3. Complex repeats |complex-repeat| 4. Using Vim scripts |using-scripts| -5. Debugging scripts |debug-scripts| -6. Profiling |profiling| +5. Using Vim packages |packages| +6. Debugging scripts |debug-scripts| +7. Profiling |profiling| ============================================================================== 1. Single repeats *single-repeat* @@ -203,6 +204,22 @@ For writing a Vim script, see chapter 41 of the user manual |usr_41.txt|. When 'verbose' is two or higher, there is a message about each searched file. + *:loadp* *:loadplugin* +:loadp[lugin] {name} Search for an optional plugin directory and source the + plugin files found. It is similar to: > + :runtime pack/*/opt/{name}/plugin/*.vim +< However, `:loadplugin` uses 'packpath' instead of + 'runtimepath'. And the directory found is added to + 'runtimepath'. + + Note that {name} is the directory name, not the name + of the .vim file. If the "{name}/plugin" directory + contains more than one file they are all sourced. + + Also see |load-plugin|. + + {not available without the |+packages| feature} + :scripte[ncoding] [encoding] *:scripte* *:scriptencoding* *E167* Specify the character encoding used in the script. The following lines will be converted from [encoding] @@ -373,7 +390,56 @@ Rationale: < Therefore the unusual leading backslash is used. ============================================================================== -5. Debugging scripts *debug-scripts* +5. Using Vim packages *packages* + +A Vim package is a directory that contains one or more plugins. The +advantages over normal plugins: +- A package can be downloaded as an archive and unpacked in its own directory. + That makes it easy to updated and/or remove. +- A package can be a git, mercurial, etc. respository. That makes it really + easy to update. +- A package can contain multiple plugins that depend on each other. +- A package can contain plugins that are automatically loaded on startup and + ones that are only loaded when needed with `:loadplugin`. + +Let's assume your Vim files are in the "~/.local/share/nvim/site" directory +and you want to add a package from a zip archive "/tmp/mypack.zip": + % mkdir -p ~/.local/share/nvim/site/pack/my + % cd ~/.local/share/nvim/site/pack/my + % unzip /tmp/mypack.zip + +The directory name "my" is arbitrary, you can pick anything you like. + +You would now have these files under ~/.local/share/nvim/site: + pack/my/README.txt + pack/my/ever/always/plugin/always.vim + pack/my/ever/always/syntax/always.vim + pack/my/opt/mydebug/plugin/debugger.vim + +When Vim starts up it scans all directories in 'packpath' for plugins under the +"ever" directory and loads them. When found that directory is added to +'runtimepath'. + +In the example Vim will find "my/ever/always/plugin/always.vim" and adds +"~/.local/share/nvim/site/pack/my/ever/always" to 'runtimepath'. + +If the "always" plugin kicks in and sets the 'filetype' to "always", Vim will +find the syntax/always.vim file, because its directory is in 'runtimepath'. + + *load-plugin* +To load an optional plugin from a pack use the `:loadplugin` command: > + :loadplugin mydebug +This could be done inside always.vim, if some conditions are met. +Or you could add this command to your |.vimrc|. + +It is perfectly normal for a package to only have files in the "opt" +directory. You then need to load each plugin when you want to use it. + +Loading packages will not happen if loading plugins is disabled, see +|load-plugins|. + +============================================================================== +6. Debugging scripts *debug-scripts* Besides the obvious messages that you can add to your scripts to find out what they are doing, Vim offers a debug mode. This allows you to step through a @@ -597,7 +663,7 @@ OBSCURE user, don't use typeahead for debug commands. ============================================================================== -6. Profiling *profile* *profiling* +7. Profiling *profile* *profiling* Profiling means that Vim measures the time that is spent on executing functions and/or scripts. The |+profile| feature is required for this. diff --git a/runtime/doc/starting.txt b/runtime/doc/starting.txt index ad2649b765..0508c52540 100644 --- a/runtime/doc/starting.txt +++ b/runtime/doc/starting.txt @@ -1,4 +1,4 @@ -*starting.txt* For Vim version 7.4. Last change: 2016 Feb 18 +*starting.txt* For Vim version 7.4. Last change: 2016 Feb 21 VIM REFERENCE MANUAL by Bram Moolenaar @@ -463,6 +463,10 @@ accordingly. Vim proceeds in this order: commands from the command line have not been executed yet. You can use "--cmd 'set noloadplugins'" |--cmd|. + Plugin packs are loaded. These are plugins, as above, but found in + 'packpath' directories. Every plugin directory found is added in + 'runtimepath'. See |packages|. + 7. Set 'shellpipe' and 'shellredir' The 'shellpipe' and 'shellredir' options are set according to the value of the 'shell' option, unless they have been set before. diff --git a/runtime/optwin.vim b/runtime/optwin.vim index 68444dde01..7e58c76ec4 100644 --- a/runtime/optwin.vim +++ b/runtime/optwin.vim @@ -1,7 +1,7 @@ " These commands create the option window. " " Maintainer: Bram Moolenaar <Bram@vim.org> -" Last Change: 2015 Jul 22 +" Last Change: 2016 Feb 21 " If there already is an option window, jump to that one. if bufwinnr("option-window") > 0 @@ -228,6 +228,8 @@ else endif call append("$", "runtimepath\tlist of directories used for runtime files and plugins") call <SID>OptionG("rtp", &rtp) +call append("$", "packpath\tlist of directories used for plugin packages") +call <SID>OptionG("pp", &pp) call append("$", "helpfile\tname of the main help file") call <SID>OptionG("hf", &hf) diff --git a/src/nvim/eval.c b/src/nvim/eval.c index 9a86c5765c..d2b9bf66e1 100644 --- a/src/nvim/eval.c +++ b/src/nvim/eval.c @@ -10782,6 +10782,7 @@ static void f_has(typval_T *argvars, typval_T *rettv) "mouse", "multi_byte", "multi_lang", + "packages", "path_extra", "persistent_undo", "postscript", diff --git a/src/nvim/ex_cmds.lua b/src/nvim/ex_cmds.lua index 6c58879d58..7bfb592ea7 100644 --- a/src/nvim/ex_cmds.lua +++ b/src/nvim/ex_cmds.lua @@ -1453,6 +1453,12 @@ return { func='ex_loadkeymap', }, { + command='loadplugin', + flags=bit.bor(BANG, FILE1, TRLBAR, SBOXOK, CMDWIN), + addr_type=ADDR_LINES, + func='ex_loadplugin', + }, + { command='lockmarks', flags=bit.bor(NEEDARG, EXTRA, NOTRLCOM), addr_type=ADDR_LINES, diff --git a/src/nvim/ex_cmds2.c b/src/nvim/ex_cmds2.c index 40074f726c..d5740e224b 100644 --- a/src/nvim/ex_cmds2.c +++ b/src/nvim/ex_cmds2.c @@ -2284,21 +2284,9 @@ int source_runtime(char_u *name, int all) return do_in_runtimepath(name, all, source_callback, NULL); } -/// Find "name" in 'runtimepath'. When found, invoke the callback function for -/// it: callback(fname, "cookie") -/// When "all" is true repeat for all matches, otherwise only the first one is -/// used. -/// Returns OK when at least one match found, FAIL otherwise. -/// If "name" is NULL calls callback for each entry in runtimepath. Cookie is -/// passed by reference in this case, setting it to NULL indicates that callback -/// has done its job. -int do_in_runtimepath(char_u *name, int all, DoInRuntimepathCB callback, - void *cookie) +static int do_in_path(char_u *path, char_u *name, bool all, + DoInRuntimepathCB callback, void *cookie) { - char_u *rtp; - char_u *np; - char_u *buf; - char_u *rtp_copy; char_u *tail; int num_files; char_u **files; @@ -2307,18 +2295,18 @@ int do_in_runtimepath(char_u *name, int all, DoInRuntimepathCB callback, // Make a copy of 'runtimepath'. Invoking the callback may change the // value. - rtp_copy = vim_strsave(p_rtp); - buf = xmallocz(MAXPATHL); + char_u *rtp_copy = vim_strsave(path); + char_u *buf = xmallocz(MAXPATHL); { if (p_verbose > 1 && name != NULL) { verbose_enter(); smsg(_("Searching for \"%s\" in \"%s\""), - (char *)name, (char *)p_rtp); + (char *)name, (char *)path); verbose_leave(); } // Loop over all entries in 'runtimepath'. - rtp = rtp_copy; + char_u *rtp = rtp_copy; while (*rtp != NUL && (all || !did_one)) { // Copy the path from 'runtimepath' to buf[]. copy_option_part(&rtp, buf, MAXPATHL, ","); @@ -2332,7 +2320,7 @@ int do_in_runtimepath(char_u *name, int all, DoInRuntimepathCB callback, tail = buf + STRLEN(buf); // Loop over all patterns in "name" - np = name; + char_u *np = name; while (*np != NUL && (all || !did_one)) { // Append the pattern from "name" to buf[]. assert(MAXPATHL >= (tail - buf)); @@ -2373,6 +2361,95 @@ int do_in_runtimepath(char_u *name, int all, DoInRuntimepathCB callback, return did_one ? OK : FAIL; } +/// Find "name" in 'runtimepath'. When found, invoke the callback function for +/// it: callback(fname, "cookie") +/// When "all" is true repeat for all matches, otherwise only the first one is +/// used. +/// Returns OK when at least one match found, FAIL otherwise. +/// If "name" is NULL calls callback for each entry in runtimepath. Cookie is +/// passed by reference in this case, setting it to NULL indicates that callback +/// has done its job. +int do_in_runtimepath(char_u *name, bool all, DoInRuntimepathCB callback, + void *cookie) +{ + return do_in_path(p_rtp, name, all, callback, cookie); +} + +static void source_pack_plugin(char_u *fname, void *cookie) +{ + char_u *p6, *p5, *p4, *p3, *p2, *p1, *p; + char_u *new_rtp; + + p4 = p3 = p2 = p1 = get_past_head(fname); + for (p = p1; *p; mb_ptr_adv(p)) { + if (vim_ispathsep_nocolon(*p)) { + p6 = p5; p5 = p4; p4 = p3; p3 = p2; p2 = p1; p1 = p; + } + } + + // now we have: + // rtp/pack/name/ever/name/plugin/name.vim + // p6 p5 p4 p3 p2 p1 + + // find the part up to "pack" in 'runtimepath' + char_u c = *p6; + *p6 = NUL; + p = (char_u *)strstr((char *)p_rtp, (char *)fname); + if (p == NULL) { + // not found, append at the end + p = p_rtp + STRLEN(p_rtp); + } else { + // append after the matching directory. + p += STRLEN(fname); + } + *p6 = c; + + c = *p2; + *p2 = NUL; + if (strstr((char *)p_rtp, (char *)fname) == NULL) { + // directory not in 'runtimepath', add it + size_t oldlen = STRLEN(p_rtp); + size_t addlen = STRLEN(fname); + new_rtp = try_malloc(oldlen + addlen + 1); + if (new_rtp == NULL) { + *p2 = c; + return; + } + uintptr_t keep = (uintptr_t)(p - p_rtp); + memmove(new_rtp, p_rtp, keep); + new_rtp[keep] = ','; + memmove(new_rtp + keep + 1, fname, addlen + 1); + if (p_rtp[keep] != NUL) { + memmove(new_rtp + keep + 1 + addlen, p_rtp + keep, + oldlen - keep + 1); + } + free_string_option(p_rtp); + p_rtp = new_rtp; + } + *p2 = c; + + (void)do_source(fname, false, DOSO_NONE); +} + +// Source the plugins in the package directories. +void source_packages(void) +{ + do_in_path(p_pp, (char_u *)"pack/*/ever/*/plugin/*.vim", + true, source_pack_plugin, NULL); +} + +// ":loadplugin {name}" +void ex_loadplugin(exarg_T *eap) +{ + static const char *pattern = "pack/*/opt/%s/plugin/*.vim"; + + size_t len = STRLEN(pattern) + STRLEN(eap->arg); + char *pat = xmallocz(len); + vim_snprintf(pat, len, pattern, eap->arg); + do_in_path(p_pp, (char_u *)pat, true, source_pack_plugin, NULL); + xfree(pat); +} + /// ":options" void ex_options(exarg_T *eap) { diff --git a/src/nvim/main.c b/src/nvim/main.c index 5cd1dbb467..dcfd9b0fdf 100644 --- a/src/nvim/main.c +++ b/src/nvim/main.c @@ -1243,6 +1243,9 @@ static void load_plugins(void) if (p_lpl) { source_runtime((char_u *)"plugin/**/*.vim", TRUE); TIME_MSG("loading plugins"); + + source_packages(); + TIME_MSG("loading packages"); } } diff --git a/src/nvim/option.c b/src/nvim/option.c index a844c4ed80..be3cb914b2 100644 --- a/src/nvim/option.c +++ b/src/nvim/option.c @@ -5839,6 +5839,7 @@ set_context_in_set_cmd ( if (p == (char_u *)&p_bdir || p == (char_u *)&p_dir || p == (char_u *)&p_path + || p == (char_u *)&p_pp || p == (char_u *)&p_rtp || p == (char_u *)&p_cdpath || p == (char_u *)&p_vdir diff --git a/src/nvim/option_defs.h b/src/nvim/option_defs.h index b1a2b00bdb..833da7907c 100644 --- a/src/nvim/option_defs.h +++ b/src/nvim/option_defs.h @@ -521,6 +521,7 @@ EXTERN int p_ari; /* 'allowrevins' */ EXTERN int p_ri; /* 'revins' */ EXTERN int p_ru; /* 'ruler' */ EXTERN char_u *p_ruf; /* 'rulerformat' */ +EXTERN char_u *p_pp; /* 'packpath' */ EXTERN char_u *p_rtp; /* 'runtimepath' */ EXTERN long p_sj; /* 'scrolljump' */ EXTERN long p_so; /* 'scrolloff' */ diff --git a/src/nvim/options.lua b/src/nvim/options.lua index 218e34f595..d19af4f73f 100644 --- a/src/nvim/options.lua +++ b/src/nvim/options.lua @@ -1640,6 +1640,16 @@ return { defaults={if_true={vi=""}} }, { + full_name='packpath', abbreviation='pp', + type='string', list='onecomma', scope={'global'}, + deny_duplicates=true, + secure=true, + vi_def=true, + expand=true, + varname='p_pp', + defaults={if_true={vi=''}} + }, + { full_name='paragraphs', abbreviation='para', type='string', scope={'global'}, vi_def=true, diff --git a/src/nvim/version.c b/src/nvim/version.c index 278255c904..95f924d6a1 100644 --- a/src/nvim/version.c +++ b/src/nvim/version.c @@ -311,7 +311,7 @@ static int included_patches[] = { // 1387 NA // 1386 NA // 1385 NA - // 1384, + 1384, // 1383 NA // 1382 NA // 1381 NA |