Explorar el Código

Only use command modifiers if available

Command modifiers were added in Vim 7.4.1898.
micbou hace 6 años
padre
commit
959d0c4c5f

+ 11 - 8
README.md

@@ -2800,15 +2800,14 @@ let g:ycm_use_ultisnips_completer = 1
 ### The `g:ycm_goto_buffer_command` option
 ### The `g:ycm_goto_buffer_command` option
 
 
 Defines where `GoTo*` commands result should be opened. Can take one of the
 Defines where `GoTo*` commands result should be opened. Can take one of the
-following values:
-`[ 'same-buffer', 'split', 'split-or-existing-window' ]`
-If this option is set to the `'same-buffer'` but current buffer can not
-be switched (when buffer is modified and `nohidden` option is set),
-then result will be opened in a split. When the option is set to
+following values: `'same-buffer'`, `'split'`, or `'split-or-existing-window'`.
+If this option is set to the `'same-buffer'` but current buffer can not be
+switched (when buffer is modified and `nohidden` option is set), then result
+will be opened in a split. When the option is set to
 `'split-or-existing-window'`, if the result is already open in a window of the
 `'split-or-existing-window'`, if the result is already open in a window of the
-current tab page (or any tab pages with the `:tab` modifier; see below), it
-will jump to that window. Otherwise, the result will be opened in a split as if
-the option was set to `'split'`.
+current tab page (or any tab pages with the `:tab` modifier; see below), it will
+jump to that window. Otherwise, the result will be opened in a split as if the
+option was set to `'split'`.
 
 
 To customize the way a new window is split, prefix the `GoTo*` command with one
 To customize the way a new window is split, prefix the `GoTo*` command with one
 of the following modifiers: `:aboveleft`, `:belowright`, `:botright`,
 of the following modifiers: `:aboveleft`, `:belowright`, `:botright`,
@@ -2824,6 +2823,10 @@ To open in a new tab page, use the `:tab` modifier with the `'split'` or
 :tab YcmCompleter GoTo
 :tab YcmCompleter GoTo
 ```
 ```
 
 
+**NOTE:** command modifiers were added in Vim 7.4.1898. If you are using an
+older version, you can still configure this by setting the option to one of the
+deprecated values: `'vertical-split'`, `'new-tab'`, or `'new-or-existing-tab'`.
+
 Default: `'same-buffer'`
 Default: `'same-buffer'`
 
 
 ```viml
 ```viml

+ 15 - 6
autoload/youcompleteme.vim

@@ -844,12 +844,21 @@ function! s:SetUpCommands()
   command! YcmDebugInfo call s:DebugInfo()
   command! YcmDebugInfo call s:DebugInfo()
   command! -nargs=* -complete=custom,youcompleteme#LogsComplete
   command! -nargs=* -complete=custom,youcompleteme#LogsComplete
         \ YcmToggleLogs call s:ToggleLogs(<f-args>)
         \ YcmToggleLogs call s:ToggleLogs(<f-args>)
-  command! -nargs=* -complete=custom,youcompleteme#SubCommandsComplete -range
-        \ YcmCompleter call s:CompleterCommand(<q-mods>,
-        \                                      <count>,
-        \                                      <line1>,
-        \                                      <line2>,
-        \                                      <f-args>)
+  if s:Pyeval( 'vimsupport.VimVersionAtLeast( "7.4.1898" )' )
+    command! -nargs=* -complete=custom,youcompleteme#SubCommandsComplete -range
+          \ YcmCompleter call s:CompleterCommand(<q-mods>,
+          \                                      <count>,
+          \                                      <line1>,
+          \                                      <line2>,
+          \                                      <f-args>)
+  else
+    command! -nargs=* -complete=custom,youcompleteme#SubCommandsComplete -range
+          \ YcmCompleter call s:CompleterCommand('',
+          \                                      <count>,
+          \                                      <line1>,
+          \                                      <line2>,
+          \                                      <f-args>)
+  endif
   command! YcmDiags call s:ShowDiagnostics()
   command! YcmDiags call s:ShowDiagnostics()
   command! YcmShowDetailedDiagnostic call s:ShowDetailedDiagnostic()
   command! YcmShowDetailedDiagnostic call s:ShowDetailedDiagnostic()
   command! YcmForceCompileAndDiagnostics call s:ForceCompileAndDiagnostics()
   command! YcmForceCompileAndDiagnostics call s:ForceCompileAndDiagnostics()

+ 6 - 2
doc/youcompleteme.txt

@@ -3027,8 +3027,8 @@ Default: '1'
 The *g:ycm_goto_buffer_command* option
 The *g:ycm_goto_buffer_command* option
 
 
 Defines where 'GoTo*' commands result should be opened. Can take one of the
 Defines where 'GoTo*' commands result should be opened. Can take one of the
-following values: "[ 'same-buffer', 'split', 'split-or-existing-window' ]" If
-this option is set to the "'same-buffer'" but current buffer can not be
+following values: "'same-buffer'", "'split'", or "'split-or-existing-window'".
+If this option is set to the "'same-buffer'" but current buffer can not be
 switched (when buffer is modified and 'nohidden' option is set), then result
 switched (when buffer is modified and 'nohidden' option is set), then result
 will be opened in a split. When the option is set to "'split-or-existing-
 will be opened in a split. When the option is set to "'split-or-existing-
 window'", if the result is already open in a window of the current tab page (or
 window'", if the result is already open in a window of the current tab page (or
@@ -3048,6 +3048,10 @@ To open in a new tab page, use the ':tab' modifier with the "'split'" or
 >
 >
   :tab YcmCompleter GoTo
   :tab YcmCompleter GoTo
 <
 <
+**NOTE:** command modifiers were added in Vim 7.4.1898. If you are using an
+older version, you can still configure this by setting the option to one of the
+deprecated values: "'vertical-split'", "'new-tab'", or "'new-or-existing-tab'".
+
 Default: "'same-buffer'"
 Default: "'same-buffer'"
 >
 >
   let g:ycm_goto_buffer_command = 'same-buffer'
   let g:ycm_goto_buffer_command = 'same-buffer'

+ 33 - 1
python/ycm/tests/test_utils.py

@@ -22,7 +22,7 @@ from __future__ import absolute_import
 # Not installing aliases from python-future; it's unreliable and slow.
 # Not installing aliases from python-future; it's unreliable and slow.
 from builtins import *  # noqa
 from builtins import *  # noqa
 
 
-from collections import defaultdict
+from collections import defaultdict, namedtuple
 from future.utils import iteritems, PY2
 from future.utils import iteritems, PY2
 from mock import DEFAULT, MagicMock, patch
 from mock import DEFAULT, MagicMock, patch
 from hamcrest import assert_that, equal_to
 from hamcrest import assert_that, equal_to
@@ -60,6 +60,7 @@ REDIR_START_REGEX = re.compile( '^redir => (?P<variable>[\w:]+)$' )
 REDIR_END_REGEX = re.compile( '^redir END$' )
 REDIR_END_REGEX = re.compile( '^redir END$' )
 EXISTS_REGEX = re.compile( '^exists\( \'(?P<option>[\w:]+)\' \)$' )
 EXISTS_REGEX = re.compile( '^exists\( \'(?P<option>[\w:]+)\' \)$' )
 LET_REGEX = re.compile( '^let (?P<option>[\w:]+) = (?P<value>.*)$' )
 LET_REGEX = re.compile( '^let (?P<option>[\w:]+) = (?P<value>.*)$' )
+HAS_PATCH_REGEX = re.compile( '^has\( \'patch(?P<patch>\d+)\' \)$' )
 
 
 # One-and only instance of mocked Vim object. The first 'import vim' that is
 # One-and only instance of mocked Vim object. The first 'import vim' that is
 # executed binds the vim module to the instance of MagicMock that is created,
 # executed binds the vim module to the instance of MagicMock that is created,
@@ -83,6 +84,15 @@ VIM_OPTIONS = {
   '&expandtab': 1
   '&expandtab': 1
 }
 }
 
 
+# This variable must be patched with a Version object for tests depending on the
+# Vim version. Example:
+#
+#   @patch( 'ycm.tests.test_utils.VIM_VERSION', Version( 7, 4, 1578 ) )
+#   def ThisTestDependsOnTheVimVersion_test():
+#     ...
+#
+VIM_VERSION = None
+
 REDIR = {
 REDIR = {
   'status': False,
   'status': False,
   'variable': '',
   'variable': '',
@@ -90,6 +100,9 @@ REDIR = {
 }
 }
 
 
 
 
+Version = namedtuple( 'Version', [ 'major', 'minor', 'patch' ] )
+
+
 @contextlib.contextmanager
 @contextlib.contextmanager
 def CurrentWorkingDirectory( path ):
 def CurrentWorkingDirectory( path ):
   old_cwd = GetCurrentDirectory()
   old_cwd = GetCurrentDirectory()
@@ -225,6 +238,21 @@ def _MockVimMatchEval( value ):
   return None
   return None
 
 
 
 
+def _MockVimVersionEval( value ):
+  match = HAS_PATCH_REGEX.search( value )
+  if match:
+    if not isinstance( VIM_VERSION, Version ):
+      raise RuntimeError( 'Vim version is not set.' )
+    return VIM_VERSION.patch >= int( match.group( 'patch' ) )
+
+  if value == 'v:version':
+    if not isinstance( VIM_VERSION, Version ):
+      raise RuntimeError( 'Vim version is not set.' )
+    return VIM_VERSION.major * 100 + VIM_VERSION.minor
+
+  return None
+
+
 def _MockVimEval( value ):
 def _MockVimEval( value ):
   result = _MockVimOptionsEval( value )
   result = _MockVimOptionsEval( value )
   if result is not None:
   if result is not None:
@@ -242,6 +270,10 @@ def _MockVimEval( value ):
   if result is not None:
   if result is not None:
     return result
     return result
 
 
+  result = _MockVimVersionEval( value )
+  if result is not None:
+    return result
+
   match = FNAMEESCAPE_REGEX.search( value )
   match = FNAMEESCAPE_REGEX.search( value )
   if match:
   if match:
     return match.group( 'filepath' )
     return match.group( 'filepath' )

+ 11 - 2
python/ycm/tests/vimsupport_test.py

@@ -26,8 +26,8 @@ from builtins import *  # noqa
 
 
 from ycm.tests import PathToTestFile
 from ycm.tests import PathToTestFile
 from ycm.tests.test_utils import ( CurrentWorkingDirectory, ExtendedMock,
 from ycm.tests.test_utils import ( CurrentWorkingDirectory, ExtendedMock,
-                                   MockVimBuffers, MockVimModule, VimBuffer,
-                                   VimError )
+                                   MockVimBuffers, MockVimModule, Version,
+                                   VimBuffer, VimError )
 MockVimModule()
 MockVimModule()
 
 
 from ycm import vimsupport
 from ycm import vimsupport
@@ -1879,3 +1879,12 @@ def JumpToLocation_DifferentFile_NewOrExistingTab_AlreadyOpened_test(
         call( 'normal! m\'' ),
         call( 'normal! m\'' ),
         call( 'normal! zz' )
         call( 'normal! zz' )
       ] )
       ] )
+
+
+@patch( 'ycm.tests.test_utils.VIM_VERSION', Version( 7, 4, 1578 ) )
+def VimVersionAtLeast_test():
+  assert_that( vimsupport.VimVersionAtLeast( '7.3.414' ) )
+  assert_that( vimsupport.VimVersionAtLeast( '7.4.1578' ) )
+  assert_that( not vimsupport.VimVersionAtLeast( '7.4.1579' ) )
+  assert_that( not vimsupport.VimVersionAtLeast( '7.4.1898' ) )
+  assert_that( not vimsupport.VimVersionAtLeast( '8.1.278' ) )

+ 13 - 0
python/ycm/vimsupport.py

@@ -1228,3 +1228,16 @@ def SwitchWindow( window ):
   the CurrentWindow context if you are going to switch back to the original
   the CurrentWindow context if you are going to switch back to the original
   window."""
   window."""
   vim.current.window = window
   vim.current.window = window
+
+
+# Expects version_string in 'MAJOR.MINOR.PATCH' format, e.g. '8.1.278'
+def VimVersionAtLeast( version_string ):
+  major, minor, patch = ( int( x ) for x in version_string.split( '.' ) )
+
+  # For Vim 8.1.278, v:version is '801'
+  actual_major_and_minor = GetIntValue( 'v:version' )
+  matching_major_and_minor = major * 100 + minor
+  if actual_major_and_minor != matching_major_and_minor:
+    return actual_major_and_minor > matching_major_and_minor
+
+  return GetBoolValue( "has( 'patch{0}' )".format( patch ) )