Cocos2d-x ゲーム制作

ゲーム制作 Cocos2d-x関連 第4回 「画面タッチに反応して画像を出そう」

投稿日:2016年7月2日 更新日:

画面を眺めててもゲームにはならないよ。画面タッチしたいんだけど!

 

前回までで画像を表示できるようになりましたが、コレではまだゲームとは言えませんね。

今回と次回で、ボールをタップしたら好きな角度で動かせるようにしてみましょう。

 

ボール移動の仕様

ボール移動操作の大きな仕様は以下の3つです。

  1. ボールをタップすると矢印画像を表示する。
  2. そのままタップを移動することで、矢印画像を360度回転できる。
  3. タップを離すとボールが指定された角度で移動する。矢印画像は削除する。

 

まずアプリがタップを検知できるようになるために、前準備として以下のプログラムを記述しておく必要があります。

 

HelloWorldScene.h


// touch
virtual bool onTouchBegan(cocos2d::Touch* pTouch, cocos2d::Event* pEvent);
virtual void onTouchEnded(cocos2d::Touch* pTouch, cocos2d::Event* pEvent);
virtual void onTouchMoved(cocos2d::Touch* pTouch, cocos2d::Event* pEvent);

 

HelloWorldScene.cpp HelloWorld::init

// タップイベントを取得する
auto listener = EventListenerTouchOneByOne::create();
listener->onTouchBegan = CC_CALLBACK_2(HelloWorld::onTouchBegan, this);
listener->onTouchEnded = CC_CALLBACK_2(HelloWorld::onTouchEnded, this);
listener->onTouchMoved = CC_CALLBACK_2(HelloWorld::onTouchMoved, this);
this->getEventDispatcher()->addEventListenerWithSceneGraphPriority(listener, this);

 

 

・「onTouchBegan」

cocos2dxのメソッドで、タップした瞬間に1回だけ実行されます。

・「onTouchMoved」

cocos2dxのメソッドで、タップして移動している最中に何回も実行されます。

・「onTouchEnded」

cocos2dxのメソッドで、タップを離した瞬間に1回だけ実行されます。

 

 

これらはイベントリスナーと呼ばれるものです。お決まりのプログラムなので、今回のような単純なタップイベントを取得する際は毎回コピペして使用できます。

 

上記を記述したらタップ処理の下準備は完了です。タップに反応するプログラムを記述していきましょう。

 

1.タップすると矢印画像を表示する。

それではプログラムを記述していきましょう。

 

HelloWorldScene.h

// キャラクター関連
cocos2d::Sprite* _ball; // プレイヤーが操作するボール
cocos2d::Sprite* _allow; // ボールの侵攻方向を表す矢印画像

float _degree = .0; // ボールの進行方向のための角度

// ドロップ接触、プレイヤー攻撃関連
float getDegree(cocos2d::Vec2 o, cocos2d::Vec2 t); // 2点間の角度を取得する

 

 

また、resourcesに矢印の画像を追加してください。

画像

 

 

 

第2回でHelloWorld::init内に記述したボール変数を以下のように変更してください。(ハイライト部分)

HelloWorldScene.cpp HelloWorld::init

// プレイヤー(ボール)
_ball = Sprite::create("ball.png");
_ball->setPosition(Vec2(visibleSize.width/2, visibleSize.height/2));
this->addChild(_ball, 1, 0);

 

ボール変数を変更する理由ですが、複数のメソッドで利用するためにクラス変数としたいからです。

 

 

HelloWorldScene.cpp HelloWorld::onTouchBegan

bool HelloWorld::onTouchBegan(Touch* pTouch, Event* pEvent){

    // タップした座標を取得
    Vec2 touchPoint = convertTouchToNodeSpace(pTouch);
    // タップした座標がボール画像の中に入っているかどうかを判断
    if(_ball->boundingBox().containsPoint(touchPoint)){
        // タップした座標とボール画像の座標の二点間の角度の取得
        _degree = getDegree(_ball->getPosition(), touchPoint);

        // 矢印オブジェクトの角度を設定
        _allow = Sprite::create("allow.png");
        _allow->setPosition(Vec2(_ball->getPosition().x, _ball->getPosition().y));
        _allow->setRotation(_degree);
        this->addChild(_allow, 0, 7);

        return true;
    }
    return false;
}

 

 

それではonTouchBegan内のプログラムを解説してきます。

1.タップした座標を取得

この1行でタップポイント(X座標、Y座標)を取得します。

 

 

2. タップポイントがボール画像内であるかどうかの判定

ボールにタップしたら矢印画像を出したいので、タップした座標がボールないにあれば処理を続行します。

・boundingBox().containsPoint()

cocos2dxのメソッドで、引数に座標を入れることでオブジェクト内にポイントが存在するかどうかを判定します。

 

 

3.角度の取得

・getDegree

自作のメソッドです。説明は後述します。

 

 

4.矢印オブジェクトの角度を設定して画像表示

画像表示自体は第2話で行ったやり方同じです。ただし、setRotation()で画像を回転させています。

 

・setRotation

cocos2dxのメソッドで、設定した角度分画像を回転させます。他にも画像に色々なアクションを起こすためのメソッドが用意されています。

 

角度の取得

角度の取得については上記のとおり、getDegreeメソッドで行います。下記のgetDegreeメソッドを追記してください。

 

 

HelloWorldScene.cpp HelloWorld::getDegree

float HelloWorld::getDegree(Vec2 o, Vec2 t){
    float radian;
    radian = ccpToAngle(ccpSub(o, t));// 角度をRADIANで取得
    float degree = CC_RADIANS_TO_DEGREES(radian);
    degree *= -1;
    degree -= 180;
 
    return degree;
}

 

 

・ccpToAngle

cocos2dxのメソッドで、二点間の角度をRADIANで取得します。

・CC_RADIANS_TO_DEGREES

cocos2dxのマクロで、RADIAN角度をDEGREE角度に変更します。

 

「cppToAngle」、「CC_RADIANS_TO_DEGREES」で角度を取得できますが、予め用意した矢印画像に対して適切な角度に調整したかったため、このgetDegreeメソッドを用意しました。

 

2.そのままタップを移動することで、矢印画像を360度回転できる。

続いて、下記プログラムを追記しましょう。

 

HelloWorldScene.cpp HelloWorld::onTouchMoved

void HelloWorld::onTouchMoved(Touch* pTouch, Event* pEvent){
    Vec2 touchPoint = convertTouchToNodeSpace(pTouch);

    // 角度の再取得
    _degree = getDegree(_ball->getPosition(), touchPoint);
    // 矢印オブジェクトの角度を更新
    _allow->setRotation(_degree);
}

 

 

1.角度の再取得

移動した先のタップポイントでgetDegreeを使用し、角度を更新します。

 

 

2.矢印オブジェクトの角度を更新

再びsetRotationで画像の角度を更新します。

 

 

タップを離すとボールが指定された角度で移動する。矢印画像は削除する。

ここでは矢印画像の削除処理のみを追加しましょう。ボールの移動は次章で行います。

下記のプログラムを追記してください。

 

HelloWorldScene.cpp HelloWorld::onTouchEnded


void HelloWorld::onTouchEnded(Touch* pTouch, Event* pEvent){

    if(_allow != nullptr){
        _allow->removeFromParent();
        _allow = nullptr;
    }
}

 

・removeFromParent()

cocos2dxのメソッドで、表示済みの画像を消すことができます。

ただし、タップを離すたびにこのメソッドを実行してしまうと二重、三重に画像を消そうとしてしまうので、_allowインスタンスが存在している場合のみ消すようにしておきます。

 

シミュレータの起動

ここまででいつものようにシミュレータを起動してみましょう。プログラムの記述ミスがなければビルドが成功してシミュレータが立ち上がるはずです。

4_sc_simu

 

うん、タップすると無事矢印が出て、くるくると動かせますよね。

次回へ続きます!

 

次回

第5回 「ボールを動かそう」

 

PrainGoogleAdSense

PrainGoogleAdSense

-Cocos2d-x, ゲーム制作
-,

執筆者:


comment

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です

関連記事

アプリ 購入画面

Cocos2d-x SDKBoxを使ってアプリ内課金をするやり方 プログラム実装~実機テストまでの13の手順

この記事では、Cocos2d-xのSDKBoxを利用したiOSアプリ内課金のプログラム実装から実機テストのやり方まで、一連の流れで説明します。     アプリ課金の実機テストを、実 …

Cocos2d-x iOS アプリ名(アプリのアイコン名)のローカライズ方法

こんにちは。akiです。 この記事ではCocos2d-xでのアプリ名(アプリのアイコン名)のローカライズについて説明します。デバイスの環境に応じて一つのアプリのタイトル名を、日本語と英語でそれぞれ表示 …

cocos2dx

Cocos2d-x クライアント側のHttpレスポンス処理

この記事は「Cocos2d-x セーブデータをサーバに送信して保存する」の続きになります。 ・第1回 : サーバにデータを保存したい理由と全体の流れ ・第2回 : クライアント側の処理とデータ送信(H …

タイムチャート

ゲーム制作 Cocos2d-x関連 第15回 「ダメージエフェクトの演出」

おそらくここが一番大変なところですが、ゲーム完成までもう一歩です!   第12回 「ボールヒットエフェクトの表示」でヒットエフェクトを表示しました。その時とやり方はほぼ同じですが、エフェクト …

エフェクト

Cocos2d-x 加算合成を利用して、背景が黒い画像をアニメーションで使えるようにする方法

アニメーションを利用してエフェクト表示するときに、以下のようなエフェクト素材を目にすることはよくあると思います。背景が透過処理されているものではなく、黒く塗りつぶされているものです。 元になる素材は「 …