2010/11/17


最近のVim界隈では、バッファセレクタの新しい形の一つであるUniteが注目を浴び始めています。
Shougo's unite.vim at master - GitHub

unite all sources

https://github.com/Shougo/unite.vim
Uniteはバッファセレクタという単純な概念に縛られた物ではなく、候補選択を行うユーザインタフェースとして提供されるライブラリ的な代物です。
Uniteにはバッファやファイル、MRU(Most Recently Used)等、通常候補選択しそうな物がUnite sourceとして既に含まれていますが、プラグインを書く事で自分で定義した候補選択がUI付きで実現出来る事になります。

Uniteはまだ発展途上ではありますが、今日はどれだけ少ないコードでUnite UIが使える様になるかを皆さんに伝えるべくUniteプラグイン書いてみました。

名付けて、ユナイトマクドナルドソースです!ェ
以下コード
let s:save_cpo = &cpo
set cpo&vim

let s:source_hamburger = { 'name': 'hamburger' }
let s:source_drink = { 'name': 'drink' }
let s:hamburger = []
let s:drink = []

function! unite#sources#mcdonalds#open_url(url)
  if has('win32')
    exe "!start rundll32 url.dll,FileProtocolHandler " . a:url
  elseif has('mac')
    call system("open '" . a:url . "' &")
  elseif executable('xdg-open')
    call system("xdg-open '" . a:url  . "' &")
  else
    call system("firefox '" . a:url . "' &")
  endif
endfunction

function! s:get_menu()
  let res = http#get("http://www.mcdonalds.co.jp/menu/regular/index.html")
  let dom = html#parse(iconv(res.content, 'utf-8', &encoding))
  for li in dom.find('ul', {'class': 'food-set'}).childNodes('li')
    let url = 'http://www.mcdonalds.co.jp' . li.childNode('a').attr['href']
    let name = li.find('img').attr['alt']
    call add(s:hamburger, [name, url])
  endfor
  for li in dom.find('ul', {'class': 'drink-set'}).childNodes('li')
    let url = 'http://www.mcdonalds.co.jp' . li.find('a').attr['href']
    let name = li.find('img').attr['alt']
    call add(s:drink, [name, url])
  endfor
endfunction

function! s:source_hamburger.gather_candidates(args, context)
  if empty(s:hamburger) && empty(s:drink) | call s:get_menu() | endif
  return map(copy(s:hamburger), '{
        \ "word": v:val[0],
        \ "source": "hamburger",
        \ "kind": "command",
        \ "action__command": "call unite#sources#mcdonalds#open_url(''".v:val[1]."'')"
        \ }')
endfunction

function! s:source_drink.gather_candidates(args, context)
  if empty(s:hamburger) && empty(s:drink) | call s:get_menu() | endif
  return map(copy(s:drink), '{
        \ "word": v:val[0],
        \ "source": "drink",
        \ "kind": "command",
        \ "action__command": "call unite#sources#mcdonalds#open_url(''".v:val[1]."'')"
        \ }')
endfunction

function! unite#sources#mcdonalds#define()
  return executable('curl') ? [s:source_hamburger, s:source_drink] : []
endfunction

let &cpo = s:save_cpo
unlet s:save_cpo
リポジトリは以下のURL
mattn's unite-mcdonalds-vim at master - GitHub

unite source for mcdonalds

https://github.com/mattn/unite-mcdonalds-vim
実行にはwebapi-vimの最新版が必要です。
mattn's webapi-vim at master - GitHub

webapi-vim: Vim Interface to Web API

https://github.com/mattn/webapi-vim
これをpathogen等を使ってランタイムパス上に追加すると、hamburgerソースとdrinkソースが追加されます。 :Unite hamburger
と実行すると...
unite-hamburger
マクドナルドの商品一覧が候補選択出来ます!
さらに選択すると...
unite-mcdonalds
マクドナルドの商品ページがブラウザで表示される! 便利!

そして... :Unite drink
とすると、なんと...
unite-drink
ドリンクの一覧が表示される! 超便利!
徹夜で作業してるとき、「あーマクドナルド行くか...」って時に使って下さい!

Unite便利!ェ
Posted at by



2010/11/10


favstarを見にいくのにいちいちブラウザあげるのが面倒くさいので、なんとかならないかなと思ってた。
普段TwitVimを使ってるんだけど、同じようにvimから見れないかなーと思って勢いで書いた。
function! s:ShowFavStar(...)
  let user = a:0 > 0 ? a:1 : exists('g:favstar_user') ? g:favstar_user : ''
  if len(user) == 0
    echohl WarningMsg
    echo "Usage:"
    echo "  :FavStar [user]"
    echo "  you can set g:favstar_user to specify default user"
    echohl None
    return
  endif
  let yql = "select * from html where url = 'http://favstar.fm/users/".user."/recent' and xpath = '//div[@class=\"tweetContainer\"]'"
  let res = http#get("http://query.yahooapis.com/v1/public/yql", {'q': yql})
  let dom = xml#parse(res.content)
  for item in dom.childNode('results').childNodes('div')
    let tweet = item.find('div', {"class": "theTweet"})
    let text = substitute(tweet.childNode('p').value(), "\n", " ", "g")
    let text = substitute(text, "^ *", "", "")
    echohl Function
    echo text
    echohl None
    let actions = item.findAll('div', {"class": "avatarList"})
    for action in actions
      let line = ''
      if action.attr['id'] =~ "^faved_by_"
        let line .= "FAV:"
      elseif action.attr['id'] =~ "^rt_by_"
        let line .= "RT:"
      endif
      for a in action.findAll('img')
        let line .= " " . a.attr['alt']
      endfor
      echohl Statement
      echo line
      echohl None
    endfor
    echo "\n"
  endfor
endfunction

command! -nargs=? FavStar call <SID>ShowFavStar(<f-args>)
ソースはたったこれだけ。いちおうリポジトリのリンク
mattn's favstar-vim at master - GitHub

vimscript for favstar

http://github.com/mattn/favstar-vim
実行には webapi-vim が必要です。webapi-vim は更新が多いと思うので pathogen とかで使った方がよいです。
mattn's webapi-vim at master - GitHub

vim interface to Web API

http://github.com/mattn/webapi-vim
html(実際にはxml)をDOMでスクレイピングしてます。webapi-vimのxml.vimさまさまです。誰が書いたの?スゲーな。えっ俺ですか。俺スゲー?
で、YQLを使ってスクレイピングしているのはHTMLは正規化されていないのでYQLに正規化してもらっています。
実行は :FavStar otsune
とするかvimrcに let g:favstar_user = "otsune"
と書いておいて :FavStar
とする等して下さい。動かなかったとしても大丈夫だ。問題ない。

実行するとこんな画面になります。
favstar-vim
ご活用下さい。もうvimscriptなんでもアリな気がしてきた。
Posted at by



2010/10/31


古くからvimmerの人は知ってるかもしれませんが、昔excitetranslate.vimというスクリプトを書きました。 英語が書かれたバッファで :ExciteTranslate と実行すると分割ウィンドウに翻訳された文章が表示されるという物です。昨日githubにも入れておきました。
mattn's excitetranslate-vim at master - GitHub

Translate between English and Japanese using Excite

http://github.com/mattn/excitetranslate-vim
前は別のリポジトリに置いてあって、最初にリポジトリにcommitしたのが2006年でした。結構長く使っているスクリプトです。
これまでvimの環境を作る際には結構な頻度で入れてきたスクリプトですが、GoogleTranslateの方が場合によっては翻訳精度が高かったりするので、googletranslate.vimというのを書きました。

mattn's googletranslate-vim at master - GitHub

Translate between English and Japanese using Google

http://github.com/mattn/googletranslate-vim
使い方はexciteと同じく :GoogleTranslate で翻訳可能です。ちなみに文章が英語であれば日本語に、日本語であれば英語に翻訳されます。
Dan the Man with Too Many Home Appliances to Maintaitain

:GoogleTranslate
引用: http://blog.livedoor.jp/dankogai/archives/51541861.html
あまりにも多くの家電製品とダンマンはMaintaitainする
...

:ExciteTranslate Maintaitainへのあまりに多くの家電をもっているダン男性 えぇ......っと。。。。。(汗
Posted at by