Hi,

On Fri, May 20, 2016 at 9:17 AM, Bram Moolenaar <[email protected]>
wrote:

>
> Justin Keyes wrote:
>
> >
> > ```
> > Doesn't work for :diffsplit, :diffpatch, :execute and :normal.
> > ```
> >
> > But it doesn't mention user commands. It would avoid a lot of redundant
> commands, and add flexibility, if `:tab` supported user commands.
> >
> > Steps to reproduce:
> >
> > ```
> > :command! -nargs=1 Foo split <args>
> > :tab Foo bar
> > ```
> >
> > - Expected behavior: opens a new buffer named "bar" in a new tab
> > - Actual behavior: opens a new buffer named "bar" in a new split window
>
> OK, but this will cause trouble if the user command has several Ex
> commands, then we don't know where to apply the modifier. E.g. when
> temporarily opening a scratch bufffer.
>
> We could make the modifiers available in <> form, so that the user
> command can apply them where needed. Possibly just <mods>, to pass on
> all modifiers.


The attached patch adds support for the <mods> user command escape
sequence.

- Yegappan

-- 
-- 
You received this message from the "vim_dev" maillist.
Do not top-post! Type your reply below the text you are replying to.
For more information, visit http://www.vim.org/maillist.php

--- 
You received this message because you are subscribed to the Google Groups 
"vim_dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
For more options, visit https://groups.google.com/d/optout.
diff --git a/runtime/doc/map.txt b/runtime/doc/map.txt
index 3fd22f6..360f4da 100644
--- a/runtime/doc/map.txt
+++ b/runtime/doc/map.txt
@@ -1411,6 +1411,13 @@ The valid escape sequences are
        <bang>  (See the '-bang' attribute) Expands to a ! if the
                command was executed with a ! modifier, otherwise
                expands to nothing.
+                                               *<mods>*
+       <mods>  The command modifiers, if specified. Otherwise, expands to
+               nothing. Supported modifiers are 'aboveleft', 'belowright',
+               'botright', 'browse', 'confirm', 'hide', 'keepalt',
+               'keepjumps', 'keepmarks', 'keeppatterns', 'lockmarks',
+               'noswapfile', 'silent', 'tab', 'topleft', 'verbose', and
+               'vertical'.
                                                *<reg>* *<register>*
        <reg>   (See the '-register' attribute) The optional register,
                if specified.  Otherwise, expands to nothing.  <register>
diff --git a/src/ex_docmd.c b/src/ex_docmd.c
index e5de379..2a1b6b0 100644
--- a/src/ex_docmd.c
+++ b/src/ex_docmd.c
@@ -6412,6 +6412,26 @@ uc_split_args(char_u *arg, size_t *lenp)
     return buf;
 }
 
+    static size_t
+add_cmd_modifier(char_u *buf, char *mod_str, int *multi_mods)
+{
+    size_t result;
+
+    result = STRLEN(mod_str);
+    if (*multi_mods)
+       result += 1;
+    if (buf != NULL)
+    {
+       if (*multi_mods)
+           STRCAT(buf, " ");
+       STRCAT(buf, mod_str);
+    }
+
+    *multi_mods = 1;
+
+    return result;
+}
+
 /*
  * Check for a <> code in a user command.
  * "code" points to the '<'.  "len" the length of the <> (inclusive).
@@ -6435,8 +6455,8 @@ uc_check_code(
     char_u     *p = code + 1;
     size_t     l = len - 2;
     int                quote = 0;
-    enum { ct_ARGS, ct_BANG, ct_COUNT, ct_LINE1, ct_LINE2, ct_REGISTER,
-       ct_LT, ct_NONE } type = ct_NONE;
+    enum { ct_ARGS, ct_BANG, ct_COUNT, ct_LINE1, ct_LINE2, ct_MODS,
+       ct_REGISTER, ct_LT, ct_NONE } type = ct_NONE;
 
     if ((vim_strchr((char_u *)"qQfF", *p) != NULL) && p[1] == '-')
     {
@@ -6462,6 +6482,8 @@ uc_check_code(
        type = ct_LT;
     else if (STRNICMP(p, "reg>", l) == 0 || STRNICMP(p, "register>", l) == 0)
        type = ct_REGISTER;
+    else if (STRNICMP(p, "mods>", l) == 0)
+       type = ct_MODS;
 
     switch (type)
     {
@@ -6585,6 +6607,103 @@ uc_check_code(
        break;
     }
 
+    case ct_MODS:
+    {
+       int multi_mods = 0;
+
+       result = 0;
+       if (buf != NULL)
+           *buf = '\0';
+
+#ifdef FEAT_WINDOWS
+       /* :aboveleft and :leftabove */
+       if (cmdmod.split & WSP_ABOVE)
+           result += add_cmd_modifier(buf, "aboveleft", &multi_mods);
+
+       /* :belowright and :rightbelow */
+       if (cmdmod.split & WSP_BELOW)
+           result += add_cmd_modifier(buf, "belowright", &multi_mods);
+
+       /* :botright */
+       if (cmdmod.split & WSP_BOT)
+           result += add_cmd_modifier(buf, "botright", &multi_mods);
+#endif
+
+#ifdef FEAT_BROWSE_CMD
+       /* :browse */
+       if (cmdmod.browse)
+           result += add_cmd_modifier(buf, "browse", &multi_mods);
+#endif
+
+#if defined(FEAT_GUI_DIALOG) || defined(FEAT_CON_DIALOG)
+       /* :confirm */
+       if (cmdmod.confirm)
+           result += add_cmd_modifier(buf, "confirm", &multi_mods);
+#endif
+
+       /* :hide */
+       if (cmdmod.hide)
+           result += add_cmd_modifier(buf, "hide", &multi_mods);
+
+       /* :keepalt */
+       if (cmdmod.keepalt)
+           result += add_cmd_modifier(buf, "keepalt", &multi_mods);
+
+       /* :keepjumps */
+       if (cmdmod.keepjumps)
+           result += add_cmd_modifier(buf, "keepjumps", &multi_mods);
+
+       /* :keepmarks */
+       if (cmdmod.keepmarks)
+           result += add_cmd_modifier(buf, "keepmarks", &multi_mods);
+
+       /* :keeppatterns */
+       if (cmdmod.keeppatterns)
+           result += add_cmd_modifier(buf, "keeppatterns", &multi_mods);
+
+       /* :lockmarks */
+       if (cmdmod.lockmarks)
+           result += add_cmd_modifier(buf, "lockmarks", &multi_mods);
+
+       /* TODO: How to support :noautocmd? */
+
+       /* :noswapfile */
+       if (cmdmod.noswapfile)
+           result += add_cmd_modifier(buf, "noswapfile", &multi_mods);
+
+#ifdef HAVE_SANDBOX
+       /* TODO: How to support :sandbox?*/
+#endif
+
+       /* :silent */
+       if (msg_silent > 0)
+           result += add_cmd_modifier(buf,
+                   emsg_silent > 0 ? "silent!" : "silent", &multi_mods);
+
+#ifdef FEAT_WINDOWS
+       /* :tab */
+       if (cmdmod.tab > 0)
+           result += add_cmd_modifier(buf, "tab", &multi_mods);
+
+       /* :topleft */
+       if (cmdmod.split & WSP_TOP)
+           result += add_cmd_modifier(buf, "topleft", &multi_mods);
+#endif
+
+       /* TODO: How to support :unsilent?*/
+
+       /* :verbose */
+       if (p_verbose > 0)
+           result += add_cmd_modifier(buf, "verbose", &multi_mods);
+
+#ifdef FEAT_WINDOWS
+       /* :vertical */
+       if (cmdmod.split & WSP_VERT)
+           result += add_cmd_modifier(buf, "vertical", &multi_mods);
+#endif
+       break;
+    }
+
     case ct_REGISTER:
        result = eap->regname ? 1 : 0;
        if (quote)
diff --git a/src/testdir/Make_all.mak b/src/testdir/Make_all.mak
index 0e4ab7f..635f23c 100644
--- a/src/testdir/Make_all.mak
+++ b/src/testdir/Make_all.mak
@@ -179,6 +179,7 @@ NEW_TESTS = test_arglist.res \
            test_perl.res \
            test_quickfix.res \
            test_syntax.res \
+           test_usrcmds.res \
            test_viminfo.res \
            test_viml.res \
            test_visual.res \
diff --git a/src/testdir/test_usrcmds.vim b/src/testdir/test_usrcmds.vim
new file mode 100644
index 0000000..61eb920
--- /dev/null
+++ b/src/testdir/test_usrcmds.vim
@@ -0,0 +1,40 @@
+" Tests for user defined commands
+
+" Test for <mods> in user defined commands
+function Test_cmdmods()
+  let g:mods = ''
+
+  command! -nargs=* MyCmd let g:mods .= '<mods> '
+  MyCmd
+  aboveleft MyCmd
+  belowright MyCmd
+  botright MyCmd
+  browse MyCmd
+  confirm MyCmd
+  hide MyCmd
+  keepalt MyCmd
+  keepjumps MyCmd
+  keepmarks MyCmd
+  keeppatterns MyCmd
+  lockmarks MyCmd
+  noswapfile MyCmd
+  silent MyCmd
+  tab MyCmd
+  topleft MyCmd
+  verbose MyCmd
+  vertical MyCmd
+
+  aboveleft belowright botright browse confirm hide keepalt keepjumps
+             \ keepmarks keeppatterns lockmarks noswapfile silent tab
+             \ topleft verbose vertical MyCmd
+
+  call assert_equal(' aboveleft belowright botright browse confirm ' .
+      \ 'hide keepalt keepjumps keepmarks keeppatterns lockmarks ' .
+      \ 'noswapfile silent tab topleft verbose vertical aboveleft ' .
+      \ 'belowright botright browse confirm hide keepalt keepjumps ' .
+      \ 'keepmarks keeppatterns lockmarks noswapfile silent tab topleft ' .
+      \ 'verbose vertical ', g:mods)
+
+  delcommand MyCmd
+  unlet g:mods
+endfunction

Raspunde prin e-mail lui