Posted at

Cocos2d-x Android開発でPluginProtocolだけ欲しい

More than 3 years have passed since last update.

自分用の手順書です。

なにか抜けてたら逐次追記します。


開発環境

Cocos2d-x 3.3 rc0

NDK r9d

本稿ではCocos2d-x 3.3 rc0を使用していますが、3.0 beta2くらいの頃から使い倒している手段なので、3.xなら大丈夫だと思います。


やりたいこと

広告を表示させたり、OSのポップアップを表示させたり、外部に遷移させたりなどを行う際、本家のplugin-xが中々使いづらく、且つ開発の進捗も怪しいのでPluginWrapperだけ使いたい。

PluginWrapperはplugin-xで共通で使用されている、UIスレッドでの処理をいい感じにしてくれるコンポーネント。


下準備


plugin-xをパブリッシュ

空の状態でパブリッシュしたいので、config.shで、余計なプラグインを削除する。

パブリッシュ自体はプロジェクト個別にコピーされたcocos2dリソースからも行えるが、PluginProtocolを全プロジェクト統一して使いたい場合は、本体の方のリソースで行ったほうが良い。

$ cd cocos2d/plugin/tools/

$ vi config.sh

#define plugins array
#export ALL_PLUGINS=("flurry" "umeng" \
#"alipay" "nd91" "googleplay" \
#"admob" \
#"twitter" "weibo" \
#"qh360" "uc" \
#"facebook" "facebookads")

export ALL_PLUGINS=()
...

そしてパブリッシュ。

この際、NDK等のパスを聞かれるので適宜入力する。


$ ./publish.sh

Please input the android-ndk path:
/Users/smith/lib/ndk/
Get ANDROID_NDK_ROOT=/Users/smith/lib/ndk

Please input the andoid-sdk path:
/Users/smith/lib/adt-bundle-mac-x86_64-20140702/sdk
Get ANDROID_SDK_ROOT=/Users/smith/lib/adt-bundle-mac-x86_64-20140702/sdk

Please input the ant tool path(such as '/Users/MyAccount/tools/ant/bin'):
/Users/smith/lib/apache-ant-1.9.4/bin
Get ANT_PATH=/Users/smith/lib/apache-ant-1.9.4/bin


mkファイルを編集


Android.mk

LOCAL_PATH := $(call my-dir)

include $(CLEAR_VARS)

$(call import-add-path,$(LOCAL_PATH)/../../cocos2d)
$(call import-add-path,$(LOCAL_PATH)/../../cocos2d/external)
$(call import-add-path,$(LOCAL_PATH)/../../cocos2d/cocos)

# パスの追加
$(call import-add-path,$(LOCAL_PATH)/../../cocos2d/plugin/publish)

LOCAL_MODULE := cocos2dcpp_shared

LOCAL_MODULE_FILENAME := libcocos2dcpp

LOCAL_SRC_FILES := hellocpp/main.cpp \
../../Classes/AppDelegate.cpp \
../../Classes/HelloWorldScene.cpp

LOCAL_C_INCLUDES := $(LOCAL_PATH)/../../Classes

LOCAL_STATIC_LIBRARIES := cocos2dx_static

# .aの追加 PluginProtocol以外に使うものもついでに
LOCAL_WHOLE_STATIC_LIBRARIES += PluginProtocolStatic
LOCAL_WHOLE_STATIC_LIBRARIES += cocosdenshion_static
LOCAL_WHOLE_STATIC_LIBRARIES += cocos_network_static
LOCAL_WHOLE_STATIC_LIBRARIES += cocos_extension_static

include $(BUILD_SHARED_LIBRARY)

$(call import-module,.)

# モジュールの追加 PluginProtocol以外に使うものもついでに
$(call import-module,protocols/android)
$(call import-module,audio/android)
$(call import-module,network)
$(call import-module,extensions)


また、ndkのバージョンとかバグとかstdとかの煩雑な問題から開放されるため、私はSTLをgnustl_staticにすることが習慣になってしまっています。


Application.mk

#APP_STL := c++_static

APP_STL := gnustl_static


libPluginProtocolプロジェクトのインポートと参照の追加

Eclipseにプロジェクトをインポートした上で、プロジェクトのプロパティからlibPluginProtocolへの参照を加える

スクリーンショット 2014-12-17 16.50.39.png


antに署名の設定

今回の題目とは関係ないけど、おまけ。


ant.properties


key.alias.password=my_fantastic_app_password
key.store.password=my_fantastic_app_password
key.store=/Users/smith/keys/apk/my_fantastic_app/my_fantastic_app_key
key.alias=my_fantastic_app_key



実装

PluginWraperを使用するためには、適宜初期化する必要があります。


javaVM


main.cpp

#include "AppDelegate.h"

#include "cocos2d.h"
#include "platform/android/jni/JniHelper.h"
#include <jni.h>
#include <android/log.h>
#include "PluginJniHelper.h"

#define LOG_TAG "main"
#define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG,LOG_TAG,__VA_ARGS__)

using namespace cocos2d;

void cocos_android_app_init (JNIEnv* env, jobject thiz)
{
AppDelegate *pAppDelegate = new AppDelegate();

JavaVM* vm;
env->GetJavaVM(&vm);
PluginJniHelper::setJavaVM(vm);
}



Cocos2dxActivityとCocos2dxGLSurfaceView

ClippingNodeとか使ってると、Cocos2dxGLSurfaceViewは必然的に設定することになるんじゃないかと。


AppActivity.java

import org.cocos2dx.lib.Cocos2dxGLSurfaceView;

import org.cocos2dx.plugin.PluginWrapper;

public class AppActivity extends Cocos2dxActivity
{
@Override public Cocos2dxGLSurfaceView onCreateView()
{
Cocos2dxGLSurfaceView glsView = super.onCreateView();
glsView.setEGLConfigChooser(5, 6, 5, 0, 16, 8);

PluginWrapper.init(this);
PluginWrapper.setGLSurfaceView(glsView);

H3NativeLifeCycle.applicationDidFinishLaunching();

return glsView;
}

...
}



使い方

GameFeatなど、ContextやActivityを欲しがるSDKにはPluginWrapper.getContext() を与える。


NiceAdHandler.java

public static void initGamefeat()

{
gamefeatController = new GameFeatAppController();
gamefeatController.init(PluginWrapper.getContext());
gamefeatController.setRefreshInterval(30);
gamefeatController.activateGF(PluginWrapper.getContext(), false, true, true);
}

Viewへの追加はrunOnMainThreadで行う必要がある。

じゃないとクラッシュする。


NiceAdHandler.java

public static void showIntersticial()

{
PluginWrapper.runOnMainThread(new Runnable(){
@Override
public void run()
{
aidController.showDialog(AdController.DialogType.ON_EXIT);
}
});
}

殊の外、jniのデバッグはめんどいので、とにかくtry / catch(Exception e) でエラーメッセージを見るという残念な手法が推奨される。


ビルド

通らなかったらごめんなさい。

$ cocos run -p android -m release --ap 14