iOS SDK (Cocos2d-x)

1. はじめに

本ドキュメントはiOS向けSmartBeatをCocos2d-xに導入するための手順を記述します。
動作検証済みのCocos2d-x(C/C++)のバージョンは、2.1.4, 2.1.5, 2.2, 2.2.3, 3.1.1, 3.2、Cocos2d-JSのバージョンは3.7, 3.8, 3.13.1となります。

本SDKが対応しているCocos2d-x上の言語はC/C++およびJavaScriptです。
動作対象iOSは、4.3以降となります。

2. iOSのProjectへのSDKの取り込み方法

Step1:SDKの取り込み

  • CocoaPods
  • マニュアル インストール
Podfileに以下の行を追加してください。

pod 'SmartBeat-bitcode'

※重複ユーザカウントの抑止設定を行う場合は、'SmartBeat-bitcode'の代わりに'SmartBeatPlus-bitcode'を記述してください。
※iOS6より前のバージョンをサポートする場合、bitcode無効版(SmartBeat, SmartBeatPlus)を指定して下さい。

その後、以下のコマンドを実行してください。

$ pod install
$ pod update

今後SDKのバージョンを更新する場合は、pod updateを実行するのみで、バージョンアップが実施できます。

また、SmartBeatのヘッダ読み込みを SmartBeatPlus/SmartBeat.h に変更してください。

//#import <SmartBeatFramework/SmartBeat.h>
#import <SmartBeatPlus/SmartBeat.h>
下記からSmartBeatのSDKをダウンロードして、unzipしてください。


他形式のSDKは こちら からダウンロードしてください。

まず、SmartBeatFramework.frameworkを任意のフォルダにコピーする。
Xcodeを起動し、対象のTargetを選択。「General」 -> 「Linked Frameworks and Libraries」上で「+」をクリックし、Add OtherからSmartBeatFramework.frameworkを選択し、追加する。
注:Xcode 5.0.2の場合cocos_ios_1

また、標準に含まれる以下のframeworkを追加する

  • SystemConfiguration.framework
  • CoreTelephony.framework
  • CoreGraphics.framework
  • OpenGLES.framework
  • AdSupport.framework(重複ユーザカウント排除機能を利用する場合に追加。デプロイターゲットとしてiOS6.0より前も対象とする場合には"Optional"で追加してください)
  • libz.tbdまたはlibz.dylib(SDKバージョン1.20以降)

Step2:APIキーの設定

Xcodeで対象のProjectのiOS配下のAppController.mmを開き以下のimport文を追加する

#import <SmartBeatFramework/SmartBeat.h>

SmartBeatの初期化APIを – application:didFinishLaunchingWithOptions: の最初に追加する
「APIキー」に関してはコンソールよりProject作成時に発行されるキーを設定する

- (BOOL)application:(UIApplication *)application
didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    [SmartBeat startWithApiKey:@"APIキー"];
    //your code

Step3:重複ユーザカウントの抑止設定

SDKバージョン1.18以降

ユーザ数の集計にIDFAを使用することで、同一ユーザの重複カウントを抑止します。これにより、アプリの再インストールを繰り返す行為(俗に言う「リセマラ」)があった場合でも、不要なMAU(Monthly Active Users)数の増加を抑えることができます。

※ 重複ユーザカウントの抑止設定を有効にすることでオーディエンス機能も有効となります。
※ 本機能はiOS 6.0以降を利用のユーザカウントにのみ有効です。

本機能を有効にしない場合には、以下の手順は不要です。

  • CocoaPods
  • マニュアル インストール
下記のように、Podfileに記述するパッケージ名を「SmartBeat-bitcode」から、「SmartBeatPlus-bitcode」へ変更してください。

# pod 'SmartBeat-bitcode'
pod 'SmartBeatPlus-bitcode'

続いて、設定反映のため、

$ pod install
$ pod update

を実行してください。
※bitcode無効版を利用する場合は、「-bitcode」なしのパッケージを指定してください。

SmartBeatIdfa.frameworkの追加

Step1と同様にして、Xcodeで「General」 -> 「Linked Frameworks and Libraries」上で「+」をクリックし、Add OtherからSmartBeatIdfa.frameworkを選択してFrameworkを追加してください。

※ SmartBeatFramework.frameworkとSmartBeatIdfa.frameworkの両方が必要です。

sb_idfa_framework

リンカオプションの追加

Xcodeで対象のTargetを選択し、「Build Settings」の「Other Linker Flags」に以下を追加してください。

-force_load /Frameworkを置いたフォルダのパス/SmartBeatIdfa.framework/SmartBeatIdfa

linker_flags

3. Cocos2d-JSのエラー取得

SDKバージョン1.21以降

以下の手順でJavaScriptバインディングを有効にすることで、Cocos2d-JSのJavaScript側のエラーを取得することができます。
※第2章の内容に従ってプロジェクトにSDKを取り込んだ後で以下の手順を行ってください。
※JavaScriptエラーの取得はCocos2d-x v3.7以上で対応しています。
※JavaScriptを使わないアプリでは以下の手順は必要ありません。

  • CocoaPods
  • マニュアル インストール

PodfileへのSmartBeatJSBindingの追加

Podfileに以下の行を追加してください。

pod 'SmartBeatJSBinding-bitcode'

続いて、設定反映のため、

$ pod install
$ pod update

を実行してください。
※bitcode無効版を利用する場合は、「-bitcode」なしのパッケージを指定してください。

SmartBeatJSBinding.frameworkの追加

まず、SmartBeatJSBinding.frameworkを任意のフォルダにコピーする。
Xcodeを起動し、対象のTargetを選択。「General」 -> 「Linked Frameworks and Libraries」上で「+」をクリックし、Add OtherからSmartBeatJSBinding.frameworkを選択し、追加する。

SmartBeat JavaScriptバインディングの登録

プロジェクトフォルダのframeworks/runtime-src/Classes/AppDelegate.cppを開いて、以下のinclude文を追加する。

#include <SmartBeatJSBinding/SmartBeatJSBinding.h>

AppDelegate::applicationDidFinishLaunching()の中で、sc->start()の呼び出しよりも前に以下の1行を追加する。

bool AppDelegate::applicationDidFinishLaunching()
{
    ...
    sc->addRegisterCallback(...);
    sc->addRegisterCallback(...);
    ...
    sc->addRegisterCallback(SmartBeat::registerSmartBeatJSBinding); //ここを追加
    sc->start();
    ...
}

4. オプション機能

本節にて、追加機能に関して記述します。アプリケーションからAPIを呼び出すことでこれら追加機能を有効にすることが可能です。

メインスレッド以外のスレッドからのAPIの呼び出しについて

SBLog、leaveBreadcrumb、logExceptionのAPIをメインスレッド以外のスレッドから呼び出す場合は、スレッドが破棄されるまでAPI内部で使用したメモリが解放されずに溜まり続ける場合があります。長時間生存するスレッドから呼び出す場合は、@autoreleasepoolで囲うようにしてください。

- (void)threadfunc:(id)argument
{
    while (YES) {
        @autoreleasepool {
            ...
            SBLog(@"log message");
            ...
        }
    }
}

4.1 画面キャプチャ機能

本機能を有効にすることで、クラッシュ発生までの画面遷移が確認できるようになります。
SDKでは、アプリケーション表示中の最新画面を定期的キャプチャし、クラッシュ時に最新の1枚をSmartBeatサーバへ送信します。
※本機能はWhitelistに登録された端末のみで動作します。第5章参照。

有効化方法

Cocos2d-xで画面キャプチャを行う場合、まず、cocos2dxのワークスペースからSmartBeatFrameworkを参照できるよう設定します。
<2.xの場合>
Xcode上で、cocos2dx.xcodeprojのワークスペース内のcocos2dxのターゲットを選択し、「Build Settings」のタブを選択し、「Search Paths」に含まれる「Framework Search Paths」にStep1で追加したSmartBeatFramework.frameworkを追加します。
<3.xの場合>
Xcode上で、cocos2d_libs.xcodeprojのワークスペース内のcocos2dx iOSのターゲットを選択し、「Build Settings」のタブを選択し、「Search Paths」に含まれる「Framework Search Paths」にStep1で追加したSmartBeatFramework.frameworkを追加します。

cocos_ios_2

<2.xの場合>

例えば、cocos2dxのルートフォルダ配下の、external配下のサブフォルダにSmartBeatFramework.frameworkをコピーしている場合、パスに「$(SRCROOT)/../../external」を設定し、recursiveとします。

<3.xの場合>

例えば、<アプリのプロジェクトフォルダ>/cocos2d/external/ 配下にSmartBeatFramework.frameworkをコピーしている場合、パスに「$(SRCROOT)/../external」を設定し、recursiveとします。

cocos_ios_2

続いてpresentRenderbufferの呼び出し前後にコードを追加します。
<2.xの場合>
/cocos2dx/platform/ios/EAGLView.mmを開いて下記のように修正してください。
<3.xの場合>
/cocos/platform/ios/CCEAGLView.mmを開いて下記のように修正してください。

まず、下記Import文を追加します。

#import <SmartBeatFramework/SmartBeat.h>

続いて、下記のようにpresentRenderbufferの前後でAPI(beforePresentRenderbuffer / afterPresentRenderbuffer)を呼び出してください。

cocos_ios_4

また、Xcode6以降でビルドする場合、/cocos2dx/platform/ios/CCES2Render.mの「resizeFromLayer:layer」に以下のコードを追加してください。※Xcode5でビルドする場合でも追加しても問題はありません。

- (BOOL)resizeFromLayer:(CAEAGLLayer *)layer
{
    //Xcode6 + iOS8対応追加コード
    glBindFramebuffer(GL_FRAMEBUFFER, defaultFramebuffer_);
    // Allocate color buffer backing based on the current layer size
    glBindRenderbuffer(GL_RENDERBUFFER, colorRenderbuffer_);

さらに、Cocos2d-x 3.7以上の場合は/cocos/renderer/CCFrameBuffer.cppのFrameBuffer::clearAllFBOs()に以下のコードを追加してください。

void FrameBuffer::clearAllFBOs()
{
    //Cocos2d-x 3.7以上対応追加コード
    GLint currentFrameBuffer;
    glGetIntegerv(GL_FRAMEBUFFER_BINDING, &currentFrameBuffer);

    for (auto fbo : _frameBuffers)
    {
        //Cocos2d-x 3.7以上対応追加コード
        fbo->_fbo = currentFrameBuffer;

        fbo->clearFBO();
    }
}
追加API

任意のデバイスをwhitelistに追加する場合、以下のAPIを利用して追加可能です。

[[SmartBeat shared] whiteListModelForOpenGLES:モデル名];

「モデル名」はiOSのAPI(sysctlbyname関数にhw.machineを指定)から取得した値が設定できます。

4.2 ログ出力

SDKバージョン1.20以降

端末のログに出力すること無く、ログの収集をすることができます。
※iOS 10.0以降では4.3章のNSLog出力機能を有効にしてもログをクラッシュデータに含める
ことができません。代わりに本機能を使用することを推奨いたします。

※64KBに満たない場合は最大500行、それ以外は64KBに収まる範囲で最新のログを取得します。
※4.3章のNSLog出力機能を有効にした場合、iOS 10.0より前の端末では本機能によるログは
クラッシュデータに含まれず、NSLogによるログのみがクラッシュデータに含まれます。

有効化方法

以下のAPI呼び出しを実装することで、ログを保存できます。

■ Objective-C
SBLog("String: %@, Integer: %d", "text", 1);

または

va_list args;
va_start(args, format);
SBLogv(format, args);
va_end(args);

※メインスレッド以外のスレッドからの呼び出しに関する注意はこちらを参照。

■ JavaScript
SmartBeat.log('message');

4.3 NSLog出力

NSLogの出力をクラッシュデータに含める場合は、NSLog出力機能を有効にしてください。
(本API呼出しは、第2章 Step2で編集したAppController.mmにて行ってください)
※iOS 10.0以降では本機能を有効にしてもNSLogをクラッシュデータに含めることはできません。
代わりに4.2章のログ出力APIを使用することを推奨いたします。

※64KBに満たない場合は最大500行、それ以外は64KBに収まる範囲で最新のログを取得します。
※本機能を有効にした場合、iOS 10.0より前の端末では4.2章のログ出力APIによるログは
クラッシュデータに含まれず、NSLogによるログのみがクラッシュデータに含まれます。

有効化方法
■ Objective-C
[[SmartBeat shared] enableNSLog];
■ JavaScript

JavaScriptで該当する関数はありません。

4.4 ユーザID設定

対象のアプリケーションが管理するユーザを識別するIDが既にある場合、それを設定することができます。
設定されたユーザIDはクラッシュとともにSmartBeatサーバへ送信されます。どのユーザでクラッシュが発生したかなど管理コンソール上で確認が可能です。

有効方法

以下のAPI呼び出しを実装することで、設定可能です。

■ Objective-C
[[SmartBeat shared] setUserId:@"user001"];
■ JavaScript
SmartBeat.setUserId('user001');

4.5 拡張情報

クラッシュ情報に拡張情報を付与することができます。アプリケーションによっては、ユーザが設定した情報や、アプリケーションが内部に保持している情報が、クラッシュ解析に役立ちます。

有効化方法

以下のAPI呼び出しを実装することで、任意のキー名と値のセットをクラッシュデータと共に保存することが可能です。
値を変更したい場合は、同じキー名で追加すると、新しい値で上書きされます。

■ Objective-C
NSMutableDictionary *extraData = [NSMutableDictionary dictionary];
[extraData setObject:@"value1" forKey:@"key1"];
[extraData setObject:@"value2" forKey:@"key2"];
[[SmartBeat shared] setExtraData:extraData];

データはNSString型のみが設定できます。

■ JavaScript
SmartBeat.addExtraData('key1', 'value1');
SmartBeat.addExtraData('key2', 'value2');

4.6 パンくず(breadcrumb)機能

任意のポイントでパンくずを残すことにより、エラー発生までにユーザが行った操作や画面遷移などを収集することができます。

有効化方法

パンくずを落とす(記録を残したい)場所で以下のAPIを呼び出して下さい。
パンくずは最後に記録されたものから最大16個保存されます。
例えば、「マップ画面」→「ゲーム画面」→「設定画面」などと、キーとなる画面の遷移時に残した場合、エラー直前にユーザがどのような画面遷移を行ったかを知ることができます。

■ Objective-C
[[SmartBeat shared] leaveBreadcrumb:@"game scene 1"];

※メインスレッド以外のスレッドからの呼び出しに関する注意はこちらを参照。

■ JavaScript
SmartBeat.leaveBreadcrumb('game scene 1');

4.7 エラー収集有効・無効切り替え

SDKバージョン1.6以降

初期状態をエラー収集無効とし、途中からエラーの収集を有効にしたい場合に利用できます。

有効化方法

APIキーの設定(上記Step2)で記述したAPIの代わりに以下のAPIで起動時に有効とするか、無効とするか設定してください。

- (BOOL)application:(UIApplication *)application
didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    BOOL enableSmartBeat = NO; //無効状態で起動する場合はNO
    [SmartBeat startWithApiKey:@"APIキー" withEnabled:enableSmartBeat];
    //your code

その後、有効にしたい場合は、任意の箇所で以下のコードを呼び出してください。呼び出された以降に発生したエラーの収集を行います。
なお、有効・無効の設定は毎起動時に SmartBeat startWithApiKey: withEnabled: で設定してください。

■ Objective-C

有効化

[[SmartBeat shared] enable];

無効化

[[SmartBeat shared] disable];

状態取得

BOOL enabled = [[SmartBeat shared] isEnabled];
■ JavaScript

有効化

SmartBeat.enable();

無効化

SmartBeat.disable();

状態取得

var enabled = SmartBeat.isEnabled();

4.8 CatchしたJavaScriptエラーの保存

SDKバージョン1.21以降

Cocos2d-JSでアプリケーションがCatchしたJavaScriptエラーを記録することができます。

有効化方法
try {
    throw new Error();
} catch (e) {
    SmartBeat.logException(e);
}

4.9 dSYM自動アップロード

dSYM自動アップロードスクリプトをXcodeのRun Scriptに組み込むことで、毎ビルド自動でdSYMをアップロードすることができます。

詳細な組込み方及びスクリプトはこちらからダウンロードして下さい。

4.10 オーディエンス機能

対ユーザ識別子として Advertising ID for Android もしくは IDFA for iOS を使用することで、アプリケーションを利用するユーザの男女比や年齢分布を確認できるようになります。

有効方法

重複ユーザカウントの抑止設定を有効にすることでオーディエンス機能も有効となります。重複ユーザカウントの抑止設定についてはこちらを参照ください。

5. リソース消費

SDK組込みによるリソースの消費計測結果を以下に示す。

端末 項目 SDK組込み時
画面キャプチャ無効
SDK組込み時
画面キャプチャ有効
iPhone5S
iOS7.0.4
メモリ消費量
CPU負荷
約1.0MB増加
増減なし
約1.7MB増加
平均 約2.3%増加
iPhone4
iOS6.0.1
メモリ消費量
CPU負荷
約1.0MB増加
増減なし
約1.3MB増加
平均 約4.8%増加

※画面キャプチャを有効にした場合は、画面の画素数に応じてメモリ消費量が増加
※画面キャプチャを有効にした場合は、画面取得、エンコード処理、保存処理が入るため、CPU負荷が増加

6. OpenGL ES画面キャプチャ対象端末

OpenGL ES画面キャプチャ機能のサポート対象を記述する

デバイス名 hw.machine SDKバージョン
iPhone 4 iPhone3,1 iPhone3,2 iPhone3,3 1.19 -
iPhone 4S iPhone4,1 1.19 -
iPhone 5 iPhone5,1 iPhone5,2 1.19 -
iPhone 5C iPhone5,3 iPhone5,4 1.19 -
iPhone 5S iPhone6,1 iPhone6,2 1.19 -
iPhone 6S iPhone8,1 1.19 -
iPhone 6S Plus iPhone8,2 1.19 -
iPhone SE iPhone8,4 1.20 -
iPhone 7 iPhone9,1 iPhone9,3 1.23 -
iPhone 8 iPhone10,1 iPhone10,4 1.23 -
iPhone 8 Plus iPhone10,2 iPhone10,5 1.23 -
iPhone X iPhone10,3 iPhone10,6 1.23 -
iPad 2 iPad2,1 iPad2,2 iPad2,3 iPad2,4 1.19 -
iPad Mini (1st) iPad2,5 iPad2,6 iPad2,7 1.19 -
iPod Touch (5th) iPod5,1 1.19 -
iPod Touch (6th) iPod7,1 1.23 -

7. 改版履歴

改版日 変更内容
2014年6月2日 初版リリース
2014年9月11日 Xcode6でのビルド時に必要な修正の追記(4.1 画面キャプチャ機能)
2014年11月20日 Cocos2d-x 3.xでの実装方法の注釈を追記
2016年1月6日 「Step3:IDFAによるユーザカウントの有効化」を追加(SDKバージョン1.18以降)
2016年3月14日 「6. OpenGL ES画面キャプチャ対象端末」を追加
2016年4月20日 「4.10 オーディエンス機能」を追加
2016年11月21日 「2. iOSのProjectへのSDKの取り込み方法」の必要ライブラリを追加
「4.1 画面キャプチャ機能(OpenGL ES)」にCococs2d-x 3.7以上の有効化方法を追記
「4.1 画面キャプチャ機能(OpenGL ES)」の追加APIを追加
「4.2 ログ出力」を追加(SDKバージョン1.20以降)
「4.3 NSLog出力」の補足説明を追加
「6. OpenGL ES画面キャプチャ対象端末」のリストを更新
2016年12月22日 「1. はじめに」でCocos2d-xの動作検証済みバージョンと対応言語を更新
「3. Cocos2d-JSのエラー取得」を追加(SDKバージョン1.21以降)
「4. オプション機能」の各章にJavaScriptのAPIを追加
「4.6 パンくず(breadcrumb)機能」を追加
「4.7 エラー収集有効・無効切り替え」を追加
「4.8 CatchしたJavaScriptエラーの保存」を追加
「4.9 dSYM自動アップロード」を追加
2017年4月13日 「3. Cocos2d-JSのエラー取得」を更新
2017年11月2日 「2. iOSのProjectへのSDKの取り込み方法」にCocoaPodsによる手順を追加
2017年12月28日 「3. オプション機能」にメインスレッド以外のスレッドからのAPI呼び出しについての説明を追加
2018年5月16日 「6. OpenGL ES画面キャプチャ対象端末」のリストを更新