2013-01-10 3 views
3

필자는 (Perforce) 버전 관리 시스템 용 .vimrc에 몇 가지 매크로를 작성했습니다 (vim 용 perforce 플러그인을 제안하지 마십시오. 나는 그것을 좋아하지 않는다). 그것들은 확인 프롬프트로 인해 깨지는 되돌리기 매크로를 제외하고는 모두 잘 작동합니다. (필자는 필자가 필자의 변경 사항을 실수로 털어 놓지 않아도됩니다.) 그것은 현재 다음과 같습니다vim : 키 확인을위한 맵 명령

map <F8> :if confirm('Revert to original?', "&Yes\n&No", 1)==1 | !p4 revert <C-R>=expand("%:p")<CR><CR><CR>:edit<CR> | endif 

이 정력이 파일을로드 할 때 불평을 bash에 발생합니다 배쉬가 보는 버퍼를 보면

bin/bash: -c: line 0: syntax error near unexpected token `(' 

을 보이는 오류가 정력을 보내는처럼 첫 번째 파이프 이후의 모든 것, bash를위한 부분이 아닙니다. 몇 가지 대안을 시도했지만 제대로 작동하지 않는 것 같습니다. 파이프 및 endif (약식을 사용하여)를 제거했을 때 확인 대화 상자를 올바르게 표시 할 수있게되었지만 사용자가 응답을 보낸 후에 vim이 불평합니다.

답변

3

여러 개의 vim 명령을 함께 묶는 데 파이프를 사용하는 것은 특별히 잘 정의되어 있지 않으며 수많은 편심이 있습니다. 비판적으로 (:help :bar 참조) 셸 명령 :!과 같은 명령 뒤에는 | 문자를 인수로 사용할 수 없습니다.

system() 기능을 더 쉽게 사용할 수 있습니다.

E.G. 당신은 파일 이름에 공백이나 따옴표와 같은 문자를 (또는 영리이 ; rm -rf ~ (집에서 시도하지 마십시오라는 이름의 한!)) 경우

:echo system("p4 revert " . shellescape(expand("%:p"))) 

shellescape() 래퍼 유용합니다. 더 읽기/유지 보수 코드를 만들기 위해 다음의

, 당신은 함수에 코드를 이동할 수 있습니다 : 당신이 매크로에 :call 또는 :echo 명령을 사용하여 액세스 할

function Revert() 
    if confirm('Revert to original?', "&Yes\n&No", 1)==1 
     return system("p4 revert " . shellescape(expand("%:p"))) 
    endif 
endfunction 

.

:map <F8> :if confirm('Revert to original?', "&Yes\n&No", 1)==1 <Bar> exe "!p4 revert" . expand("%:p") <Bar> edit <Bar> endif<CR><CR> 

:map 키 입력의 바보 같은 순서입니다 기억 :

+0

해결책에 작은 버그가 있습니다.이 명령에는 "p4"가 아니라 "p4 revert"가 필요하지만 전반적인 형식이 작동합니다. 감사합니다 –

4

나는 당신이이 라인을 따라 뭔가를 할 생각이 F8을 매핑하고 무엇이 입력 한 경우 일 것입니다 키 입력의 순서이어야 할 수 있습니다. <CR>:if 문장의 중간에있는 것은 '조건이 참이면이 시점에서 명령을 실행할 때'및 'Enter'을 의미하지 않습니다. '; :if 명령을 입력하는 중 'Enter 여기를 누르십시오'라는 의미입니다. 이는 분명히 원하는 것이 아닙니다.

하면 내부에서, 한 번에 한 조각을 밖으로까지 건물 :

  1. 는 때때로 실행할 쉘 명령이있다.
  2. 쉘 명령은 '가끔'비트를 수행하기 위해 :if 내부에 있어야하므로 그 뒤에 :endif이 있어야합니다.
  3. ! 다음에 오는 모든 것이 쉘에 전달되며, 보통은 다른 Vim 명령의 시작을 나타내는 | 문자를 포함합니다.|은 쉘 명령에서 사용하기에 아주 좋은 문자이기 때문에 합리적입니다. 그래서 우리는 쉘 명령을 포함하는 어떤 방법이 필요합니다. :exe이 작업을 수행 할 수 있습니다. 그것은 제공된 문자열을 명령으로 실행합니다. 그리고 그 인자는 문자열이고 정의 된 끝을가집니다. 따라서 일반적인 형식은 :if condition | exe "!shell command" | endif입니다.
  4. 쉘 명령에 표현식이 있습니다. :exe을 사용하면 명령의 문자열 상수 부분을 표현식의 결과와 간단하게 연결할 수 있기 때문에이 작업을 쉽게 수행 할 수 있습니다. 따라서 명령은 :exe "!p4 revert" . expand("%:p")이됩니다. 파일에서 자체적으로 시도하고 더 이상 진행하기 전에 원하는 것을 확인하십시오.
  5. 해당 조건을 넣으면 :if confirm('Revert to original?', "&Yes\n&No", 1)==1 | exe "!p4 revert" . expand("%:p") | edit | endif이됩니다. 매핑을 정의하기 전에 다시 시도하십시오.
  6. 작업을 마쳤 으면 매핑을 정의하십시오. 리터럴 |은 매핑을 끝내고 다음 Vim 명령의 시작을 나타냅니다. 원본에서 매핑 정의는 조건을 끝내고 (파일을로드 한 후 :map <F8>으로 확인) 매핑을 정의하는 Vim 파일에서 !p4 부분을 즉시 실행했습니다! 명령에서 Enter을 누를 때마다 <CR>으로 쓰는 방법과 마찬가지로 명령에서 |을 각각 <Bar>으로 변경해야합니다. 그것은 위의 매핑을 제공합니다. 명령 줄에 먼저 입력하여 시도한 다음 :map <F8>을 다시 실행하여 생각하는대로 확인하십시오. 그런 다음 F8을 눌러보십시오.
  7. 해당되는 경우 매핑을 .vimrc에 입력합니다.
+0

감사합니다, 불행히도 나는 오직 하나의 대답을 받아 들일 수 있지만, 나는뿐만 아니라 당신 upvoted있다. –