TwitVim - Twitter client for Vim : vim online
TwitVim is a Vim plugin that allows you to post to Twitter and view Twitter timelines.
http://www.vim.org/scripts/script.php?script_id=2204
twitvim - Twitter Client for Vim - Google Project Hostingtwitvimも例外なく僕の欲しい機能がなかったりする。例えば
A Twitter client written in Vim script. See http://vim.sourceforge.net/scripts/script.php?script_id=...
http://code.google.com/p/twitvim/
- <leader>vなんかでそのツィートのpermalinkを開いてほしい
- 入力中に今何文字入力しているか確認したい
- 公式RTじゃなくて軟式RT(非公式RT)が使いたい
こういうときは外側からそのスクリプトを弄る。
でもtwitvimの関数の殆どは"s:"で始まるスクリプトスコープ。外側からは触れません。ただしhack無しの場合。
スクリプトスコープの関数は、実はSNRという装飾が付いた関数名になっていて、例えば
function s:launch_browser(url)
と宣言された関数を外部から呼び出すには
<SNR>39_launch_browser
と装飾キーとスクリプト番号を付与してあげれば呼び出しが可能。このスクリプト番号とはスクリプトファイル1つに対して1つ割り当てられた数値。
:scriptnames
で確認出来ます。またファイル名でひっかけなくてもcommandコマンドの結果から抜き取る事も出来ます。
silent! redir => commands
silent! command PosttoTwitter
silent! redir END
let g:twitvim_sid = substitute(split(commands, "\n")[-1], '^.*<SNR>\(\d\+\)_.*$', '\1', '')
あとはこのSIDを使って、mapしたり関数を呼び出したりすればok。例えば↑のpermalinkを開く改造であれば
function! TwitVimShowInBrowser()
silent! redir => json
silent! TwitVimShowCurbuffer
silent! redir END
let curbuffer = eval(substitute(json, "\n", '', 'g'))
let id = get(curbuffer.statuses, line('.'))
if id != 0
let user = substitute(curbuffer.buffer[line('.')-1], ':.*', '', '')
let url = "http://twitter.com/".user."/statuses/".id
call function('<SNR>'.g:twitvim_sid.'_launch_browser')(url)
endif
endfunction
この様に書ける訳です。スクリプトスコープで無いと参照する事が出来ない関数を呼び出しています。 こうかけば非公開関数であるはずのlaunch_browser()を呼び出す事が出来ます。同じ要領で、文字数をカウントしてみましょう。twitvimはコマンドラインからツィートを投げたりするのですが、コマンドラインは入力のフックがとても難しいのです。
function! TwitVimShowMessageLength()
let line = getcmdline()
if expand('<sfile>') !~ 'CmdLine_Twitter'
return line
endif
echo ""
redraw
echohl WarningMsg
echo function('<SNR>'.g:twitvim_sid.'_mbstrlen')(line) . " character(s)"
echohl None
redraw
silent sleep 1
return line
endfunction
cnoremap <c-g> <c-\>eTwitVimShowMessageLength()<cr>
getcmdline()関数で現在のカーソル位置情報を退避しておき、現在の文字数を非公開関数mbstrlen()から得て表示。1秒経ったら元に戻すという物。これで
:PosttoTwitter
とした後、タイプ中に「今何文字目だろう?確認するには投げてみるしかないし、長すぎたら消えて履歴から戻せないんだよな。」って時でもCTRL-gをタイプすれば文字数が分かる様になります。
さて、最後の軟式RTについてですが実はtwitvimには手動RTのインタフェースが既に定義されている。でもキーマッピングされていない為にどこからも呼び出す事が出来ない。おそらく公式RTポスト処理を実装した時に軟式RTポスト処理をそのままにしたのだろう。
exe "nnoremap <buffer> <leader>q :call <SNR>".g:twitvim_sid."_Retweet()<cr>"
こうすれば呼び出せる。全体のコードだと以下の様になる。
function! s:TwitVimSetup()
if has('win32')
let g:twitvim_browser_cmd = 'rundll32 url.dll,FileProtocolHandler'
else
let g:twitvim_browser_cmd = 'w3m'
endif
silent! redir => commands
silent! command PosttoTwitter
silent! redir END
let g:twitvim_sid = substitute(split(commands, "\n")[-1], '^.*<SNR>\(\d\+\)_.*$', '\1', '')
function! TwitVimShowIcon()
silent! redir => json
silent! TwitVimShowCurbuffer
silent! redir END
let curbuffer = eval(substitute(json, "\n", '', 'g'))
let id = get(curbuffer.statuses, line('.'))
if id != 0
let user = substitute(curbuffer.buffer[line('.')-1], ':.*', '', '')
exec "OpenBrowser http://api.dan.co.jp/twicon/".user."/bigger"
endif
endfunction
function! TwitVimShowInBrowser()
silent! redir => json
silent! TwitVimShowCurbuffer
silent! redir END
let curbuffer = eval(substitute(json, "\n", '', 'g'))
let id = get(curbuffer.statuses, line('.'))
if id != 0
let user = substitute(curbuffer.buffer[line('.')-1], ':.*', '', '')
let url = "http://twitter.com/".user."/statuses/".id
call function('<SNR>'.g:twitvim_sid.'_launch_browser')(url)
endif
endfunction
function! TwitVimShowMessageLength()
let line = getcmdline()
if expand('<sfile>') !~ 'CmdLine_Twitter'
return line
endif
echo ""
redraw
echohl WarningMsg
echo function('<SNR>'.g:twitvim_sid.'_mbstrlen')(line) . " character(s)"
echohl None
redraw
silent sleep 1
return line
endfunction
cnoremap <c-g> <c-\>eTwitVimShowMessageLength()<cr>
function! TwitVimUserMap()
nnoremap <buffer> <leader>t :FriendsTwitter<cr>
nnoremap <buffer> <leader>T :RepliesTwitter<cr>
exe "nnoremap <buffer> <leader>q :call <SNR>".g:twitvim_sid."_Retweet()<cr>"
nnoremap <buffer> <leader>i :call TwitVimShowIcon()<cr>
nnoremap <buffer> <leader>V :call TwitVimShowInBrowser()<cr>
if has('win32') && !has('gui_running')
exe "noremap <char-206><char-199> ".maparg("<c-pageup>")
exe "noremap <char-206><char-210> ".maparg("<c-pagedown>")
endif
endfunction
autocmd FileType twitvim call TwitVimUserMap()
silent! delcommand UseVimball
endfunction
autocmd VimEnter * call s:TwitVimSetup()
vimrcに足して使ってます。ちなみに
UseVimball
コマンドを消しているのはUserTwitter
と被って補完を間違う事が多い為。この方法さえ分かれば、貴方もVim Hackerですね!どんどん他人のスクリプトを改造してしまいましょう!