在任意宽度的窗口中在 Vim 中软包装80个字符

我想使用 Vim 的 软包装功能(:set wrap)来包装一些80个字符的代码,而不管我的实际窗口宽度。

我还没有找到一种方法来做到这一点-所有的软包装似乎绑在窗口的宽度

  • textwidthwrapmargin都用于硬包装(它们向文件中插入换行符)
  • 垂直分割成多个窗口,并使用 :vertical resize 80(可能与 :set breakat=允许任何字符中断)对其中的一个排序工作(即使它有点骇客) ,但中断时,使用 :set number作为行号占据一个可变数量的列(取决于文件长度) ,这些是80的一部分。

有什么方法可以做到这一点在 Vim? 根据其他消息来源,情况看起来并不乐观

现在我的近似值是使用 /^.\{80}\zs.\+作为默认搜索,所以它至少被高亮显示。我曾经想过为它添加一个 :syntax项,但是当它与其他语法项重叠时,这个想法就破灭了,所以我放弃了这个想法。

43366 次浏览

你可以的

  • 通过 :set numberwidth=6
  • 然后你可以用 :set columns=86(或鼠标)调整你的窗口大小到适当的大小。

如果您编辑一个包含100万行的文件,您可能会遇到麻烦,但这是不太可能的。你这样也浪费了6栏屏幕空间。所以还是有各种各样的问题。

您可以使用 :match突出显示第80列,就像它说的 给你给你一样。

除此之外,我看不出有什么办法可以做到这一点。不过,这似乎是一个不错的功能。

你试过 'linebreak'吗?

        *'linebreak'* *'lbr'* *'nolinebreak'* *'nolbr'*
'linebreak' 'lbr' boolean (default off)
local to window
{not in Vi}
{not available when compiled without the  |+linebreak|
feature}
If on Vim will wrap long lines at a character in 'breakat' rather
than at the last character that fits on the screen.  Unlike
'wrapmargin' and 'textwidth', this does not insert <EOL>s in the file,
it only affects the way the file is displayed, not its contents.  The
value of 'showbreak' is used to put in front of wrapped lines.
This option is not used when the 'wrap' option is off or 'list' is on.
Note that <Tab> characters after an <EOL> are mostly not displayed
with the right amount of white space.

我没有软包装的解决方案,但是对于标记列,从 Vim 7.3(发布于2010-08-15)开始,:set colorcolumn=80将突出显示第80列。颜色将取决于您的语法文件。

参见 Vim 80列布局问题:h colorcolumn

试试这个:

set columns=80
autocmd VimResized * if (&columns > 80) | set columns=80 | endif
set wrap
set linebreak
set showbreak=+++

如果 一直都是需要80列,则可以删除 if (&columns > 80) |

没有什么好办法。如果我们修改@eborisch 的答案,我们可以用 autocmd破解一个临时的 setlocal softwrap。如果每次进入缓冲区时都调整大小,并且在设置局部变量 softwrap时将大小调整到特定的长度,那么就得到了所需的行为。

假设我们想软包装到80列,我们可以在 .vimrc中编写以下内容。

augroup softwrap
autocmd VimResized * if (exists('b:softwrap') && &columns > 80) | set columns=80 | endif
autocmd BufEnter * set columns=999
augroup END

要打开特定缓冲区的模式,请使用以下命令:

let b:softwrap=1
set columns=80

Eborisch 的回答和我在这里找到的其他一些答案以及我必须解决的问题结合起来,我得出了以下两部分的解决方案:

第一部分使得编辑长行文本变得更加容易:

" Allow enabling by running the command ":Freeform", or <leader>sw
command! Softwrap :call SetupSoftwrap()
map <Leader>sw :call SetupSoftwrap() <CR>


func! SetupFreeform()
" Use setlocal for all of these so they don't affect other buffers


" Enable line wrapping.
setlocal wrap
" Only break at words.
setlocal linebreak
" Turn on spellchecking
setlocal spell


" Make jk and 0$ work on visual lines.
nnoremap <buffer> j gj
nnoremap <buffer> k gk
nnoremap <buffer> 0 g0
nnoremap <buffer> $ g$


" Disable colorcolumn, in case you use it as a column-width indicator
" I use: let &colorcolumn = join(range(101, 300), ",")
" so this overrides that.
setlocal colorcolumn=


" cursorline and cursorcolumn don't work as well in wrap mode, so
" you may want to disable them. cursorline highlights the whole line,
" so if you write a whole paragraph on a single line, the whole
" paragraph will be highlighted. cursorcolumn only highlights the actual
" column number, not the visual line, so the highlighting will be broken
" up on wrapped lines.
setlocal nocursorline
setlocal nocursorcolumn
endfunc

仅凭这一点,你就可以得到像标记或自述这样的文本包装。

正如在其他答案中提到的,要达到精确的列宽度,需要准确地告诉 vim 有多少列,并在每次调整 vim 的大小时覆盖它:

command! -nargs=? Draft :call SetupDraftMode(<args>)
func! SetupDraftMode()
" I like 80 columns + 4 for line numbers
set columns=84
autocmd VimResized * if (&columns > 84) | set columns=84 | endif


:Softwrap
endfunc

这方面仍存在一些问题:

  • 在调用 set column 之后,vim 不会清除您指定的列之外的屏幕,而且我不知道如何告诉它,所以理想情况下,您应该在打开 vim 之后立即调用这个函数
  • 当您打开 vim 时,它会显示一个带有版本号的提示和一些有用的命令,因此这些命令不会被清除。您可以添加 set shm+=I来禁用该提示符
  • 您不能打开任何垂直分割,因为这样两个分割都将是 ~ 40列。您需要将列设置为所需宽度的2倍,然后始终有一个分割打开。
  • 我的 vimscript 非常糟糕,但是理想情况下,有人可以修改上面的 Draft函数,以列宽作为参数,或者使用全局变量(g:explicit_vim_width?)如果窗口大小改变,可以手动设置。