你能告诉Vim打开一个不同于命令行传递的文件或者:e?

时间:2011-06-24 11:39:19

标签: vim

我想教Vim如何从像File::Find这样的名字打开Perl 5模块。我已经有一个用Perl 5编写的包装脚本来处理命令行(见下文),但我希望能够说出像:tabe File::Find这样的东西并让它真正执行:tabe /home/cowens/apps/perlbrew/perls/perl-5.14.0/lib/5.14.0/File/Find.pm

我目前的计划是以某种方式使用autocmd BufNewFile和/或autocmd BufPreRead,但我无法弄清楚如何切换文件名。

#!/usr/bin/perl

use strict;
use warnings;

my @files = @ARGV;
for my $file (@files) {
    next if -f $file; #skip files that really exist

    #convert from module name to module file
    (my $module = $file) =~ s{::}{/}g;
    $module .= ".pm";

    #look for module in the include paths
    for my $dir (@INC) {
        my $candidate = "$dir/$module";
        if (-f $candidate) {
            $file = $candidate;
            last;
        }
    }
}

#replace this script with vim
exec "vim", "-p", @files;

6 个答案:

答案 0 :(得分:4)

否则

:verbose au BufReadCmd

会告诉你其他类型的插件是如何做到的(例如zip,netrw,fugitive)。样本输出应该给你很多想法:

zip  BufReadCmd
    zipfile:* call zip#Read(expand("<amatch>"), 1)
    Last set from C:\Program Files\Vim\vim73\plugin\zipPlugin.vim
    *.zip     call zip#Browse(expand("<amatch>"))
    Last set from C:\Program Files\Vim\vim73\plugin\zipPlugin.vim

Network  BufReadCmd
    ftp://*   exe "silent doau BufReadPre ".fnameescape(expand("<amatch>"))|call netrw#Nread(2,expand("<amatch>"))|exe "silent doau BufReadPost ".fnameescape(expand("<amatch>"))
    Last set from C:\Program Files\Vim\vim73\plugin\netrwPlugin.vim
    http://*  exe "silent doau BufReadPre ".fnameescape(expand("<amatch>"))|call netrw#Nread(2,expand("<amatch>"))|exe "silent doau BufReadPost ".fnameescape(expand("<amatch>"))
    Last set from C:\Program Files\Vim\vim73\plugin\netrwPlugin.vim

fugitive_files  BufReadCmd
    *.git/index
              exe s:BufReadIndex()
    Last set from C:\Program Files\Vim\vimfiles\plugin\fugitive.vim
    *.git/*index*.lock
              exe s:BufReadIndex()
    Last set from C:\Program Files\Vim\vimfiles\plugin\fugitive.vim
    fugitive://**//[0-3]/**
              exe s:BufReadIndexFile()
    Last set from C:\Program Files\Vim\vimfiles\plugin\fugitive.vim
    fugitive://**//[0-9a-f][0-9a-f]*
              exe s:BufReadObject()
    Last set from C:\Program Files\Vim\vimfiles\plugin\fugitive.vim

答案 1 :(得分:3)

考虑使用ctags。如果您能够在源代码上运行ctags进程,那么您应该能够达到以下目的:

vim -t File::Find

Vim有关于此的信息(:help vim)我认为ctags可能远远超出您的尝试范围,允许您从一个源文件的中间跳转到原始函数定义在另一个。

答案 2 :(得分:2)

要手动打开这些文件,我建议使用:find:tabfind命令分别代替:edit:tabedit。该 这两对命令之间的区别在于前者的外观 不仅适用于当前路径中的文件,还适用于中列出的目录中的文件 path选项(请参阅:help 'path')。如果添加Perl @INC目录 通过Vim path选项,您可以使用:find或快速找到模块文件 :tabfind个命令。例如,要打开新标签页并进行编辑 您可以在File::Find模块文件中键入

:tabfind File/Find.pm

(您不必手动输入整个子路径:find和。{ :tabfind完成时会考虑当前的path值。)

使用gf^Wf按模块名称自动查找这些文件, ^Wgf,您需要另外更改(使用filetype插件或 autocommand)Perl文件的以下选项。

:set isfname+=:
:set suffixesadd+=.pm
:set includeexpr=substitute(v:fname,'::','/','g')

在这些选项之后(以及包含Perl path的{​​{1}}选项 目录)设置,您可以使用@INC轻松打开模块文件 - 就像 相应模块名称的命令。

答案 3 :(得分:0)

基于下面的答案的懒惰解决方案。目前的问题:

  1. 它写的文件是原始名称,而不是munged名称
  2. 看起来设置文件类型的自动命令运行得太快,根本没有运行,或者很困惑。
  3. 正在使用外部命令来完成工作
  4. 它特定于我想要的改变(即它不是一般的)
  5. 当我有更多停机时间时,我希望修复上述所有内容并将其转换为插件。

    .vimrc

    中的

    autocmd BufReadCmd * r!cat_perl %
    
    cat_perl

    中的

    #!/usr/bin/perl
    
    use strict;
    use warnings;
    
    sub cat {
        my $file = shift;
        open my $fh, "<", $file
            or die "could not open $file: $!";
        print while <$fh>;
        exit;
    }
    
    my $file = shift;
    
    cat $file if -f $file;
    
    #convert from module name to module file
    (my $module = $file) =~ s{::}{/}g;
    $module .= ".pm";
    
    #look for module in the include paths
    for my $dir (@INC) {
        my $candidate = "$dir/$module";
        cat $candidate if -f $candidate;
    }
    print "";
    

答案 4 :(得分:0)

使用vim的gf命令(转到文件)实际上可能是这样。

在您的代码中,如果您看到类似File :: Find的字符串,请将光标放在它上面并以正常模式键入gf。对我来说,这会立即将我带到File :: Find包。

我认为这是perl文件类型库的一部分,因为它在使用--noplugin执行vim时适用于我。

答案 5 :(得分:0)

这是一个working example showing how to use the BufReadCmd autocmd来编辑指定文件以外的文件(在这种情况下,在打开.css文件时编辑相应的.scss文件)。