アイデアカードとかいうアイデア出しのサポートツールを見つけました。
目的、着眼点、どう変えるかという3種類のカードがあってカードを引くことでランダムなフレーズが完成するってやつです。昔そういう遊びをしたことはありませんか?誰が、どこで、なにを、どうした、っていう感じたくさんカードにしておいてランダムに引いてできた文章がおかしくて笑う、みたいな遊び。それに近いです。
詳しく説明する気はあまりないので気になる人は上のURLを見てくれればおk。
実物のカードが存在するみたいなんですが、iOS版なんかもあるようです。じゃあRubyのプログラムにしちゃえばいいじゃん?ってことでgem化してみました。完成物はrubygems.orgにアップロード済みです。1回そこまでやってみたかったんです。
ソースはこちらです。
gemの作り方
こちらのスライドを参照しました。超助かりました。
最終的に必要になるのでrubygems.orgでユーザー登録。RubyGems.org | your community gem host
$ bundle gem idea_card
idea_card.gemspec
を編集、authorとかemailとかを埋める実装する
$ rake install
でローカルインストールして確認$ rake release
する # 初回はrubygems.orgのIDとパスワードが設定されていないって怒られるので次の手順$ gem push
IDとパスワードを入れる
$ rake release
中身の説明
データファイル
カードには目的、着眼点、変化の3種類があります。それぞれの文言をハードコーディングしてもよかったのですが一応外部ファイルに書いておくことにしました。
一例ですが、目的を書いたgoals
というテキストファイルがあります。このように一行がカード一枚に対応しています。
スクリプト本体
こういう風に使えるように作りました。
IdeaCard.draw
IdeaCard
はモジュールでdraw
はモジュールの特異メソッドです。
で、実装はこれだけ。
ポイントはIdeaCard.goal
、IdeaCard.point
、IdeaCard.change
の3つのメソッド。必要性はさておき、動的にメソッドを定義しています。実装がかぶっていたからメタにやってみようという程度の理由です。メソッドに対応したファイルを読んで入力を全て取っておき、そのなかからランダムに1つだけ返すという実装です。
微妙にはまる
これといって特に難しいことはありませんが、一箇所はまりました。
current_file_path = File.dirname(__FILE__)
functions.each do |m|
eval <<-EOC
def #{m}
path = File.expand_path "./#{m}s", "#{current_file_path}" # <= この部分
@#{m}s ||= load(path)
@#{m}s.sample
end
EOC
end
このソースファイルと同じパスにデータファイルを置いてあるので、相対パスを使ってデータファイルを読みいくという作りにするつもりで、最初は"#{current_file_path}"
のところにそのまま__FILE__
としていました。ところが、eval
するタイミングでは__FILE__
はこのファイルをrequire
している人、つまりlib/idea_card.rb
(1つ上の階層のファイル)になってしまっていました。おかげでデータファイルが取れないため想定したとおりに動きませんでした。
そういうわけで、evalの外で__FILE__
の値を取っておくという上のような実装に変えて事なきを得ました。これってメタプロの仕組みちゃんとわかってれば当たり前なんですかね。
パーフェクトRubyとメタプログラミングRuby読みなおそうかなー。