Chẳng hạn, :echo strftime(%c)
sẽ hiển thị thời gian hiện tại ở phía dưới, nhưng làm thế nào để chèn chuỗi thời gian này vào văn bản (ngay sau con trỏ)?
Chẳng hạn, :echo strftime(%c)
sẽ hiển thị thời gian hiện tại ở phía dưới, nhưng làm thế nào để chèn chuỗi thời gian này vào văn bản (ngay sau con trỏ)?
Câu trả lời:
Bạn có thể sử dụng thanh ghi biểu thức "=
, với p
(hoặc P
) ở chế độ bình thường hoặc <C-R>
ở chế độ chèn:
Ở chế độ bình thường:
( <C-M>
ở đây có nghĩa là Control+ M, hoặc chỉ nhấn Enter/ Return)
"=strftime('%c')<C-M>p
Trong chế độ chèn:
( <C-M>
có cùng ý nghĩa như trên, <C-R>
có nghĩa là Control+ R)
<C-R>=strftime('%c')<C-M>
Nếu bạn muốn chèn kết quả của cùng một biểu thức nhiều lần, thì bạn có thể muốn ánh xạ chúng vào các phím trong .vimrc
:
(ở đây <C-M>
và <C-R>
nên được nhập theo nghĩa đen (một chuỗi gồm năm ký tự có thể in được Vim sẽ dịch chúng bên trong))
:nmap <F2> "=strftime('%c')<C-M>p
:imap <F2> <C-R>=strftime('%c')<C-M>
"=
đăng ký. : - /
<C-R>=&sessionoptions
- nó thậm chí còn hoàn thành tab wildmode!
<c-r>=
lệnh chậm cho lệnh có thể có nhiều đầu ra và cũng có thể ngắt thụt lề để văn bản đầu ra không thể đọc được. Ví dụ, <c-r>=execute('nmap')
đầu ra sẽ được viết từng dòng, rất chậm.
:r!date +\%c
xem :help :r!
date
là một lệnh bên ngoài và !
gọi các lệnh bên ngoài trong khi OP yêu cầu các lệnh vim.
!
là lệnh vi (m) gọi các lệnh bên ngoài . Bạn có thể đúng OP không muốn chỉ xuất các lệnh vim nhưng nếu (các) anh ta làm, !
sẽ không làm.
Các lệnh này sẽ chèn đầu ra strftime("%c")
bên phải nơi con trỏ của bạn:
:exe ":normal i" . strftime("%c")
và
:call feedkeys("i". strftime("%c"))
Có nhiều cách khác để làm những gì bạn muốn (ví dụ như những câu trả lời của Mikel ).
Chỉnh sửa : Thậm chí tốt hơn, để chèn tại chỗ, hãy sử dụng thanh =
ghi như Chris Johnsen mô tả
Nếu bạn muốn chèn đầu ra của lệnh vim (trái ngược với giá trị trả về của một lệnh gọi hàm ), bạn phải nắm bắt nó. Điều này được thực hiện thông qua :redir
lệnh, cho phép bạn chuyển hướng tương đương với đầu ra tiêu chuẩn của vim thành một biến, tệp, đăng ký hoặc mục tiêu khác.
:redir
là loại bất tiện đau đớn để sử dụng; Tôi sẽ viết một hàm để đóng gói chức năng của nó theo cách thuận tiện hơn, đại loại như
funct! Exec(command)
redir =>output
silent exec a:command
redir END
return output
endfunct!
Khi bạn đã khai báo một hàm như vậy, bạn có thể sử dụng thanh ghi biểu thức (như được giải thích bởi Chris Johnsen) để chèn đầu ra của lệnh tại vị trí con trỏ. Vì vậy, từ chế độ bình thường, nhấn i^R=Exec('ls')
để chèn danh sách bộ đệm hiện tại của vim.
Xin lưu ý rằng lệnh sẽ thực thi trong không gian tên hàm, vì vậy nếu bạn sử dụng biến toàn cục, bạn sẽ phải xác định không gian tên một cách rõ ràng bằng cách thêm tiền tố vào g:
. Cũng lưu ý rằng Exec()
, như được viết ở trên, sẽ nối một dòng mới kết thúc vào đầu ra một dòng. Bạn có thể muốn thêm một cuộc gọi substitute()
vào chức năng để tránh điều này.
Đồng thời xem https://stackoverflow.com/questions/2573021/vim-how-to-redirect-ex-command-output-into-civerse-buffer-or-file/2573054#2573054 để biết thêm thông tin về redir
và liên kết đến một lệnh liên quan.
set paste
lệnh trước khi trả lại đầu ra và set nopaste
sau đó, để tránh thụt lề cầu thang khi các dòng bắt đầu bằng khoảng trống. Trên thực tế, tôi muốn lưu giá trị của tùy chọn dán hiện tại và trả lại nhưng tôi không thể làm như vậy.
set nopaste
nên làm việc sau return output
, bởi vì câu lệnh return là một điểm thoát khỏi hàm. Tôi đã đặt giải pháp của mình cho vấn đề này như một câu trả lời riêng trên trang này.
:call append(line('.'), strftime("%c"))
Sẽ đặt nó trên dòng tiếp theo, sau đó bạn có thể nhấn J
( Shift+ J) để nối nó với vị trí hiện tại.
Hoặc nếu bạn cần tất cả trong một lệnh, bạn có thể làm
:call setline(line('.'), getline(line('.')) . strftime("%c"))
hoặc là
:call setline(line('.'), getline(line('.')) . " " . strftime("%c"))
tùy thuộc vào việc bạn có muốn một không gian được chèn trước ngày hay không.
Cải thiện câu trả lời @intuited để tránh sự cố với khoảng trắng hàng đầu và thụt lề ngày càng tăng:
"Examples:
":call Exec('buffers')
"This will include the output of :buffers into the current buffer.
"
"Also try:
":call Exec('ls')
":call Exec('autocmd')
"
funct! Exec(command)
redir =>output
silent exec a:command
redir END
let @o = output
execute "put o"
return ''
endfunct!
Điều này chỉ đơn giản sẽ chèn tại vị trí hiện tại trong tệp khi bạn :call Exec('command')
từ chế độ bình thường. Như đã lưu ý trong nhận xét , =Exec('command')
cách tiếp cận Ctrl + R ban đầu (chế độ chèn) với Exec(..)
trả về một chuỗi có thể được sửa một phần bằng cách sử dụng set paste
, nhưng không cung cấp cơ hội để đặt set nopaste
bất cứ nơi nào.
Các let @o = output
cú pháp đặt đăng ký o
các nội dung của biến output
, như đã giải thích ở đây: https://stackoverflow.com/a/22738310/1143274
Các return ''
dòng là để các giá trị trả về mặc định của 0
tôi không nhận được chèn vào bộ đệm.
Đây là cách tôi làm điều đó. Nó đặt nó ngay sau con trỏ bởi vì nó sử dụng p
.
" save previous yank
let reg_save = @@
" save your text to the '@' register
let @@ = strftime('%c')
" paste it after the cursor
exec "normal! p"
" restore previous yank
let @@ = reg_save