RubyMotionでは外部ライブラリも使えるので,ちょっとゲームでも作ってみようかと思って,ちょうど手元にcocos2d for iPhoneレッスンノートとかがあるのでcocos2dで試してみました.
cocos2dのダウンロード・インストール
http://www.cocos2d-iphone.org/download からダウンロード
Stable Versionのcocos2d-iphone-1.0.1.tar.gz を落として解凍する.
$ motion create cocos2dTest
$ cd cocos2dTest
$ mkdir vendor
$ cp -R ~/cocos2d-iphone-1.0.1 ./vendor/cocos2d-iphone
XCodeテンプレートをインストールします.
$ cd ./vendor/cocos2d-iphone
$ sh install-templates.sh -f -u
XCodeで作れるテンプレートをRubyMotionで動くようにする
ひとまず,cocos2dを参考にコードを書きます.
Xcodeを立ちあげてFile>New>Project
をします.
テンプレート選択画面はiOS>cocos2d>cocos2d
を選びます.
AppDelegate.m
とRootViewController.m
とHelloWorldLayer.m
を参考に変換します.
./app/app_delegate.rb
class AppDelegate
def application(application, didFinishLaunchingWithOptions:launchOptions)
@window = UIWindow.alloc.initWithFrame UIScreen.mainScreen.bounds
director = CCDirector.sharedDirector
@vc = RootViewController.alloc.initWithNibName nil, bundle:nil
@vc.wantsFullScreenLayout = true
glView = EAGLView.viewWithFrame(
@window.bounds,
pixelFormat:KEAGLColorFormatRGB565,
depthFormat:0)
director.setOpenGLView glView
director.setDeviceOrientation KCCDeviceOrientationPortrait
director.setAnimationInterval 1.0/60
director.setDisplayFPS true
@vc.setView glView
@window.addSubview @vc.view
@window.makeKeyAndVisible
CCTexture2D.setDefaultAlphaPixelFormat KCCTexture2DPixelFormat_RGBA8888
CCDirector.sharedDirector.runWithScene HelloWorldLayer.scene
true
end
def application(application, willResignActive:launchOptions)
CCDirector.sharedDirector.pause
end
def application(application, didBecomeActive:launchOptions)
CCDirector.sharedDirector.resume
end
def application(application, didReceiveMemoryWarning:launchOptions)
CCDirector.sharedDirector.purgeCachedData
end
def application(application, didEnterBackground:launchOptions)
CCDirector.sharedDirector.stopAnimation
end
def application(application, willEnterForeground:launchOptions)
CCDirector.sharedDirector.startAnimation
end
def application(application, willTerminate:launchOptions)
director = CCDirector.sharedDirector.
director.openGLView.removeFromSuperview
@vc.release
@window.release
director.end
end
def application(application, significantTimeChange:launchOptions)
end
end
./app/root_view_controller.rb
class RootViewController < UIViewController
end
./app/hello_world_layer.rb
class HelloWorldLayer < CCLayer
def self.scene
scene = CCScene.node
layer = HelloWorldLayer.node
scene.addChild layer
scene
end
def init
super
@label = CCLabelTTF.labelWithString(
"Hello World",
fontName:"Marker Felt",
fontSize: 64)
size = CCDirector.sharedDirector.winSize
@label.position = [size.width/2, size.height/2]
self.addChild @label
self
end
end
Rakefileの設定
外部ライブラリを使う場合は,Rakefile
の編集が必要.
vendorの設定と,OpenGLESやAVFoundationなどのframeworkの設定や依存ライブラリの設定です.
Rakefile
$:.unshift("/Library/RubyMotion/lib")
require 'motion/project'
Motion::Project::App.setup do |app|
# Use `rake config' to see complete project settings.
app.name = 'cocos2dTest'
app.vendor_project("vendor/cocos2d-iphone",
:xcode,
:xcodeproj => "cocos2d-ios.xcodeproj",
:target => "cocos2d",
:products => ["libcocos2d.a"],
:headers_dir => "cocos2d")
app.frameworks += [
"OpenGLES",
"OpenAL",
"AVFoundation",
"AudioToolbox",
"QuartzCore"]
app.libs << "/usr/lib/libz.dylib"
app.interface_orientations = [:landscape_right]
end
vendor_project で外部ライブラリのパスを指定し,2つ目の引数を:xcode
にしてxcode projectを指定します.
.aで提供されている場合は,:static
にすると良いです.
RubyMotionでの詰まりどころ
本来なら,ここでrake
すればcocos2dがビルドされて,app内がビルドされて無事に動くのですが,
Objective-C stub for message `viewWithFrame:pixelFormat:depthFormat:' type `@@:{CGRect={CGPoint=ff}{CGSize=ff}}@I' not precompiled. Make sure you properly link with the framework or library that defines this message.
というエラーが出てシミュレータが終了してしまいました.
これは,./app/app_delegate.rb
のEAGLView.viewWithFrame
でEAGLView viewWithFrame:pixelFormat:depthFormat:
がRuby側から見えてないようです.
RubyMotionでは,定義を参照するために,gen_bridge_metadata
というのを使って*.bridgesupport
というファイルを作っています.
しかし,Rakefile
で指定した:headers_dir => "cocos2d"
の直下しか見ずにgen_bridge_metadata
をしているようです.
しかし,それだとcocos2d/Platforms/iOS
とかの下の定義が参照出来ずにエラーになっているようです.
(EAGLView.h
はcocos2d/Platforms/iOS
の下にあります.)
そのため,/Library/RubyMotion/lib/motion/project/vendor.rb
を編集するか,自分でcocos2d-iphone.bridgesupport
ファイルを生成する必要があります.
ひとまず,bridgesupport
を生成するスクリプトを走らせることにしました.
def sh(command)
system(command)
end
path = Dir.getwd
source_files = Dir.glob('**/*.{c,m,cpp,cxx,mm,h}')
headers = source_files.select { |p| File.extname(p) == '.h' }
bs_files = []
unless headers.empty?
bs_file = File.basename(path) + '.bridgesupport'
if !File.exist?(bs_file) or headers.any? { |h| File.mtime(h) > File.mtime(bs_file) }
includes = headers.map { |p| "-I" + File.dirname(p) }.uniq.join(' ')
sh "/usr/bin/gen_bridge_metadata --format complete --no-64-bit --cflags \"-I. #{includes}\" #{headers.join(' ')} -o \"#{bs_file}\""
end
bs_files << bs_file
end
そして,改めてrake
します.
同じエラーが出ました.orz.
一応,生成されたbridgesupportを見ても確かに元のものよりは定義が増えているのですが,EAGLView
に関するものが増えておらず,ダメなようです.
cocos2dのForumを見ると,cocos2d-iphone/cocos2d/Platform/iOS
をcocos-2d-iphone
直下に持ってきてrake
するとかアドホックな方法で成功はしているらしいですが,cocos2dのソース側も色々とPath変更をしていたりでめんどくさそうでやりたくないです.
というわけで,まだ問題は解決出来ていないです.
0 comments:
コメントを投稿