モーションの再生開始と再生終了のコールバック(Native)

最終更新: 2024年12月19日

概要

Cubism SDK for Nativeでは、モーションの再生開始と再生終了時にコールバックによるイベントの取得が行なえるようになりました。

サンプルでは、コールバック関数で再生開始と再生終了を通知するログテキストを出力しています。

コールバックの実装

今回はモーションの再生開始時と再生終了時にコールバックによる処理を行うため、モーションを管理する抽象クラスである
Framework/src/Motion/ACubismMotion でコールバックを扱えるように実装を行っています。

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
class ACubismMotion
{
public:
// モーション再生開始コールバック関数の定義
typedef void (*BeganMotionCallback)(ACubismMotion* self);
// モーション再生終了コールバック関数の定義
typedef void (*FinishedMotionCallback)(ACubismMotion* self);
// モーション再生開始コールバックの登録
void SetBeganMotionHandler(BeganMotionCallback onBeganMotionHandler);
// モーション再生終了コールバックの登録
void SetFinishedMotionHandler(FinishedMotionCallback onFinishedMotionHandler);
//モーション再生開始コールバックの取得
BeganMotionCallback GetBeganMotionHandler() const;
//モーション再生終了コールバックの取得
FinishedMotionCallback GetFinishedMotionHandler();
private:
// モーション再生開始時に呼び出されるコールバック関数を入れる変数
BeganMotionCallback _onBeganMotion;
// モーション再生終了時に呼び出されるコールバック関数を入れる変数
FinishedMotionCallback _onFinishedMotion;
};
class ACubismMotion { public: // モーション再生開始コールバック関数の定義 typedef void (*BeganMotionCallback)(ACubismMotion* self); // モーション再生終了コールバック関数の定義 typedef void (*FinishedMotionCallback)(ACubismMotion* self); ・ ・ ・ // モーション再生開始コールバックの登録 void SetBeganMotionHandler(BeganMotionCallback onBeganMotionHandler); // モーション再生終了コールバックの登録 void SetFinishedMotionHandler(FinishedMotionCallback onFinishedMotionHandler); //モーション再生開始コールバックの取得 BeganMotionCallback GetBeganMotionHandler() const; //モーション再生終了コールバックの取得 FinishedMotionCallback GetFinishedMotionHandler(); ・ ・ ・ private: // モーション再生開始時に呼び出されるコールバック関数を入れる変数 BeganMotionCallback _onBeganMotion; // モーション再生終了時に呼び出されるコールバック関数を入れる変数 FinishedMotionCallback _onFinishedMotion; };
class ACubismMotion
{
public:
    // モーション再生開始コールバック関数の定義
    typedef void (*BeganMotionCallback)(ACubismMotion* self);

    // モーション再生終了コールバック関数の定義
    typedef void (*FinishedMotionCallback)(ACubismMotion* self);
    ・
    ・
    ・
    // モーション再生開始コールバックの登録
    void SetBeganMotionHandler(BeganMotionCallback onBeganMotionHandler);

    // モーション再生終了コールバックの登録
    void SetFinishedMotionHandler(FinishedMotionCallback onFinishedMotionHandler);

    //モーション再生開始コールバックの取得
    BeganMotionCallback GetBeganMotionHandler() const;

    //モーション再生終了コールバックの取得
    FinishedMotionCallback GetFinishedMotionHandler();
    ・
    ・
    ・

private:
    // モーション再生開始時に呼び出されるコールバック関数を入れる変数
    BeganMotionCallback _onBeganMotion;

    // モーション再生終了時に呼び出されるコールバック関数を入れる変数
    FinishedMotionCallback _onFinishedMotion;
};
Tips

サンプルでは、以下の状態だとコールバックが呼び出せませんのでご注意ください。

  • 再生中のモーションが「ループ」として設定されているとき
  • コールバックにNULLが登録されているとき

コールバック関数の利用

コールバック関数で実際に処理させたい内容を実装します。

サンプルでは、モーション再生開始と再生終了を通知するログテキストを LAppPal::PrintLog() を使用して出力するように実装しています。
モーション再生開始時と再生終了時の処理を変更したい場合は、下記関数の実装を変更してください。

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
void BeganMotion(ACubismMotion* self)
{
LAppPal::PrintLog("Motion Began: %x", self);
}
void FinishedMotion(ACubismMotion* self)
{
LAppPal::PrintLog("Motion Finished: %x", self);
}
void BeganMotion(ACubismMotion* self) { LAppPal::PrintLog("Motion Began: %x", self); } void FinishedMotion(ACubismMotion* self) { LAppPal::PrintLog("Motion Finished: %x", self); }
void BeganMotion(ACubismMotion* self)
{
   LAppPal::PrintLog("Motion Began: %x", self);
}

void FinishedMotion(ACubismMotion* self)
{
   LAppPal::PrintLog("Motion Finished: %x", self);
}

また、コールバック関数の登録はモーションデータを読み込むFramework層の CubismUserMotion::LoadMotion() 使用時にモーションの生成と同時にコールバック関数を渡しています。
既にモーションがある際は 「コールバックの実装」で紹介した SetBeganMotionHandler() と SetFinishedMotionHandler() を使用しています。

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
CubismMotionQueueEntryHandle LAppModel::StartMotion(const csmChar* group, csmInt32 no, csmInt32 priority, ACubismMotion::FinishedMotionCallback onFinishedMotionHandler, ACubismMotion::BeganMotionCallback onBeganMotionHandler)
{
if (motion == NULL)
{
csmString path = fileName;
path = _modelHomeDir + path;
csmByte* buffer;
csmSizeInt size;
buffer = CreateBuffer(path.GetRawString(), &size);
// モーションデータを読み込むのと同時にコールバック関数を渡して登録する
motion = static_cast<CubismMotion*>(LoadMotion(buffer, size, NULL, onFinishedMotionHandler, onBeganMotionHandler));
}
else
{
motion->SetBeganMotionHandler(onBeganMotionHandler);
motion->SetFinishedMotionHandler(onFinishedMotionHandler);
}
}
CubismMotionQueueEntryHandle LAppModel::StartMotion(const csmChar* group, csmInt32 no, csmInt32 priority, ACubismMotion::FinishedMotionCallback onFinishedMotionHandler, ACubismMotion::BeganMotionCallback onBeganMotionHandler) { ・ ・ ・ if (motion == NULL) { csmString path = fileName; path = _modelHomeDir + path; csmByte* buffer; csmSizeInt size; buffer = CreateBuffer(path.GetRawString(), &size); // モーションデータを読み込むのと同時にコールバック関数を渡して登録する motion = static_cast<CubismMotion*>(LoadMotion(buffer, size, NULL, onFinishedMotionHandler, onBeganMotionHandler)); ・ ・ ・ } else { motion->SetBeganMotionHandler(onBeganMotionHandler); motion->SetFinishedMotionHandler(onFinishedMotionHandler); } }
CubismMotionQueueEntryHandle LAppModel::StartMotion(const csmChar* group, csmInt32 no, csmInt32 priority, ACubismMotion::FinishedMotionCallback onFinishedMotionHandler, ACubismMotion::BeganMotionCallback onBeganMotionHandler)
{
    ・
    ・
    ・
    if (motion == NULL)
    {
        csmString path = fileName;
        path = _modelHomeDir + path;

        csmByte* buffer;
        csmSizeInt size;
        buffer = CreateBuffer(path.GetRawString(), &size);
        // モーションデータを読み込むのと同時にコールバック関数を渡して登録する
        motion = static_cast<CubismMotion*>(LoadMotion(buffer, size, NULL, onFinishedMotionHandler, onBeganMotionHandler));
        ・
        ・
        ・
    }
    else
    {
        motion->SetBeganMotionHandler(onBeganMotionHandler);
        motion->SetFinishedMotionHandler(onFinishedMotionHandler);
    }
}

サンプルでは、タップイベントを取得するOnTap()実行時に呼び出される StartRandomMotion() からコールバック関数を渡しています。

また、実際にモーションを再生しているのは CubismMotion::DoUpdateParameters() となるので、CubismMotion にコールバック関数を渡せるように実装を行っています。

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
CubismMotion* CubismMotion::Create(const csmByte* buffer, csmSizeInt size, FinishedMotionCallback onFinishedMotionHandler, BeganMotionCallback onBeganMotionHandler)
{
CubismMotion* ret = CSM_NEW CubismMotion();
ret->Parse(buffer, size);
ret->_sourceFrameRate = ret->_motionData->Fps;
ret->_loopDurationSeconds = ret->_motionData->Duration;
// コールバック関数の登録
ret->_onFinishedMotion = onFinishedMotionHandler;
ret->_onBeganMotion = onBeganMotionHandler;
}
CubismMotion* CubismMotion::Create(const csmByte* buffer, csmSizeInt size, FinishedMotionCallback onFinishedMotionHandler, BeganMotionCallback onBeganMotionHandler) { CubismMotion* ret = CSM_NEW CubismMotion(); ret->Parse(buffer, size); ret->_sourceFrameRate = ret->_motionData->Fps; ret->_loopDurationSeconds = ret->_motionData->Duration; // コールバック関数の登録 ret->_onFinishedMotion = onFinishedMotionHandler; ret->_onBeganMotion = onBeganMotionHandler; }
CubismMotion* CubismMotion::Create(const csmByte* buffer, csmSizeInt size, FinishedMotionCallback onFinishedMotionHandler, BeganMotionCallback onBeganMotionHandler)
{
    CubismMotion* ret = CSM_NEW CubismMotion();

    ret->Parse(buffer, size);
    ret->_sourceFrameRate = ret->_motionData->Fps;
    ret->_loopDurationSeconds = ret->_motionData->Duration;
    // コールバック関数の登録
    ret->_onFinishedMotion = onFinishedMotionHandler;
    ret->_onBeganMotion = onBeganMotionHandler;
}

実装の発展について

サンプルではモーションの再生開始と再生終了のみの実装ですが、これらの実装を発展させることにより、モーションの再生開始時や再生終了後にコールバック関数で非同期処理などが利用できるようになったり、
コールバックを適用したい実際の処理から関数を逆引きすることによって、モーション再生開始と終了以外の箇所にもコールバックの実装が可能になります。

この記事はお役に立ちましたか?
はいいいえ
この記事に関するご意見・
ご要望をお聞かせください。