Rubyでどう書く?:RubyCocoa+Core Animationでお手軽アニメーション
佐藤伸吾(KBMJ)
2008/08/14 08:00
今回はRubyCocoaとMac OS XのフレームワークであるCore Animationを使って、お手軽にアニメーションを作成してみましょう。
問題
RubyCocoaは、Mac OS XのCocoaオブジェクトをRubyスクリプトからRubyオブジェクトとして扱うための、Ruby用ライブラリとフレームワークです。RubyCocoaを用いれば、RubyでCocoaアプリケーションを記述することができるのです。
Core AnimationはMax OS Xのフレームワークで、その利点は手軽さにあります。普通にアニメーションプログラミングを行おうとすると、時間軸管理、非同期な描画スレッド、パフォーマンスの向上など、考慮すべき点があまりにも多すぎます。
しかし、Core Animationを用いれば、面倒な部分はOSに任せて、自分の実現したいことに集中できるのです。
今回はRubyCocoaとMac OS XのフレームワークであるCore Animationを使って、お手軽にアニメーションを作成してみましょう。
回答例
AppController.rbを作成し、以下のように記述します。
require 'osx/cocoa'
OSX.require_framework 'QuartzCore'
class AppController < OSX::NSObject
ib_outlet :window
ib_outlet :view
ib_action :pressPosition
ib_action :pressRotation
ib_action :pressSepia
ib_action :pressBloom
ib_action :pressHole
ib_action :pressZoom
ib_action :pressHalftone
def awakeFromNib
bitmapImage = OSX::NSBitmapImageRep.imageRepWithContentsOfFile_('/Users/ssato/Pictures/ruby.png')
image = bitmapImage.CGImage()
layer = OSX::CALayer.layer()
layer.contents = image
layer.frame = OSX::CGRectMake(0,0,995/4,996/4)
black=OSX::CGColorCreateGenericRGB(0,0, 0,1.0)
backgroundLayer=OSX::CALayer.layer()
backgroundLayer.backgroundColor=black
backgroundLayer.addSublayer_(layer)
@view.setLayer_(backgroundLayer)
@view.setWantsLayer_(true)
end
def pressPosition(sender)
animation = OSX::CABasicAnimation.animationWithKeyPath_('position')
animation.duration = 1.0
layer = @view.layer.sublayers.objectAtIndex_(0)
position = layer.position
animation.fromValue = OSX::NSValue.valueWithPoint_(OSX::NSPointFromCGPoint(position))
position.x += 256;
position.y += 160;
animation.toValue = OSX::NSValue.valueWithPoint_(OSX::NSPointFromCGPoint(position))
animation.autoreverses = true
animation.repeatCount = 4
layer.addAnimation_forKey_(animation, 'positionAnimation')
end
def pressRotation(sender)
animation = OSX::CABasicAnimation.animationWithKeyPath_('transform')
animation.duration = 0.5
animation.autoreverses = true
animation.repeatCount = 4
transform = OSX::CATransform3DIdentity
animation.fromValue = OSX::NSValue.valueWithCATransform3D(transform)
transform = OSX::CATransform3DMakeRotation(Math::PI, 0, 1.0, 0)
transform.m34 = 1.0 / -420.0
animation.toValue = OSX::NSValue.valueWithCATransform3D(transform)
layer = @view.layer.sublayers.objectAtIndex_(0)
layer.addAnimation_forKey_(animation, 'transformAnimation')
end
def pressSepia(sender)
filter = OSX::CIFilter.filterWithName_('CISepiaTone')
filter.setDefaults()
layer = @view.layer.sublayers.objectAtIndex_(0)
layer.name = 'sepiaFilter'
layer.setFilters_(OSX::NSArray.arrayWithObject_(filter))
end
def pressBloom(sender)
filter2 = OSX::CIFilter.filterWithName_('CIBloom')
filter2.setDefaults
filter2.setValue_forKey_(OSX::NSNumber.numberWithFloat_(0.0), 'inputIntensity')
filter2.setValue_forKey_(OSX::NSNumber.numberWithFloat_(5.0), 'inputRadius')
filter2.setName_('bloomFilter')
layer = @view.layer.sublayers.objectAtIndex_(0)
layer.setFilters_(OSX::NSArray.arrayWithObject_(filter2))
pluseAnimation = OSX::CABasicAnimation.animation
pluseAnimation.keyPath = 'filters.bloomFilter.inputIntensity'
pluseAnimation.fromValue = OSX::NSNumber.numberWithFloat_(0.0)
pluseAnimation.toValue = OSX::NSNumber.numberWithFloat_(1.5*2)
pluseAnimation.duration = 1.0
pluseAnimation.repeatCount = 4
pluseAnimation.autoreverses = true
layer.addAnimation_forKey_(pluseAnimation, 'bloom')
end
def pressHole(sender)
filter = OSX::CIFilter.filterWithName_('CIHoleDistortion')
filter.setDefaults()
layer = @view.layer.sublayers.objectAtIndex_(0)
layer.setFilters_(OSX::NSArray.arrayWithObject_(filter))
end
def pressZoom(sender)
filter = OSX::CIFilter.filterWithName_('CIZoomBlur')
filter.setDefaults()
layer = @view.layer.sublayers.objectAtIndex_(0)
layer.setFilters_(OSX::NSArray.arrayWithObject_(filter))
end
def pressHalftone(sender)
filter = OSX::CIFilter.filterWithName_('CICMYKHalftone')
filter.setDefaults()
layer = @view.layer.sublayers.objectAtIndex_(0)
layer.setFilters_(OSX::NSArray.arrayWithObject_(filter))
end
end
Interface Builderで画像1のようにコンポーネントを配置します。
画像1
NSObjectを追加して、ClassにAppcontrollerを指定します(画像2)。
画像2
OutletsとActionsのConnectionを画像3のように設定します。
画像3
実行結果
Positionボタンを押すと、画像が斜めに移動します(画像4)。
画像4
Rotationボタンを押すと画像が回転し、Sepiaをクリックすると画像がセピア色になります(画像5)。
画像5
同様に、Bloomは画像が光り輝き(画像6)、Holeは画像に穴が空きます(画像7)。Zoomボタンはズームエフェクト(画像8)で、Halftoneはハーフトーンフィルタです(画像9)。
画像6
画像7
画像8
画像9
解説
- 特集: Rubyでどう書く? (7件)
- ホワイトペーパー
- 話題のタグ
UI
マイクロソフト
Microsoft
Internet Explorer
iPhone 3G
iPod touch
リファレンス
ブラウザ
Google
Windows XP
Java
CSS
アプリケーション
インストール
Chrome
OS
Firefox 3
Apple
Firefox
Linux
Mac OS X
データベース
JavaScript
Windows 7
Mozilla
Safari
脆弱性
Webデザイン
モバイル
Off Topic
Windows
開発環境
仮想化
セキュリティ
WebKit
Webサービス
オープンソース
小技
RIA
Database
PHP
iPhone
プログラミング言語
HTML
Opera
Flash
Tips
ソフトウェア開発
Windows Vista
Ajax
話題のタグを見る »
グーグル、JavaScriptプログラミングツールをリリース
Windowsの歴史 Windows Server 2008編:同じカーネルを持つ「Vista」とは対照的に早くから支持を得たサーバOS
Windowsの歴史 Windows Server 2003 R2編:安定性と先進性の両立目指す「R2」の先駆けとなったOS
モジラ、「Firefox 3.6」の第1ベータ版をリリース
企業ITシステムの企画、構築、運用のイロハ
―エン・ジャパン厳選求人☆毎週更新―
進むストレージ環境の見直し
100万円で実現!中小企業の情報漏えい対策
大丈夫?あなたの会社のセキュリティ対策
【最終警告】パンデミック対策特集
最大32個のセンサーが電力を徹底管理!