2013-04-05 10 views
8

私はコマンドを書きたい、このコマンドはこの形式を持っているでしょう:引数を渡すには:command to function?

[range]MyCMD[!] [count] [oneArg] [flags] 

または

[range]MyCMD[!] [oneArg] [count] [flags] 

:[range]P[rint] [count] [flags] 

または

:[range]d[elete] [x] {count} 

へコマンドMyCMDは最終的には何らかの作業を行うための関数を呼び出します。私はここでは、この行(を動作しません)

command! -nargs=+ -range -bang -count=0 MyCMD <line1>,<line2>call MyFUNC(<q-args>, "<bang>","<count>", .... ..) 

を書いた問題は、これらの引数を処理する方法を、次のとおりです。私は助け、-range-countについて読ん

  • 問題1を同時に使用することはできませんが、私はそれらの両方が必要です。私はまた、いくつかのvimコマンドを見ました:delete、:print、これらのコマンドを使うと、rangecountの両方を与えることができます。また、{count}または[count]が利用可能な場合、vim docには同じコマンドの2つのエントリがあることがわかりました。以下のような:

    :[range]d[elete] [x]  
    :[range]d[elete] [x] {count} 
    

または

:[range]p[rint] [flags] 
:[range]p[rint] {count} [flags] 

はなぜですか?なぜ[count]とだけではないのですか? (これは別の小さな疑問だろう)

  • 問題2私のデザインから、これらすべての引数はオプションであり、彼らは、デフォルト値を持っている(下表参照します)。これらの引数を関数に渡すにはどうすればいいですか(私は<q-args> and <f-args>をチェックしました)、どのユーザー入力がどの引数であるかを区別するにはどうすればよいですか?

    argName | Default value | description 
        ------------------------------------- 
        range | current line | this could be get by function xxx () range 
        count | 0    | this could be get by <count> 
        bang | ""   | this is easy too, with <bang> 
        arg  | " "   | this argument could have space 
        flags | ""   | no space allowed for flags 
        ------------------------------------- 
    

    感謝:たとえばユーザーが

    :MyCMD 5 g

    5 is count? or arg? 
    g is arg or flag? 
    or '5 g' is arg? 
    

を与え、ここで引数のデフォルト値です。

答えて

9

複雑なカスタムコマンドの場合、Vimの限られた解析オプションだけに依存することはできません。範囲を-rangeで処理させることができますが、引数の組み合わせを自分で解析する必要があります。 (おそらく一度だけ呼び出されるように:function MyFUNC(...) rangeで定義する必要があります)MyFUNCインサイド

:command! -nargs=* -range -bang MyCMD <line1>,<line2>call MyFUNC(<bang>0, <q-args>) 

、空白のsplit()引数。あるいは、可変数の引数を使用して関数を定義して<f-args>を使用することもできますが、関数の引数の数は制限されています(20 IIRCまで)。

<bang>0は、ブーンをブール値に変換するのに便利です。これは通常必要なものです。

+0

thx Ingo !.はい、私は関数のargsを解析するだろうが、私は正しい方法を知らない。 3つの引数が解析される必要があります。 count、arg、およびflags。すべてオプションです。多分私はいくつかのフォーマットを定義するべきです。 "arg"の場合、スペースは許されているので、値は引用符で囲まなければなりません。それは少し簡単です。数字やフラグ文字列をチェックします。私はやります。これ以上の提案はありますか? – Kent

+0

と私のポストの "別の小さな質問"の理由を知っていますか?私は昨日私の問題の答えを探して、ただ気づいた。ありがとうございました。 – Kent

+0

引数があまりにもあいまいで構文解析できない場合は、構文を再考してください。たぶん統一性を強化したり、それがどのようなタイプのものであるかのヒントを与えるかもしれない。 –

0

厳しい質問があります。私は本当に解決策はありませんが、ここに私の発見です。ヨーヨーとして

:MY 
[0, 3, 1, 0, ''] 
:MY! 
[1, 3, 1, 0, ''] 
:%MY 
[0, 1, 10, 10, ''] 
:%MY 4 
[0, 1, 4, 4, ''] 
:MY 4 
[0, 3, 4, 4, ''] 
:%MY flag 
[0, 1, 10, 10, 'flag'] 
:MY flag 
[0, 3, 1, 0, 'flag'] 
:%MY 4 flag 
[0, 1, 4, 4, 'flag'] 

-countの代わり-range

:command! -count -bang -nargs=* MY echo [<bang>0, <line1>, <line2>, <count>, <q-args>] 

結果と今

:MY 
[0, 3, 3, -1, ''] 
:MY! 
[1, 3, 3, -1, ''] 
:%MY 
[0, 1, 10, 10, ''] 
:%MY 4 
[0, 1, 10, 10, '4'] 
:MY 4 
[0, 3, 3, -1, '4'] 
:%MY flag 
[0, 1, 10, 10, 'flag'] 
:MY flag 
[0, 3, 3, -1, 'flag'] 
:%MY 4 flag 
[0, 1, 10, 10, '4 flag'] 

:次のシナリオを実行した後

:command! -range -bang -nargs=* MY echo [<bang>0, <line1>, <line2>, <count>, <q-args>] 

あなたはそれが簡単ではないことがわかります。あなたのコマンドに-rangeを使用することをお勧めします。そして\d\+で番号を探して<q-args>を解析します。

+0

ありがとう、ピーター。 '\ d +'を探すだけでは不十分です。なぜなら、 'arg'は数字やスペースを含む文字列であるからです。 – Kent