Làm cách nào tôi có thể sử dụng hoàn thành chế độ chèn trong macro?


11

Tôi đang cố gắng xác định một macro sẽ nhanh chóng tạo ra một danh sách các từ ngẫu nhiên.
Tôi muốn macro biến nó thành một danh sách như

a
b
c
d
e

vào đây

arezzo
bywords
czars
détente
eyrie

Những gì tôi có cho đến nay:

  • đặt con trỏ trên chữ a
  • bắt đầu ghi macro qq
  • a vào chế độ chèn
  • <C-x><C-k> - perform dictionary completion on the character before cursor - in this case the lettera`
  • <C-p>chọn mục cuối cùng trong danh sách hoàn thành xuất hiện, trên hệ thống của tôi đó là từ arezzo. (NB Tôi đã longestbao gồm trong 'completeopt'cài đặt của mình , được yêu cầu <C-p>để hoạt động theo cách này trong khi hoàn thành 'set completeopt=longest,menuone,preview':).
  • <C-y> chấp nhận hoàn thành
  • ^[^[ thoát chế độ chèn
  • j chuyển xuống dòng tiếp theo, sẵn sàng thực hiện thao tác tương tự trên dòng tiếp theo
  • q dừng ghi âm

Khi tôi tạo macro và thực hiện các bước theo cách thủ công, mọi thứ đều hoạt động tốt, tuy nhiên khi tôi thực thi macro, tôi thấy một thông báo nhấp nháy trong dòng lệnh như:

quét tập tin từ điển

và không có gì xảy ra, trong số các lệnh trong macro chỉ jđược chạy, tức là con trỏ di chuyển xuống dòng, nhưng không có lệnh nào hoàn thành chạy.
Có thể sử dụng hoàn thành chế độ chèn trong một macro không, và nếu vậy, làm thế nào tôi có thể làm điều đó?


Tôi không hiểu <C-p>bước của bạn ... khi tôi làm điều đó trong vim của mình, nó chỉ đưa ra thông báo back at original- không chọn mục cuối cùng .. Tôi đã sử dụng phím mũi tên lên hai lần để chọn từ cuối cùng (trường hợp của tôi azures), nhấn enter và sau đó Esc+j+q.. nó hoạt động khá tốt khi thực thi macro
Sundeep

1
@spasic điểm ah tốt, tôi có nên nói, nhưng tôi đang sử dụng set completeopt=longest,menuone,previewcác của nó longestlựa chọn gây <C-p>chèn ngay lập tức. Nếu tôi xóa longestkhỏi completeoptchuỗi, tôi sẽ có hành vi tương tự như bạn. Ngoài ra, có các phím mũi tên làm việc! cảm ơn (tôi quên bạn có thể sử dụng chúng để điều hướng danh sách hoàn thành)
the_velour_fog

Có thể menu bật lên đang can thiệp. Có lẽ cố gắng :set completeopt=a<c-x><c-k><esc>jnhư vĩ mô của bạn.
Antony

@Antony Tôi không chắc tại sao <Cp> không hoạt động, nhưng các phím mũi tên chỉ hướng hoạt động.
the_velour_fog

Câu trả lời:


2

EDIT : Thực sự bạn là sau khi hoàn thành từ điển; bạn không nhất thiết cần chế độ chèn (chế độ Ctrl + X) để thực hiện việc này. Như bạn đã khám phá, nó làm cho việc làm việc với các macro trở thành một nỗi đau thực sự. Kịch bản dưới đây có thể được sử dụng để thực hiện hoàn thành từ điển mà không cần chế độ chèn, do đó bạn có thể dễ dàng lặp lại nó bên trong macro.

Thêm mã dưới đây vào .vimrctệp của bạn , đóng và mở lại bất kỳ cửa sổ vim nào để cung cấp chức năng mới, sau đó ghi lại chính mình nhấn <C-k>để thực hiện hoàn thành và jchuyển xuống dòng tiếp theo. Tôi đã thêm một kiểm tra cho longesttùy chọn và nếu nó bị vô hiệu hóa, nó chọn một mục ngẫu nhiên sử dụng thời gian ngẫu nhiên của hệ thống. Nếu nó tìm thấy longesttùy chọn, nó sẽ tìm kiếm thủ công mục nhập phù hợp dài nhất từ ​​điển và chèn vào đó.

Nếu bạn không thích <C-k>lập bản đồ, vui lòng thay đổi nó khi bạn thấy phù hợp. Nó sẽ làm việc với bất kỳ ánh xạ nào bạn muốn.

Ngoài ra, lệnh trả về biểu thức cho ánh xạ để đánh giá thêm \<esc>ký tự vào cuối để chúng tôi tự động rời khỏi chế độ chèn sau mỗi lần chèn và 0cwở phía trước để vào chế độ chèn để bắt đầu và đảm bảo chúng tôi ghi đè lên toàn bộ từ chính xác Tùy thuộc vào hành vi chính xác mà bạn muốn (nếu từ của bạn không đẹp ở đầu mỗi dòng), bạn có thể sử dụng bcwthay thế để tìm từ bắt đầu thực tế. Tuy nhiên, sau đó bạn sẽ thấy một số điều kỳ lạ khi quay trở lại các từ bắt đầu dòng. Có lẽ có một lệnh nâng cao hơn để bỏ qua dòng kết thúc và thực hiện cả hai cùng một lúc, nhưng tôi không thể tìm thấy một lệnh.

map <expr> <C-k> CompleteDictionary()
fun! CompleteDictionary()
    let cword = expand(“<cword>”)
    let res = []
    for m in readfile(&dictionary)
        if m =~ '^' . cword
            call add(res, m)
        endif
    endfor
    if &completeopt =~ 'longest'
        let max = 0
        let maxindex = 0
        let index = 0
        for item in res
            if strlen(item) > max
                let max = strlen(item)
                let maxindex = index
            endif
            let index = index + 1
        endfor
        return "0cw" . res[maxindex] . "\<esc>"
    else
        return "0cw" . res[system('@echo %RANDOM%') % len(res)] . "\<esc>"
    endif
endfun

Ngoài ra, sẽ không khó để mở rộng logic ở đây để tạo ánh xạ thay thế (ví dụ: sử dụng tham số hàm) thực hiện bất kỳ chức năng nào mà chế độ chèn cung cấp. Tôi sẽ sẵn lòng hỗ trợ với bất kỳ yêu cầu nào như vậy và cập nhật tập lệnh này khi tôi có thời gian.


Điều này nghe có vẻ như là một lời giải thích hợp lý về vấn đề này, nhưng tôi đã thử cả hai giải pháp được đề xuất của bạn và dường như không có ích gì.
Giàu

Bạn đã thử sleeplệnh như là tốt?
Tim

Có, mặc dù chỉ với giá trị đề xuất của bạn là 5 giây. Bạn đã quản lý để có được một trong hai giải pháp để làm việc? Bạn có thể đăng một danh sách đầy đủ các bước?
Giàu

Tôi không phải là người viết câu hỏi. Tuy nhiên, tôi có thể tái tạo vấn đề: bạn phải thêm dài nhất vào completeoptnhư được mô tả trong các nhận xét (một lần nữa, không phải bởi tôi). chỉnh sửa : Rất tiếc, 'longest'được yêu cầu cho ctrl-pbước: không ctrl-y. Tuy nhiên các bước được mô tả bởi công việc câu hỏi-hỏi cho tôi trong vim -Nu NONEvới completeoptchỉnh sửa.
Giàu

Tôi nghĩ rằng tôi đã tìm thấy một giải pháp, hãy cho tôi vài phút để cập nhật câu trả lời của tôi với nó.
Tim
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.