cocos2d : 脳トレ15パズル-その2

脳トレ15パズルの途中経過


15パズルと名乗っていますが、実際は上記映像のように記憶ゲームです。15パズルが
シャッフルされた順番(経路)を記憶し、その経路を逆に辿って元に戻します。

アイデアのきっかけ

仕事で15パズルを作成する機会があったのですが、中間チェックの際クライアントから
「パズルが解けない」場合があると報告されたのです。適当にピースを配置すると解けない
パズルになるようなので、完成した状態からシャッフルすることにしました。色々なところで
見かける15パズルですが、完成した状態からシャッフルして崩すのは演出ではなく必要なこと
だったのです。このときにシャッフルした順番を記憶すれば簡単に解けるのでは?
と思ったのがアイデアのきっかけです。私が社会人に成り立ての頃、CD-ROMの時代のお話し。

メモは明日

週末を利用して一気に作成したのでメモがめちゃくちゃ。色々忘れないうちにメモに
まとめないと…。明日しっかりとまとめよう。
ややこしそうな部分は完成したので、あとは合間の時間でも問題なく進められそうです。
 
 
 

coco2d : 脳トレ15パズル-その1

今週の進捗

書き溜めた記事はもう無いので箇条書きのメモ…。
 

homeボタンの作成

cocos2dではボタンはmenuItemで作成し、それをmenuに登録する形になります。
menuItemには幾つか種類があり、spriteからボタンを作成する場合は以下の様に
menuItemSpriteを利用します。引数はON/OFFそれぞれのスプライト。
—————————————————————————————
MenuItemSprite* menuHome = MenuItemSprite::create(spHomeOFF, spHomeON);
—————————————————————————————
このときボタンの文字を別のスプライトで用意したかったのですが、以下の様にmenuItemに
普通のspriteを追加しても問題なく機能した。
—————————————————————————————
Sprite* txtHome = Sprite::create(“images/txt_home.png”);
txtHome->setPosition(winSize.width/2, btnHeight/2);
menuHome->addChild(txtHome);
————————————————————————————-
 

透明度の設定

透明度の設定はsetOpacityを利用する。注意点としては0〜255の値を取ると言うこと。
————————————————————————————-
spHomeOFF->setOpacity(0);
————————————————————————————-
 

ブレンドの設定

結局今回は利用しなかったけれど、参考になりそうなページをメモ。
photoshopのオーバーレイのような効果はデフォルトではなさそう。オーバーレイは乗算と
スクリーンの組合せだから仕方ないと思いつつもメジャーなのだから用意して欲しい。
→参考:Cocos2d-x で BlendFunc
 

スプライトシート作った

利用したのはshoeBoxというフリーのアプリ。以下のサイトが詳しいです。
→参考:これぞ神ツール!ゲーム制作に役立つShoeBoxというフリーツールが便利すぎる
スクリーンショット 2014-08-26 23.39.44
スプライトシートの利用方法は以下のサイトが詳しいです。
→参考:SpriteFrameCacheとSpriteBatchNode
 

SpriteBatchNodeと透過png

SpriteBatchNodeで透過pngを表示したら、透過部分が黒くなる…。SpriteBatchNodeを
利用しないで同じものを表示すると正常なので、SpriteBatchNodeの問題だと思うのだけれど…。
色々試行錯誤したけれど回避方法が分からない。今回はパネル15枚で固定なのでSpriteBatchNode
は使わないことにした。
スクリーンショット 2014-08-27 12.27.17
今回はそんな感じ。
 
 
 

coco2d : とりあえずデザイン

15パズルのデザインはだいぶ前に作成してあったので、合間の時間に少し修正して
背景として組み込んでみました。

iOS7っぽいデザイン

これからはcocos2dの勉強を兼ねて15パズルをアレンジした脳トレを作成していきます。
デザインは電車の中で大人が遊んでいても知的に見えそう?なのを目指してます。
color

レイアウトを下揃えで配置したい

私がこれまで作成してきたjQueryアプリはデザインを下揃えにして、縦に短い機種では
タイトル部分を表示しないようなデザインにしてきました(仕事ではあり得ない仕様ですね)。
 
cocos2dでも同じようにしたいので調査開始。
ちなみにdesignResolutionSizeはiPhone5に合わせるようにしました。
———————————————————————————–
static cocos2d::Size designResolutionSize = cocos2d::Size(640, 1136);
———————————————————————————–
 
予想では「align」等のキーワードで下揃えができそうな気がしていたのですが見つかりません。
ですが色々なサイトを回ってgetVisibleOriginという関数に出会いました。
この関数は「見えている範囲の左下(原点)の座標」を返します。これを利用して背景画像を
配置する時に以下の様に記述。
———————————————————————————–
Size winSize = Director::getInstance()->getWinSize();//—画面サイズを取得
Sprite* pBG = Sprite::create(“images/back_blue.jpg”);//—背景スプライト作成
Point origin = Director::getInstance()->getVisibleOrigin();//—端末左下の座標を取得
pBG->setPosition(Vec2(origin.x + winSize.width/2, origin.y + winSize.height/2));
———————————————————————————–
結果、以下の様にiPhone5ではタイトルを表示、それ以前ではタイトル部を非表示に
レイアウトすることができるようになりました。
スクリーンショット-2014-08-26-20.10
iPadはアスペクト比がiPhoneと大きく異なるのでjQueryアプリ同様に対応外にしました。
→参考:ユニバーサルアプリを iPhone のみの対応にする

cocos2d : 物理エンジン

前回の記事でサンプルを諦めましたが、もう少し頑張ってみました。
 

chipmunk

もう少し頑張ろうと思ったのは、以下のサイトを発見したのが切欠。
→参考:Cocos2d-x3.0を使って3日でFlappyなんちゃらが作れる作り方
上記のサイトに乗っているソースを参考ににサンプルを書き換えてみたら動いたのです!
 
しかしv2からv3への書き換えという感じではなく。本書で用意した物理空間で利用する
様々な処理は全く必要としませんでした(Config.hやPhysicsSprite.h等も)。
物凄くシンプルに機能を実現することができました。
 
なのでキーとなっているcreateWithPhysicsを調べたら、本書で利用しているbox2dでは
なくChipmunk(シマリス)という2D物理エンジンを利用するための仕組みらしいです。
cocos2dではv3以降ではChipmunkを推していくらしいです。
 
なので、次はcreateWithPhysicsをキーに検索を進めると以下のサイトを発見。
これを参考に本書のサンプルで地面にリンゴがぶつかるところまでを作成しました。
→参考:cocos2d-xで引っぱりゲーを作ってみる
 
スクリーンショット 2014-08-24 19.51.45
地面は分かりやすく別のスプライト(黒い矩形)を用意して実験しています。
このままサンプルを進めて7章のサンプルと同じものを作成する事もできると思うのですが
やはり物理エンジンには(現時点で)あまり興味を持てないので。ここで本書を利用した
学習はやめようと思います。
 
購入した本はもう一冊有りますが、そのまえにjavaScriptで作成しようと思っていた
脳トレ系のゲームをcocos2dで作成してみようと思っています。
ゲームは15パズルを利用したシンプルなゲームなのでjavaScriptゲームの第一弾として
考えていたのですが、途中で2048にハマって、そのクローンを作成したためお蔵入りして
いたのです。
 
 
 

cocos2d-x ver3.2 : 7章5項〜6項、そして諦める…

7.5 重力のある世界を作成する

この項は問題なく修了。
 

7.6 林檎や虫に物理的な構造を与える

v3への変換ができません。エラーが消えないのです…。
私が作成したいゲームに物理エンジンは必要ないので諦めて、
もう少し情報が増えてから再挑戦しようと思います。
 

アフィン変換で足止め

本書p323のアフィン変換の処理(nodeToParentTransform)をver3に書き換えるのに
時間がかかった…。xcodeのお助け機能を利用していわれるがままに以下の様に書き換えた。
——————————————————————
・m_obAnchorPointInPoints → _anchorPointInPoints
・m_sTransform → _transform
・その他ccの削除
——————————————————————
しかし最後の2行のエラーが消えない。
——————————————————————
_transform = AffineTransformMake(c, s, -s, c, x, y);
return _transform;
——————————————————————
エラーの内容は上の処理が「No vialble overloaded ‘=’」そして下の段が
「No vialble conversion from ‘cocos2d::Mat4′ to ‘cocos2d::AffineTransform’」
nodeToParentTransform関数の返す値はAffineTransformという構造体にしなければ
ならなそうで、_transformはMat4(行列)という型らしいのでエラーになっている。
なので、以下の様にまとめたらエラーが消えた。
——————————————————————
return AffineTransformMake(c, s, -s, c, x, y);
——————————————————————
落ち着いて考えると以下の変換が間違っているのだと思う。m_sTransformは
alt+クリックで検索しても何も出てこないので変換する必要はない普通の変数?なのかな。
——————————————————————
・m_sTransform → _transform
——————————————————————
でも、とりあえずアフィン変換のエラーは無くなった。
 

実装部分のエラー

本書p324の下のソース6行目で処理でエラーになる。
——————————————————————
pApple->initWithTexture(appleBatchNode->getTexture());
——————————————————————
以前ver3でCCが外れたためPhysicsSpriteが既存のPhysicsSpriteと被ったのかな?
6章でAnimation.hをMyAnime.hに変更したようにPhysicsSpriteをMyPhysicsSprite
と変えたけれど、同じようにエラーになります。
エラーの内容は「initWithTexture is a protected member of ‘cocos2d::Sprite’」
initWithTextureはspriteの関数だからPhysicsSpriteからは利用できないよ!
ということだと思うのですが、PhysicsSpriteはSpriteを継承しているのだから
利用できても良いのでは?色々調べたけれど同じ様な症例がなく手詰まり。
box2Dには余り興味がないので、もう少し情報が増えてから再度学ぶことにしました。
 
その他メモ
PTM(pixel per meter):32PTMなら32ピクセルが1メートルとなる
 
そんなこんなで、cocos2dの参考書を利用した学習はお終い。
書き溜めた記事もなくなったので、また週一くらいの更新ペースに戻ります。
 
 
 

cocos2d-x ver3.2 : 7章4項

7.4 林檎や虫を表示

今回もキャッシュ関連の関数が出てきました。私はjavaScriptでは対応できないような、
アクション性の高いゲームをcocos2dで作成したいので、この辺はあとでサンプルを自力で
作成する必要性を感じています。スプライトを考えなしで大量表示するとアプリがクラッシュ
するそうです。色々調べている時に、アプリの高速化について有用なサイトがあったのでメモ
→参考:Cocos2d-xでiPhone&Androidアプリ開発記10 アプリ高速化

SpriteBatchNode

使い方は以下の様な感じ。rectを設定する必要がないので、前回登場したSpriteFrameCache
よりも簡単に利用できそう。しかし重ね順(Z値)の変更ができないそうです。
→参考:画像を高速で表示する
—————————————————————————-
appleBatchNode = SpriteBatchNode::create(“apple.png”);
—————————————————————————-
でもってSpriteBatchNodeからスプライトを作成する記述が以下の通り。
—————————————————————————-
Sprite* pApple = Sprite::createWithTexture(appleBatchNode->getTexture());
—————————————————————————-
SpriteBatchNodeからgetTextureでテクスチュアを取得してスプライトを作成。
???…これってTextureCacheと何が違うの?
→参考:CCTextureCacheとCCSpriteFrameCacheを理解してキャッシュを自在にあやつる

SpriteBatchNodeの機能

SpriteBatchNodeの機能が良く分からないので色々調べました。一番分かりやすいサイトは
以下のサイト。「同じスプライトをまとめて表示するノード」という感じです。
→参考:CCSpriteBatchNode? CCSpriteFrame? CCSpriteFrameCache?
だとすると、本書のサンプルではSpriteBatchNodeからテクスチュアを取ってきて
それを利用してスプライトを作成するのは違うような気がします。

SpriteBatchNodeの本来の使い方?

ということで、さらに調べると以下のサイトが見つかりました。
→参考:SpriteFrameCacheとSpriteBatchNode
このサンプルではthis(本書のサンプルならレイヤーを継承したGameScene)に
SpriteBatchNodeを追加して、SpriteBatchNodeにspriteを追加しています。
こういう使い方ならTextureCacheとは全く異なることが分かります。
関係性としては以下のような構造。
—————————————————————————-
this ← SpriteBatchNode ← sprite
—————————————————————————-
本書サンプルを見直すとp308下のソース6行目に、きちんとthisにSpriteBatchNodeを
addしていました!
—————————————————————————-
05 appleBatchNode = SpriteBatchNode::create(“apple.png”);
06 this->addChild(appleBatchNode);
—————————————————————————-
でも本書のサンプルではSpriteBatchNodeにスプライトを追加するのではなく、
SpriteBatchNodeから取得したテクスチュアで作成したスプライトをthisに追加しています。
これでも効果あるの?
—————————————————————————-
// リンゴを表示
Sprite* pApple = Sprite::createWithTexture(appleBatchNode->getTexture());
pApple->setPosition(point);
this->addChild(pApple, kZOrder_Apple, kTag_Apple);
—————————————————————————-
以下のサイトでは、シミュレータに表示される情報で、描画回数を測定する記述があります。
v3で表示のされ方が変わりましたが、v3にもあるので確認したところ。
上記の記述でも問題ないようです。
→参考:Cocos2d-x:同じ画像を使い回して描画する
でも確認のため、以下の様にthisをappleBatchNodeに書き換えて試してみた。
—————————————————————————-
this->addChild(pApple, kZOrder_Apple, kTag_Apple);

appleBatchNode->addChild(pApple, kZOrder_Apple, kTag_Apple);
—————————————————————————-
問題なく機能した。thisを利用するとappleBatchNodeを意識せずに利用できるけれど
意識してappleBatchNodeを利用した方がよいのかな?とりあえず、本書の記述がthis
ではなくてappleBatchNodeだったら混乱せずに理解できたのに。と思いました。
ちなみにthisとappleBatchNodeが異なるものであることはCCLOGで確認しました。

SpriteFrameCacheとの連携

SpriteBatchNodeに追加できるスプライトはSpriteBatchNodeで最初に指定した画像しか
利用できないので、前回学んだSpriteFrameCacheを利用して異なる画像
(実際はまとめられた1枚のスプライトシート)をSpriteBatchNodeに利用するのが
良いらしいです。
→参考:テクスチャアトラスとBatchNode
→参考:SpriteFrameCacheとSpriteBatchNode
 

スケジュールの時間間隔を段々短く

本書p310の最下段playingGame関数では、スケジュールに関して不思議な処理をしている。
—————————————————————————-
・最初にスケジュールを停止して、最後にスケジュールを再設定
—————————————————————————-
これはスケジュールで設定した数値を「動的に変更」する事ができないための処理らしいです。
なんか奥の方に手を突っ込んで無理矢理変えることもできそうな気がしますが、たぶん
良くないことなのでしょう。
以下のサイトではObjective-Cの文法だけど本書と同じ仕組みで時間を変更しています。
→参考:Cocos2d schedule interval decreased
 

ランダムを再設定してみた

サンプルを再生すると、林檎や虫が以下の様に表示される。なんだか表示される場所が
ナナメになって規則性があるの?って感じ。
スクリーンショット 2014-08-22 20.31.51
でもソースを確認すると以下の様に1つのランダムの値をx,yの両方で利用していた。
たぶんこれが原因。
—————————————————————————-
int random = rand();//—-位置をランダムで設定
int locX = random % 80 + 10;
int locY = random % 30 + 50;
—————————————————————————-
なので、以下の様にYは別のランダムを利用するように変更しました。
—————————————————————————-
int random = rand();//—-位置をランダムで設定
int locX = random % 80 + 10;
random = rand();//—-ランダムを再設定してみた
int locY = random % 30 + 50;
—————————————————————————-
その結果、以下の様にきちんとランダムになりました。
スクリーンショット 2014-08-22 20.38.13
そんな感じで7.4は修了。
 
 
 

cocos2d-x ver3.2 : 7章3項

フレームアニメーションの方法

CCArrayをVectorに置き換えることに慣れてきました。でもテクスチャキャッシュで、
また躓いたので再度メモ。テクスチャキャッシュはv3ではDirectorの管轄となっている。
———————————————————————————-
Texture2D *texture = TextureCache::sharedTextureCache()->addImage(fileName);

Texture2D *texture = Director::getInstance()->getTextureCache()->addImage(fileName);
———————————————————————————-
→参考:cocos2d-x 2.x → 3.0

SpriteFrameについて

よく利用する画像はキャッシュに入れて利用し、GPUへの負荷を軽減させる。本書のサンプルでは
まずSpriteFrameCacheのインスタンスを作成してcacheと命名。
本書302のソース6行目は以下の様に書き換えました。
———————————————————————————-
06 SpriteFrameCache *cache = SpriteFrameCache::getInstance();
———————————————————————————-
次にSpriteFrameCacheに設定するSpriteFrameを作成します。本書のサンプルでは14〜16行目
———————————————————————————-
14 Texture2D *texture = Director::getInstance()->getTextureCache()->addImage(fileName);
15 Rect bounds = Rect(0, 0, texture->getContentSize().width, texture->getContentSize().height);
16 frame = SpriteFrame::createWithTexture(texture, bounds);
———————————————————————————-
まず14行目で指定した画像ファイルからテクスチャ(2D)を作成しtextureと命名。
15行目で画像ファイルの矩形サイズ(Rect型)を取得してboundsに代入。
そして16行目で14行目のtextureと15行目のboundsを利用してSpriteFrameを作成。
アニメは配列(Vector)にSpriteFrameを入れて作成する。
そして19行目で作成したSpriteFrameをVectorのanimFrameに追加。
———————————————————————————-
19 animFrames.pushBack(frame);
———————————————————————————-
SpriteFrameにすべてのspriteを追加したら、createWithSpriteFramesを利用して
SpriteFrameからActionを作成。本書では22行目の処理。
———————————————————————————-
22 Animation* animation = Animation::createWithSpriteFrames(animFrames, 0.1);
———————————————————————————-

ここまでの疑問

ここまでの流れではSpriteFrameCacheにspriteFrameを記憶させる記述が無い。
キャッシュからSpriteFrameを取得する記述は以下の様にfile名をキーにして取得している。
———————————————————————————-
11 SpriteFrame *frame = cache->getSpriteFrameByName(fileName);
———————————————————————————-
SpriteFrameを作成しているのは以下の部分で、キーを設定しているようには見えないし
(キーはテクスチュアを作成する時に利用している)、前後にSpriteFrameCacheに
追加しているような記述もない。
5章でも学んだTextureCacheは以下の様にTextureCacheにaddImageで画像を
追加している記述があるのに。SpriteFrameでは必要ないの?
———————————————————————————-
14 Texture2D *texture = Director::getInstance()->getTextureCache()->addImage(fileName);
———————————————————————————-
調べたけれど良く分からない。とりあえずtextureを作成した時に利用したfileNameを
キーにキャッシュからspriteFrameを取得できる事を覚えておこう。

アニメを停止する箇所は?

続いてGameScene.cppでアニメを再生している箇所を確認。再生している部分は
本書p304のソース10行目の以下の処理。
———————————————————————————-
pCat->runAction(action);
———————————————————————————-
しかし停止している部分は?と思ったのですが、ソースを追って以下の様な仕組みである
ことを理解しました。
———————————————————————————-
・指が移動している間(onTouchMoved)はアニメを再生する。
・アニメがすでに再生されている場合は何もしない(6行目のif文によりチェック)
・アニメはそもそも3コマだけなので、3コマ再生したら勝手に止まる。
———————————————————————————-
Flashで似たような仕組みを作成する時はマウスアップのタイミングでアニメを停止させたり
していたので、てっきりcocosも同じだと勘違いしていました。
このことは、アニメの再生速度を0.1から1.0に変更すると確認できます。指を離しても
3コマ(3秒)はアニメが再生されます。

Rectが必要な理由

なぜspriteFrameの作成には矩形情報が必要なのか調べると、スプライトシートや
テクスチャアトラスという仕組みを利用するためらしいです。以下のサイトが詳しいです。
→参考:CCTextureCacheとCCSpriteFrameCacheを理解してキャッシュを自在にあやつる
 
上記のサイトでは、私が疑問に感じていた「SpriteFrameCacheへの登録」も説明されて
います。しかし本書のサンプルには該当する記述はありません。
ですが、内容を元に推測すると以下の様な感じになっている?
———————————————————————————-
・SpriteFrameを作成する時に自動的に登録される。
・キーを指定しない場合はファイル名がキーとして割り当てられる
———————————————————————————-
フレームアニメは利用頻度が高いので、本書のサンプルを学び終えたら色々試してみようと思う。
 
 
 

cocos2d-x ver3.2 : 7章2項

7.2スワイプによる猫の移動

この章では新しい事を結構学びました。

タッチポイント:左下が原点にならない!

onTouchBeganでタップされたポイントを取得しているので、以下の様にログでポイントを
表示するようにしました。
—————————————————————————-
Point loc = pTouch->getLocation();
CCLOG(“x:%f, y:%f”, loc.x, loc.y);
—————————————————————————-
この結果を踏まえたタップについての仕様をメモしておこうと思います。
・返される座標の値はdesignResolutionSizeで設定した座標系のものになる。
 このとき画面サイズによっては上下が見切れてしまうため、画面の左下が必ずしも
 原点(0.0)になるわけではない
(OpenGLの座標系は左下が原点)。
実際にretinaのシミュレータで左下をタップすると約(0,100)となります!
iPhone5は縦横比が1:0.56なので、これを1024の幅に当てはめると、高さは577位になります。
しかしdesignResolutionSizeで高さは768に設定されているため、上下合わせて約200pxが
隠れていることになります。ですから左下をタップして約(0,100)になるのは計算通りという
感じです。しかし、これはちょっと嫌な感じです。cocos2dの学習が一通り住んだら、まずは
コンテンツの表示について試行錯誤し、左下をきちんと(0,0)にする方法を見つけたいです。

タップイベントの有効/無効

本書p298の上のソース7行目。onTouchBeganでfalseを返せばタップを無効にできる。
本サンプルの場合はonTouchMovedが処理されない。onTouchBeganだけ返値を設定しないと
行けない理由は、このようにタップの有効/無効の設定があるため。
—————————————————————————-
return pCat->boundingBox().containsPoint(loc);
—————————————————————————-
ちなみに上記の処理は、pCat->boundingBox()で猫の矩形の範囲を取得し
containsPoint(loc)でloc(タップしたポイント)が猫の矩形の範囲内にあるかをチェック
しています。範囲内にあればtrueになるのでタップが有効となります。

絶対値の取得

この項ではv3への書き換えが余り無かったので、本書p298下のソース11~12行目のif文を
絶対値を利用した記述に書き換えてみた。
—————————————————————————-
if (loc.x – pTouch->getPreviousLocation().x > threshold ||
pTouch->getPreviousLocation().x – loc.x > threshold) {

float dist_x = std::abs(loc.x – pTouch->getPreviousLocation().x);
if (dist_x > threshold) {
—————————————————————————-
絶対値の取得はjavaScriptと同じabsを利用しますがC++ではMathクラスではなくstdクラス
なのでstd::abs()となるそうです。調べている途中にfloat用のfabsというのを見つけたの
ですがC++ではfabsではなくabsでよいそうです。
→参考:When do I use fabs and when is it sufficient to use std::abs?
あと絶対値とは関係有りませんが、cocos2dのタッチイベントでは、前回の引数で送られてきた
値がgetPreviousLocationに記憶されているため、前回の値が必要な時に変数を別途用意する
必要がないのは少し便利かも。

コンストラクタ?

本書p297では5章、6章で利用しなかったコンストラクタというものが登場します。
言葉自体は良く効くのですが、あまり良く理解していません。というか、これまでは
AppDelegate.cppから実行しているGamaSceneのscene関数が、コンストラクタなのかな?
と思っていました。以下のサイトによればコンストラクタはオブジェクトを作る時に実行され
メンバ変数の初期化を行うところらしいです。
→参考:第3章 コンストラクタ
これまではinit関数の中で変数を初期化していましたが、正式にはコンストラクタを利用する
のが正しいのだそうです。でもって初期化の方法には2種類あり、推奨されるのは本書のサンプル
で利用している:(コロン)を利用した構文の方だそうです。
→参考:C++のコンストラクタにある「:(コロン)」について

CREATE_FUNCのおさらい

cocos2dのクラスは大抵インスタンスを作成する時にはcreate関数を利用する。しかし
独自クラス(本書ではGamaScene等)の場合は利用できない。独自クラスでcreate関数を
利用できるようにするためにCREATE_FUNCを使う必要がある。
→参考:C++初心者が【cocos2d-x】を勉強する2回目のページ中程
これによってクラスがcreateされた時にinit関数が実行される。本書のサンプルでは
AppDelegate.cppから実行されるscene関数内でcreateしている(このタイミングで
initが実行される)

コンストラクタが実行されるタイミング

ではコンストラクタは何時実行されるの?CCLOGをあちこちに書いてコンストラクタが実行
される場所を探った。結果、CREATE_FUNCを定義している部分(ccPlatformMacros.h)でした。
CREATE_FUNCでは以下の様にnewしているところがあり、ここでインスタンスを作成しています。
※newでインスタンスを作成するのはjavaScriptも同じ。
—————————————————————————-
__TYPE__ *pRet = new __TYPE__(); \
—————————————————————————-
CREATE_FUNCは必須というわけでななく、インスタンス作成時のお決まりの処理を
やってくれる処理なのようです(メモリまわりの処理とかもしてくれているらしい)。
 
 

cocos2d-x ver3.2 : 7章1項

7.1 プロジェクトの準備

この項では新しい事は学びませんでしたが、
これまで学んだ事を少し忘れて戸惑った部分をメモしておきます。

createSceneはsceneに

AppDelegate.cppにおいてデフォルトではシーンを作成する関数名はcreateSceneとなっている
しかし過去のヴァージョンではsceneとなっていたようで、本書ではsceneと命名されている。
なのでAppDelegate.cppでは以下の様に関数名も変更しないと行けない。
—————————————————————————
auto scene = HelloWorldScene::createScene();

auto scene = GameScene::scene();
—————————————————————————

winSizeとframeSize

マルチレゾリューションに関する部分でwinSizeとframeSizeが混乱するのでメモ。
—————————————————————————
frameSize→実機の実際の解像度
winSize→setDesignResolutionSizeによって設定された解像度
—————————————————————————
→参考:画面サイズ、ウインドウサイズについて
本書のサンプルではAppMacros.hで以下の様に設定しているため、winSizeは(1024, 768)
となる。しかし、この値を実際に利用しているのはAppDelegate.cpp。
—————————————————————————
static cocos2d::Size designResolutionSize = cocos2d::Size(1024, 768);
—————————————————————————
そして、注意点としてはAppDelegate.cppにおいてResolutionPolicyをNO_BORDERに
しているため上下のデザインが隠れてしまう。
—————————————————————————
glview->setDesignResolutionSize(designResolutionSize.width, designResolutionSize.height, ResolutionPolicy::NO_BORDER);
—————————————————————————
frameSizeを取得する部分をv3.2に変換することは6章で学んだが、ややこしいので再度メモ。
—————————————————————————
CCSize viewSize = CCEGLView::sharedOpenGLView()->getFrameSize();

Size viewSize = Director::getInstance()->getOpenGLView()->getFrameSize();
—————————————————————————

色の指定

色を指定している部分は以下の様に書き換えました。
—————————————————————————
m_pTimeLeft_Tenths->setColor(ccBLACK);

m_pTimeLeft_Tenths->setColor(Color3B::BLACK);
—————————————————————————

ラベルの表示法について思うこと

ここで学ぶサンプルでは残り時間や得点を桁毎に別のラベルを作成しています。本書では
文字の間隔を調整するためと説明されていますが、そのために記述するソースが凄く多く
なっています。ver3では文字間を設定できるようですが、v2ではできなかったのでしょうか?
→参考:Cocos2d-x3.0rc2でのLabelの使い方
 
最後にキャプチャを。
スクリーンショット 2014-08-18 22.47.26
 
 
 

cocos2d-x ver3.2 : eclipseが壊れた

Androidへのビルド

もう色々大変…。

Android.mkの修正

6章のサンプルをeclipseでビルドしようとしたらエラーになった。
本書でもeclipseの場合はproject/jni/Android.mkを修正する説明がありますが
6章では5章とことなり複数のクラスファイルを利用しているので以下の様に書き換えました。
※調べている途中で有用なサイトに出会ったのでメモ。以下のページの下の方で
 Android.mkを便利に書き換える方法があります。
→参考:cocos2d-x 3.0 Final(正式版、安定版)を使ってみる(導入編)
————————————————————————-
LOCAL_SRC_FILES := hellocpp/main.cpp \
../../Classes/AppDelegate.cpp \
../../Classes/ScrollLayer.cpp \
../../Classes/TitleScene.cpp \
../../Classes/MyAnime.cpp \
../../Classes/GameScene.cpp
————————————————————————-
しかし、それでもエラーが治りません。エラーの内容からcocos2d本体に問題がありそう
だったのでlibcocos2dを疑う。これがv3ではなくv2なのでは?
 
なので、Eclipseの左カラムのPackageExplorerにある以下のlibcocos2dをv3に変更する
方法を調べるも分からない。
スクリーンショット 2014-08-13 0.22.18
 
そして行き詰まった勢いで削除してしまう!。するとv2で作成したプロジェクトはエラーが
発生するがv3で作成した5章のサンプルはエラーにならない。ビルドもできる…。
 
PackageExplorerにあるlibcocos2dはv2でv3は別の仕組みなの?
そしてv3とlibcocos2dで検索して調べると以下のサイトが見つかりました。
→参考:cocos2d-x v3.2 rc0のAndroidプロジェクトをEclipseで正しく(たぶん…)ビルドする
上記ページの中程にv3.2ではlibcocos2dへのパスが間違っている!という記事が…。
これを修正したらビルドできました!。
ver3ではlibcocos2dは各プロジェクト内にあるのですね。
 

5章でのメモ忘れ

この作業をしている中で、5章のサンプルでも修正したことを思い出しました。こんな重要な
ことをメモし忘れているなんて…。過去の該当記事を確認するとメニューのコールバック設定
で悪戦苦闘していたタイミングのようです。こっちの問題に集中していたのでメモし忘れて
いたのかも…。ともあれ、
今回はきちんとメモして、印象にも残ったので次は大丈夫だと思います。
 

最終的にeclipseが壊れた…

最後に実機(is11t)でスクリーンショットを取ろうと思ったら、転送の途中でeclipseが
フリーズ…。でもってアプリを強制修了。アプリを再起動しても実機に転送できずエラー。
変なキャッシュ?が残っているのかな、と思いeclipseのクリーン起動というのを試す。
→参考:MacのEclipseをclean起動するコマンド
そしたら、さらに悪化した…。なんだか色々なパスが切れたのか?
 
色々試行錯誤して、最終的にはアプリアイコンをダブルクリックしてもスプラッシュ画面
すら出てこないレベルに…。
 

再インストール

もう一度eclipseを再インストール(verはJUNO with ADT)。しかしダメ。setup.pyで
設定した情報をviエディタで変更したけれど効果なし。eclipseは7月に最新版のLUNAが
出ているのでこれをインストールしたけれどだめ。javaScriptのコンテンツは問題なく
ビルドできるのにcocos2dのコンテンツだけダメ。C/C++に関する部分がダメっぽい。
あと以下の事をメモ。
—————————————————————–
eclipseをクリーン起動するとjavaScriptのコンテンツもビルドできなくなる…
—————————————————————–
スクリーンショット 2014-08-19 18.13.08←3種類のEclipse
 

Mac Book Proにインストール

Mac Book Proにインストールして試してみた。javaScriptのコンテンツは問題なく
ビルドできる(この環境は大切なのでクリーン起動はしないと決意)。しかし
cocos2dのコンテンツはビルドできない…。内容的には以下の質問サイトと同じっぽい
のですが、解決できません。
→参考:cocos2d-x 3.2 project cause eclipse cdt’s error
 

そして諦める

cocos2dでアプリを作成できるレベルになるのはまだ先なので、とりあえずAndroid環境は
わすれてxcodeだけで7章に進むことに。7章が終わってから、また調べようと思います。