多摩美 - “iTamabi” – iPhoneアプリ開発プロジェクト 2010
openFrameworks for iPhone:Addonをつかう
Addonについて
Addonとは
- OpenFrameworksに機能を拡張するためのライブラリー
- processingのLibrariesのような存在
- OpenFrameworks単体ではできなかった様々な機能を実現
- oF本体の開発者以外でも独自に開発して追加することが可能
- アドオン情報
- addons | openFrameworks http://www.openframeworks.cc/addons
- oF addons http://addons.openframeworks.cc/
- of unofficial http://www.openframeworks.info/addons
openFramewokrs v0.0061 for iPhone FAT版にインストールされているAddon
- 他のプラットフォーム(Mac/Win/Linux)と共通のもの
- ofxDirList – ディレクトリの項目の一覧を生成
- ofxVectorGraphics – OpenFrameworksからPostscriptを生成し出力する
- ofxVectorMath – ベクトルや、座標、行列の計算を行う
- ofxXmlSettings – アプリケーションの設定をXML形式で保存、読込み
- iPhone版固有のAddon
- ofxiPhone – openFrameworksをiPhoneで作動させるためのコアな機能
- ofxAccelerometer – iPhone/iPad版固有のAddon、iPhone/iPadの加速度センサーの値を取得
- ofxMultiTouch – マルチタッチのインタフェイスを使用するための機能
Addonの追加方法
- Addonは、フォルダ内のソース(src)、またもし存在すればライブラリ(libs)フォルダをプロジェクトに追加する
- まず、Addonのフォルダごとプロジェクトに追加した後で、余計なものを取り除く(examples, install.xmlなど)
- 複数のAddonが存在する際などは、プロジェクト内に「Addons」というグループを作成し、その中に追加していくとわかりやすい
Addonを使ってみる
物理シミュレーション – ofxBox2D
Box2Dとは
- C++で書かれた、物理エンジン
- 重力や反発力、摩擦、衝突判定といった物理計算を複雑な計算をすることなく利用できる
- ActionScript、Java、C#、Pythonなどにも移植されている
ダウンロードとインストール
- iPhone/iPadで、Box2Dを使用する場合には、最新版が必要
- Google Codeからダウンロード – http://code.google.com/p/vanderlin/downloads/detail?name=ofxBox2d_v2.1.zip&can=2&q=
- Zipファイルを展開して、「ofxBox2d」フォルダを「openFrameworksのフォルダ/addons/」以下にコピーする
ofxBox2dをプロジェクトに追加
- XCodeで「ファイル」→「新規プロジェクト」を選択して新規プロジェクトを作成
- XCode画面の左側のコラム「グループとファイル」の欄の一番先頭にあるプロジェクト名の表示されたアイコンをコントロール+クリック、もしくは右クリック – 「追加」→「新規グループ」を選択
- 追加されたグループのフォルダに「addons」という名前をつける
- addonsフォルダをコントロール+クリック、もしくは右クリック – 「追加」→「既存のファイル」を選択
- addonsフォルダから「ofxBox2d」フォルダを選択
- 設定画面の設定はそのままで「追加」をクリック
- ofxBox2dフォルダ内の「example」はフォルダごと削除して、「参照を削除」を選択
サンプルテンプレートをダウンロード
- Box2Dの基本設定をしたサンプルテンプレートを下記にアップロードしました
- Box2Dの世界の基本設定を一通りしたもの
testApp.h
#pragma once #include "ofMain.h" #include "ofxiPhone.h" #include "ofxiPhoneExtras.h" #include "ofxBox2d.h" class testApp : public ofxiPhoneApp { public: void setup(); void update(); void draw(); void exit(); void touchDown(ofTouchEventArgs &touch); void touchMoved(ofTouchEventArgs &touch); void touchUp(ofTouchEventArgs &touch); void touchDoubleTap(ofTouchEventArgs &touch); void lostFocus(); void gotFocus(); void gotMemoryWarning(); void deviceOrientationChanged(int newOrientation); ofxBox2d box2d; //Box2Dのインスタンス };
testApp.mm
#include "testApp.h" //-------------------------------------------------------------- void testApp::setup(){ //iPhone、iPadの基本設定 ofRegisterTouchEvents(this); ofxAccelerometer.setup(); ofxiPhoneAlerts.addListener(this); ofBackground(0,0,0); //Box2Dの基本設定 box2d.init(); //初期化 box2d.registerGrabbing(); //物体をつかめるように設定 box2d.setGravity(0, 1); //重力の設定(下方向に1) box2d.createBounds(0, 0, ofGetWidth(), ofGetHeight()); //枠を追加 box2d.setFPS(15.0); //Box2Dの演算の更新頻度を設定 box2d.setIterations(5, 5); //インタラクションの精度を設定 } //-------------------------------------------------------------- void testApp::update(){ box2d.update(); //Box2Dの物理演算を実行 } //-------------------------------------------------------------- void testApp::draw(){ } //-------------------------------------------------------------- void testApp::exit(){ } //-------------------------------------------------------------- void testApp::touchDown(ofTouchEventArgs &touch){ } //-------------------------------------------------------------- void testApp::touchMoved(ofTouchEventArgs &touch){ } //-------------------------------------------------------------- void testApp::touchUp(ofTouchEventArgs &touch){ } //-------------------------------------------------------------- void testApp::touchDoubleTap(ofTouchEventArgs &touch){ } //-------------------------------------------------------------- void testApp::lostFocus(){ } //-------------------------------------------------------------- void testApp::gotFocus(){ } //-------------------------------------------------------------- void testApp::gotMemoryWarning(){ } //-------------------------------------------------------------- void testApp::deviceOrientationChanged(int newOrientation){ }
物理世界に物体を置いてみる
- ofxBox2dCircle – 円形の物理法則を適用可能な物体
- 生成した円は、vector(動的配列)に格納して管理してみる – circles
- 画面をタッチすると、その座標をとりだして、円(ofxBox2dCircle)を生成し、vector circlesに追加する
- testApp.mmのdrawメソッド内で、circlesに格納された全ての円(ofxBox2dCircle)を描画している
testApp.h
#pragma once #include "ofMain.h" #include "ofxiPhone.h" #include "ofxiPhoneExtras.h" #include "ofxBox2d.h" class testApp : public ofxiPhoneApp { public: void setup(); void update(); void draw(); void exit(); void touchDown(ofTouchEventArgs &touch); void touchMoved(ofTouchEventArgs &touch); void touchUp(ofTouchEventArgs &touch); void touchDoubleTap(ofTouchEventArgs &touch); void lostFocus(); void gotFocus(); void gotMemoryWarning(); void deviceOrientationChanged(int newOrientation); ofxBox2d box2d; //Box2Dのインスタンス vector <ofxBox2dCircle> circles; //円形の物体のインスタンス };
testApp.mm
#include "testApp.h" //-------------------------------------------------------------- void testApp::setup(){ //iPhone、iPadの基本設定 ofRegisterTouchEvents(this); ofxAccelerometer.setup(); ofxiPhoneAlerts.addListener(this); ofBackground(0,0,0); //Box2Dの基本設定 box2d.init(); //初期化 box2d.registerGrabbing(); //物体をつかめるように設定 box2d.setGravity(0, 1); //重力の設定(下方向に1) box2d.createBounds(0, 0, ofGetWidth(), ofGetHeight()); //枠を追加 box2d.setFPS(15.0); //Box2Dの演算の更新頻度を設定 box2d.setIterations(5, 5); //インタラクションの精度を設定 } //-------------------------------------------------------------- void testApp::update(){ box2d.update(); //Box2Dの物理演算を実行 } //-------------------------------------------------------------- void testApp::draw(){ //描画した円(ofxBox2dCircle)の数だけ、円を描画する for(int i=0; i<circles.size(); i++) { circles[i].draw(); } } //-------------------------------------------------------------- void testApp::exit(){ } //-------------------------------------------------------------- void testApp::touchDown(ofTouchEventArgs &touch){ //画面をタッチすると新たに円(ofxBox2dCircle)を追加する ofPoint pos; //タッチした座標を格納するための変数 pos.set(touch.x, touch.y); //タッチした場所を取得 ofxBox2dCircle c; //新規にofxBox2dCircleをインスタンス化 c.setPhysics(1.0, 0.8, 0.3); //物理特性を設定 //Box2Dの世界に追加 c.setup(box2d.getWorld(), pos.x, pos.y, ofRandom(10, 30)); circles.push_back(c); //Vector、circlesに作成した円を追加 } //-------------------------------------------------------------- void testApp::touchMoved(ofTouchEventArgs &touch){ } //-------------------------------------------------------------- void testApp::touchUp(ofTouchEventArgs &touch){ } //-------------------------------------------------------------- void testApp::touchDoubleTap(ofTouchEventArgs &touch){ } //-------------------------------------------------------------- void testApp::lostFocus(){ } //-------------------------------------------------------------- void testApp::gotFocus(){ } //-------------------------------------------------------------- void testApp::gotMemoryWarning(){ } //-------------------------------------------------------------- void testApp::deviceOrientationChanged(int newOrientation){ }
iPhone / iPadの加速度センサーで、重力の向きと大きさを変化させる
– testApp.mm のupdateメソッドの中に、加速度センサーの値を参照するコードを追加する
testApp.h
#pragma once #include "ofMain.h" #include "ofxiPhone.h" #include "ofxiPhoneExtras.h" #include "ofxBox2d.h" class testApp : public ofxiPhoneApp { public: void setup(); void update(); void draw(); void exit(); void touchDown(ofTouchEventArgs &touch); void touchMoved(ofTouchEventArgs &touch); void touchUp(ofTouchEventArgs &touch); void touchDoubleTap(ofTouchEventArgs &touch); void lostFocus(); void gotFocus(); void gotMemoryWarning(); void deviceOrientationChanged(int newOrientation); ofxBox2d box2d; //Box2Dのインスタンス vector <ofxBox2dCircle> circles; //円形の物体のインスタンス };
testApp.mm
#include "testApp.h" //-------------------------------------------------------------- void testApp::setup(){ //iPhone、iPadの基本設定 ofRegisterTouchEvents(this); ofxAccelerometer.setup(); ofxiPhoneAlerts.addListener(this); ofBackground(0,0,0); //Box2Dの基本設定 box2d.init(); //初期化 box2d.registerGrabbing(); //物体をつかめるように設定 box2d.setGravity(0, 1); //重力の設定(下方向に1) box2d.createBounds(0, 0, ofGetWidth(), ofGetHeight()); //枠を追加 box2d.setFPS(15.0); //Box2Dの演算の更新頻度を設定 box2d.setIterations(5, 5); //インタラクションの精度を設定 } //-------------------------------------------------------------- void testApp::update(){ box2d.update(); //Box2Dの物理演算を実行 //加速度センサーで重力を設定 ofPoint gravity = ofxAccelerometer.getForce(); gravity *= 5.0; gravity.y *= -1.0; box2d.setGravity(gravity); } //-------------------------------------------------------------- void testApp::draw(){ //描画した円(ofxBox2dCircle)の数だけ、円を描画する for(int i=0; i<circles.size(); i++) { circles[i].draw(); } } //-------------------------------------------------------------- void testApp::exit(){ } //-------------------------------------------------------------- void testApp::touchDown(ofTouchEventArgs &touch){ //画面をタッチすると新たに円(ofxBox2dCircle)を追加する ofPoint pos; //タッチした座標を格納するための変数 pos.set(touch.x, touch.y); //タッチした場所を取得 ofxBox2dCircle c; //新規にofxBox2dCircleをインスタンス化 c.setPhysics(1.0, 0.8, 0.3); //物理特性を設定 //Box2Dの世界に追加 c.setup(box2d.getWorld(), pos.x, pos.y, ofRandom(10, 30)); circles.push_back(c); //Vector、circlesに作成した円を追加 } //-------------------------------------------------------------- void testApp::touchMoved(ofTouchEventArgs &touch){ } //-------------------------------------------------------------- void testApp::touchUp(ofTouchEventArgs &touch){ } //-------------------------------------------------------------- void testApp::touchDoubleTap(ofTouchEventArgs &touch){ } //-------------------------------------------------------------- void testApp::lostFocus(){ } //-------------------------------------------------------------- void testApp::gotFocus(){ } //-------------------------------------------------------------- void testApp::gotMemoryWarning(){ } //-------------------------------------------------------------- void testApp::deviceOrientationChanged(int newOrientation){ }