好きなエディタでこまめに結果確認しながらjruby + processingする
jirbでインタラクティブに書き換えるのも楽しいけどある程度構造考えながらだとエディタで編集しながらのほうがよくて、でも普段emacs使っていてprocessingのIDEは使いたくなかったのでfcwrap(現rascut)からファイル監視の処理をパクってかつ、いつも書く起動まわりの処理をまとめてみた。
require 'pathname' require 'logger' require 'thread' require 'java' include_class 'processing.core.PApplet' include_class 'processing.core.PMatrix' include_class "processing.core.PImage" include_class "processing.core.PFont" class SketchBook JFrame = javax.swing.JFrame DEFAULT_OPTIONS = { :interval => 2, :target_file => Time.now, } def initialize(filename, options = {}) @options = DEFAULT_OPTIONS.merge(options) @target_file = Pathname.new(filename) @timestamp = Time.now @logger = Logger.new(STDOUT) @logger.progname = 'SketchBook' create_sketch open_sketch Sketch.new end def logger @logger end def create_sketch p5_program = '' @mutex = Mutex.new @mutex.synchronize do file = open(@target_file) file.each do |line| p5_program += line end end p5_program = [ 'class Sketch < PApplet', p5_program, 'end' ].join("\n") def p5_environment binding end result = false begin eval(p5_program, p5_environment) result = true rescue logger.error "#{@target_file.basename.to_s} has SyntaxError!" result = false end result end def open_sketch(applet) @frame.visible = false if @frame @frame = JFrame.new applet.class.to_s @frame.content_pane.add applet @frame.default_close_operation = JFrame::EXIT_ON_CLOSE applet.init @frame.pack @frame.visible = true end def file_updated? if @target_file.mtime > @timestamp @timestamp = @target_file.mtime logger.info "#{@target_file.basename.to_s} was updated." true else false end end def run loop do if file_updated? if create_sketch open_sketch Sketch.new end end sleep [@options[:interval], 1].max end end end sketchbook = SketchBook.new(ARGV[0]) sketchbook.run
でコマンドラインから以下のようにするとfoo.rbが監視対象になるので好きなエディタで編集できる。
$ jruby sketchbook.rb foo.rb
foo.rbはこんな感じでrubyであるという点以外は普通のprocessingに近く書ける
def setup size 100, 100 background 255 no_stroke @img_megane = load_image("utamaru160_meagne_only.PNG") smooth end def draw fill 255, random(100), random(100) # background 128 4.times do tint 255, 255, 255, 30 sz = random(20, 40) # image(@img_megane, random(width), random(height), sz, sz) ellipse(random(width), random(height), sz, sz) end end
デモ映像ではwindowsコマンドラインからjruby + sketchbook.rb起動して同じマシン上のcoLinux内のemacsで編集してるfoo.rbを編集して保存されるたびにapplet窓にfoo.rbの内容が反映されている。PAppletのstaticメソッドなんかはあいかわらずPApplet.radiansとかアクセスしないとダメなんだけど普段使ってるエディタが使えるので大部楽しい。