バージョン

menu_open
Wwise SDK 2022.1.17
高レベルストリームマネージャAPI概要

イントロダクション

Wwise サウンドエンジンは、ストリームマネージャを使用してサウンドバンクをロードし、ストリーミングされたオーディオファイルを読み込みます。I/Oマネージャをお持ちでない場合は、これをあらゆるゲーム I/O にご使用いただくことが可能です。高レベルストリームマネージャをクライアントとして直接使用せず、低レベル I/O フックの実装により Wwise I/O をゲームに統合する場合には、この章を読み飛ばしていただいても結構です。

ストリームマネージャ メインインターフェイス

ストリームマネージャのメインインターフェイスは、AK::IAkStreamMgr により定義されますが、これは基本的にストリーミングオブジェクトのファクトリです。

ストリームマネージャのインスタンス化

ストリームマネージャを使用する前に、これをインスタンス化する必要があります。

Default Streaming Manager Information

ストリームマネージャのインスタンス化は、実装固有のものです。従って、ストリームマネージャの Audiokinetic デフォルト実装ファクトリ関数は、AkStreamMgrModule.h: AK::StreamMgr::Create()で定義されています。これに実装固有の設定を渡す必要があります(初期設定に関する詳細は、Audiokinetic ストリームマネージャ初期化設定 を参照してください)。

高レベルストリーミングデバイス

Default Streaming Manager Information

ストリームオブジェクト作成と使用の前に、高レベルストリーミングデバイスを作る必要があります。この概念はAudiokineticストリームマネージャのデフォルト実装に固有のものです。高レベルストリーミングデバイスは、基本的に独自のスレッドで実行されるI/Oスケジューラ実装で、これに関連付けられているストリームオブジェクトを一元化し、データ転送要求を低レベル I/Oにポストします。一般に高レベルデバイスは、単にデバイスと呼ばれます。特定にフラグおよび設定を持つ1つ以上のデバイスが、好ましくは初期化時にゲームによって作成されます。初期設定に関する詳細は、Audiokinetic ストリームマネージャ初期化設定 のセクションをご覧ください。AK::StreamMgr::CreateDevice() は、デバイスIDを返しますが、これはファイルロケーションおよびデバイス割り当てのために低レベルI/Oによって保持される必要があります。(更なる詳細は、ファイルロケーションの解決 のセクションをご覧ください。)正しい終了のためには、このデバイスIDが AK::StreamMgr::DestroyDevice() に渡されなければなりません。実装固有の全ての関数については、AK::StreamMgr::CreateDevice()AK::StreamMgr::DestroyDevice() は、ヘッダ AkStreamMgrModule.h で定義されています。

ストリームの作成

ストリームマネージャ メインAPIの多くはストリームファクトリメソッドのセットです。ファイル識別子と設定を与えられ、これらはストリームオブジェクトを作成し、そのストリームにインターフェイスを戻します。すべてのストリーム操作は、このインターフェイスを介して実行されます。 ストリーム作成メソッドの両セットはオーバーロードを2つ持ちますが、これらは使用するファイル識別方式に応じて異なります。1つ目のオーバーロードは、ファイルの識別に文字列を使用しますが、2つ目のオーバーロードは、整数IDを使用します。

Default Streaming Manager Information

AK::IAkStreamMgr::CreateStd() または AK::IAkStreamMgr::CreateAuto() 文字列ファイルオーバーロードを使用する場合、ストリームマネージャは、この文字列を AK::StreamMgr::IAkFileLocationResolver::Open() の文字列オーバーロードに転送します。同様に、IDファイル識別子のオーバーロードを呼び出すと、AK::StreamMgr::IAkFileLocationResolver::Open() のIDオーバーロードへの呼び出しがトリガされます。詳細は、 ファイルロケーションの解決 セクションをご覧ください。

注釈: 低レベルI/OインターフェースのOpen() メソッドは、ファイル識別子からファイル記述子を作成します。

ストリーム作成メソッドは、ファイル識別子に加えて、ファイルロケーション用フラグを含む AkFileSystemFlags 構造体へのポインタを受け付けます。

Default Streaming Manager Information

このポインタはそのまま低レベルI/Oへ渡されます。AkFileSystemFlags に関する詳細およびサウンドエンジンがどのようにこれらを使用するかについては、サウンドバンクストリーミングオーディオファイル基本的なファイルロケーション のセクションをご覧ください。

ストリーム作成メソッドには、追加引数があります:in_bSyncOpen。ユーザーは(サウンドエンジンと同じように)、ストリームオブジェクトでラップされたファイルハンドルがこのコール中にオープンされる必要がある場合には、trueを渡します。falseを渡すと、Stream Managerによるファイルオープン延期を許可することになります。延期は発生する可能性も発生しない可能性もあります。延期が発生して、ファイルオープンに失敗した場合、 AK::IAkStdStream::Read() または AK::IAkAutoStream::GetBuffer() への次のコールはAK_Failを返します。

注釈: これは、致命的なエラーとみなされるべきではありません。サウンドエンジンはストリームされたオーディオファイルに対して false を渡します。GetBuffer() が false を返すと、これは I/O エラーとみなされ、ストリームが正常に破棄されます。
Default Streaming Manager Information

引数 in_bSyncOpenは、低レベルI/Oに直接渡されます。低レベルI/Oのこのフラグの影響についての詳細は 遅延オープン を参照してください。

AK::IAkStreamMgr::CreateStd() は、標準ストリームを作成し、 AK::IAkStreamMgr::CreateAuto() は自動ストリームを作成します。これらの2タイプのストリームについて、以下のセクションで解説しています。

ストリームの破棄

どちらのタイプのストリームオブジェクトも Destroy() メソッドを定義します。ストリームにより使用されているリソースを解放するためには、このメソッドを呼び出す必要があります。これを実行した後には、オブジェクトを再び使用することはできません。

Default Streaming Manager Information

ストリームマネージャのデフォルト実装では、AK::IAkStdStream::Destroy() とAK::IAkAutoStream::Destroy() は単にストリームオブジェクトにフラグを設定するために使用されます。実際の破棄は、I/Oスレッドによって後から実行されます。これは、ウェイクアップのたびに、すべてのオープンストリームを点検し、I/O要求が低レベルI/Oへ発行されるための次のストリームを見つけ、すべての終了したストリームをクリーンアップします。メモリが解放されるのは、この時点のみで、(ファイルハンドルを解放する)AKStreamMgr::IAkLowLevelIOHook::Close() が呼び出されます。

破棄が予定されているストリームオブジェクトは、低レベルI/O で保留されている所有I/O転送がなくなったらすぐに解放されるよう、I/Oスレッドに信号を送ります。

ストリームプロファイリングが発生している場合、I/Oスレッドは、監視スレッドによる承認を待ってからストリームオブジェクトを破棄します。監視スレッドは、200ミリ秒ごとにプロファイリングパスを実行します。

標準ストリーム

AK::IAkStreamMgr::CreateStd() への呼び出しにより、返される AK::IAkStdStream インターフェースを介して制御可能である標準ストリームオブジェクトが作成されます。

定義

標準ストリームは、基本的なリード/ライト方式を使用してI/O動作を制御します。 AK::IAkStdStream::Read() または AK::IAkStdStream::Write() が呼び出されると、I/O要求がスケジューラにキューイングされ、ストリームはそのステータスを AK_StmStatusPending に設定します。ユーザーは、要求転送サイズとバッファのアドレスを渡します。完了すると、ストリームはそのステータスをAK_StmStatusCompleted または  AK_StmStatusError に設定します。その位置は、実際に転送されるサイズによってインクリメントされるので、次の操作は新しい位置で発生します。別の位置を強制するには、新しい転送を開始する前に、ユーザーが AK::IAkStdStream::SetPosition() メソッドを使用する必要があります。

同時に発生可能なI/O操作は1つのみです。後続の操作は、 AK::IAkStdStream::Read() または AK::IAkStdStream::Write()を呼び出すことによって、明示的に開始される必要があります。ユーザーがストリームの使用を終えた時は、AK::IAkStdStream::Destroy() を呼び出す必要があります。これにより、インターフェースが無効になります。

Default Streaming Manager Information

リードまたはライトのコールは、低レベルI/OのI/O転送につながります。クライアントレベルで要求されるサイズがストリーミングデバイスの粒度( AkDeviceSettings::uGranularity )より大きい場合、転送が分割されます。ストリームは、全転送が完了するまで、または、エラーまたはエンドオブファイル状況が発生するまで、AK_StmStatusPending または AK_StmStatusIdle 状態のままになります。

インターフェースは、クエリ設定、現在のステータスまたは位置へのアクセス、および以前の操作に供給されるバッファへのアクセスなど、他のメソッドを公開します。

標準ストリームデータアクセス方式

標準ストリーム操作を起動する方法は2つあります:

作成設定

標準ストリームを作成する時には、オープンモード(AkOpenMode)を指定する必要があります。オープンモードは、ストリームがリードまたはライトのどちらに使用されるのか、または、リードとライトの両方に使用されるのかを指定します。リードのみのためにオープンされたストリームへの AK::IAkStdStream::Write() の呼び出しは、明らかに失敗してしまいます。

ストリームの名前を AK::IAkStdStream::SetStreamName() を使用して指定することができます。文字列がストリームオブジェクトにコピーされ、 AK::IAkStdStream::GetInfo() でクエリすることが可能です。

Default Streaming Manager Information

ストリーム名は、Wwise の Advanced Profiler ストリーミングタブに表示されるものです。

ヒューリスティック

標準ストリームのヒューリスティックは、操作ごとに指定されています。

AK::IAkStdStream::Read()AK::IAkStdStream::Write() には、操作の優先度と(ミリ秒単位での)期限が必要です。一般的には、Stream Manager は、期限の短い操作を好みます。ストレージデバイスが提供できるより大きなI/O帯域幅をアプリケーションが必要とする場合、優先度の高いストリームが好まれます。期限をゼロに指定すると、データが今必要とされていることを意味し、I/O は既に遅れています。このような場合には、優先度の低い他のストリームより前に処理されます。

注釈: サウンドエンジンのBank Manager(バンクマネージャ)は、標準ストリームを使用します。SoundBank データを独自のバッファに読み込んで解析します。バンクローディングの平均スループットと優先度を指定するためのメソッドが1つサウンドエンジンAPIで公開されています:AK::SoundEngine::SetBankLoadIOSettings()。(詳細は、Wwise Sound Engine の Banks を参照してください。)バンクマネージャは、 AK::IAkStdStream::Read() を呼び出し、これが完了するとデータを解析して読み取ります。これには、このメソッドの引数として与えられた優先度が使用されます。操作の期限が、ユーザーにより指定されたスループットから計算されます:

標準ストリーム操作の期限と自動ストリームの平均スループットのデッドラインは、Stream Manager のI/Oスケジューラと等価です。サウンドエンジンの使用により、I/O上でのバンクロードの負荷を、オーディオストリームやゲーム内の他のストリームの負荷と調整することができます。

一般的な注意点とその他の考慮事項

ブロックサイズ

リードおよびシークの粒度やバッファアラインメントへの低レベルでの制約は、Stream Manager レベルでは“ブロックサイズ”と呼ばれます。ストリームのインターフェース上の AK::IAkStdStream::GetBlockSize() メソッドは、低レベルI/Oをクエリし、これにストリームに関連付けられたファイル記述子を渡して、呼び出し元にその値を返します。ファイル記述子に関する詳細は、低レベルI/Oのセクションと AK::StreamMgr::IAkLowLevelIOHook::GetBlockSize() メソッドを参照してください。ストレージデバイスの中には、データ転送サイズへの制約があるものもあります。例えば、Win32プラットフォームでは、FILE_FLAG_UNBUFFERED フラグで開かれるファイルは、物理デバイスのセクタサイズのみの倍数の転送サイズを可能にします。リードまたはライトの操作がブロックサイズの倍数ではない転送サイズを要求した場合には、これらの操作は失敗します。高レベルインターフェースのユーザーは、 AK::IAkStdStream::GetBlockSize() に返される値の倍数であるリードサイズを要求しなければなりません。AK::IAkStdStream::SetPosition() は、同様の制約を受けます。しかしながら、これは自動的に下位のブロック境界にスナップし、実際のファイル位置オフセットを返します。

一般的に、ゲームタイトルでは、Stream Manager が使用されます。ゲームタイトルは、低レベルI/Oサブモジュールも実装するので、使用可能な転送サイズを認識しています。サウンドエンジンは、ストレージデバイスの制約を認識しないので、常に標準ストリームのリードサイズをブロックサイズの境界までスナップします。

ストリームステータス保留中に呼び出されるメソッド

AK::IAkStdStream::Read()AK::IAkStdStream::Write() は、ストリームが AK_StmStatusPending ステートにある間に呼び出された場合には失敗します。AK::IAkStdStream::GetPosition()AK::IAkStdStream::SetPosition() は、I/O転送が完了する前または後で発生する可能性があるので、不定な結果をもたらします。しかし、これらがI/Oでブロックすることはありません。

AK::IAkStdStream::Cancel() は、転送の保留中に使用することが可能ですが、パフォーマンスが低下するので、これの使用はお薦めできません。このメソッドは、保留されているI/Oがないことを呼び出し元に確認します。低レベルI/Oに要求が送信される前に呼び出しが実行されると、タスクがキューから除去されます。しかしながら、既に低レベルI/Oへ要求が送信されている場合には、I/Oが完了するまで呼び出し元がブロックされます。

Tip: ユーザーは、ストリームを破棄( AK::IAkStdStream::Destroy() )する前に AK::IAkStdStream::Cancel() を明示的に呼び出す必要はありません。しかし、最良のパフォーマンスを得るためにも、ストリームが AK_StmStatusPending ステートにない場合にのみ、ユーザーは Destroy() を呼び出すべきです。

自動ストリーム

AK::IAkStreamMgr::CreateAuto() を呼び出すと、返される AK::IAkAutoStream インターフェースを介して制御可能である自動ストリームオブジェクトが作成されます。

定義

自動ストリームは、入力のみに使用されるストリームです。I/O要求が、ユーザーによる明示的な関数呼び出しなしで、低レベルI/Oへ “フードの下で” 送信されるため自動ストリームと呼ばれています。ストリーミングメモリは Stream Manager に所有されており、ストリーミングされたデータには、ストリーミングメモリアドレスを求めることによりアクセス可能です。ストリーミングメモリの一領域がユーザーに許可されると、これが明示的に解放されるまでロックされたままになります。一方、内部スケジューラは、ロックされていないメモリ内でデータ転送を実行します。ストリームは、作成時にはアイドル状態です。I/O要求の自動スケジューリングは、ユーザーが AK::IAkAutoStream::Start() を呼び出すと開始します。これは、AK::IAkAutoStream::Stop() の呼び出しにより停止または一時停止、AK::IAkAutoStream::Start() の再度呼び出しにより再開することが可能です。

注意: ストリームが停止している間は、GetBuffer() を呼び出さないでください。ストリームからバッファを取得する前に必ず Start() を呼び出す必要があります。

データは、 AK::IAkAutoStream::GetBuffer() への呼び出しによりアクセス可能です。低レベルI/Oから既にデータが読み出されている場合、このメソッドは AK_DataReady、このデータを含むバッファのアドレス、およびそのサイズを返します。バッファがもはや必要とされない場合は、これを AK::IAkAutoStream::ReleaseBuffer() への呼び出しにより解放することができます。続いて、ストリームの位置は、解放されたバッファのサイズだけインクリメントされます。ユーザーは、AK::IAkAutoStream::SetPosition() への呼び出しにより新しい位置を強制することができます。 AK::IAkAutoStream::GetBuffer() への次の呼び出しは、この位置と一致します。

注意: ストリームの位置を変更すると、一部データのフラッシュが発生する場合があります。自動ストリームはシーケンシャルアクセス用に最適化されています。ループを指定するヒューリスティックがあり、これにより Stream Manager は、ストリーミングメモリを効率的に管理することができます。詳細は、一般的な注意点とその他の考慮事項 section セクションをご覧ください。
注意: 低レベル I/O がエラーを報告すると、ストリームがエラーモードになります。自動ストリームはエラー状態から回復することができないため、 AK::IAkAutoStream::GetBuffer() は常に AK_Fail を返します。

自動ストリームデータへのアクセス法

自動ストリーム内のデータへは次の2つの方法でアクセス可能です:

AK::IAkAutoStream::GetBuffer() には、4つのリターンコードがあります:

  • AK_DataReady
  • AK_NoMoreData
  • AK_NoDataReady
  • AK_Fail

ユーザーが、データで満たされたバッファを付与されている場合、メソッドは AK_DataReady または AK_NoMoreData を返します。ストリームバッファが空の場合、 AK::IAkAutoStream::GetBuffer() は、サイズがゼロおよびバッファアドレスが null で AK_NoDataReady を返します。低レベルI/Oがエラーを報告した場合、または、無効なパラメータでメソッドが呼び出された場合には、AK_Fail が返されます。

ファイルの最後のバッファが付与されると AK_DataReady の代わりに AK_NoMoreData が返されます。Stream Manager は、(ユーザーから見た)現在の位置を、ファイル記述子構造体のメンバとして低レベルI/Oにより提供されるファイルサイズと比較することにより、これが最後のバッファであると判断します。 AK::IAkAutoStream::GetBuffer() への後続の呼び出しは、サイズゼロで AK_NoMoreData を返します。

AK::IAkAutoStream::GetBuffer() を呼び出すたびに、新しいバッファが提供されます。バッファは、 AK::IAkAutoStream::ReleaseBuffer() への呼び出しにより明示的に解放される必要があります。これらのバッファは、GetBuffer() によって付与された順番に解放されます。バッファが解放されると、そのアドレスは無効になります。ReleaseBuffer() は、クライアントがバッファを保持していない場合には、AK_Fail を返します。しかし、これは致命的エラーとみなされるべきではありません。

Tip: 可能であれば、一度に一つのバッファのみを取得するようにしてください。これにより、Stream Manager はI/Oを実行するためのスペースをより多く得ることができます。複数のバッファの同時使用は、主にリング/ダブルバッファへのアクセスを必要とするハードウェアまたはその他のインターフェース向けです。特定のストリームに対して複数のバッファを使用する場合は、適切なヒューリスティック( AkAutoStmHeuristics::uMinNumBuffers )を渡すことにより通知する必要があります。

注意: 自動ストリーム使用時によくあるミスは、ReleaseBuffer() の呼び出しを忘れることです。

GetBuffer() への呼び出しに成功し付与されたバッファサイズは、Stream Manager により決定されます。下層ファイルの末尾に到達した場合以外は、ブロックサイズの倍数でなければなりません。また、作成時に渡されたバッファ制約(AkAutoStmBufSettings 参照)を使用して、GetBuffer() により返されるサイズを強制することも可能です。

注意: バッファサイズを強制すると、ストリーミングメモリと/または帯域幅が浪費される可能性があるので、パフォーマンスが最適以下になる場合があります。また、ユーザー指定の制約はサポートされない場合があります。 IAkStreamMgr::CreateAuto() は、AK_Fail を返します。
Default Streaming Manager Information

通常、ストリームが終わりに達した場合を除き、このサイズは高レベルデバイスの作成設定で指定された粒度に対応します。

ブロッキング

in_bWait フラグを True に設定した状態での AK::IAkAutoStream::GetBuffer() への呼び出しは、データの準備ができるまでユーザーをブロックします。従って、メソッドは AK_NoDataReady を返すことができません。最終バッファが既に付与・解放されている場合には、メソッドはサイズゼロで AK_NoMoreData を直ちに返します。

ポーリング

ユーザーは、 in_bWait フラグを False に設定して呼び出された AK::IAkAutoStream::GetBuffer() によって返されるコードを評価することで、データを取得することができます。AK_NoDataReady が返された場合、他のタスクを行い、しばらくしてから再度試してみてください。

作成設定

自動ストリームは、標準ストリームより多くの設定でインスタンス化されますが、特にバッファサイズ制約とヒューリスティックが重要です。これらの設定により、Stream Manager は最適メモリ量を割り当て、データ転送要求に優先順位をつけることができます。

バッファ制約

一部の設定は、ユーザーにより指定されるメモリ関連の制約です。バッファサイズは直接指定することが可能です。Stream Manager にバッファサイズを選択させたいけれども制限内にとどめたい場合は、最小限のバッファサイズまたはブロックサイズ、あるいは両方を指定することができます。バッファサイズはブロックサイズの倍数になります。

Tip: バッファ制約はオプションであり、通常 Stream Manager がストリーミングメモリを最適に管理できるようにすることを目的で使用するべきではありません。サウンドエンジンは、一部プラットフォーム上でのデコードハードウェアを使用する時に、バッファ制約を使用します。これらのデコーダは、特定のバイトアラインメント(ブロックサイズ)と最小バッファサイズで、一度に2つのバッファにアクセスする必要があります。

Default Streaming Manager Information

現在の実装では、カスタム自動ストリームバッファサイズがデバイス粒度を超えることはできません。(粒度に関する詳細は Audiokinetic ストリームマネージャ初期化設定 を参照。)

ヒューリスティック

Stream Manager によるスケジューリングとメモリ割り当て実行を支援するためにヒューリスティックが提供される必要があります。自動ストリームヒューリスティックは、作成時にストリームごとに指定されますが、最適な動作のために非常に重要です。AK::IAkAutoStream::GetHeuristics() や AK::IAkAutoStream::SetHeuristics() を介して、いつでもクエリや変更が可能です。

  • スループット:平均スループットは、特定のストリームに対して既に利用可能なデータをどれだけ持っているか認識しているため、I/Oスケジューラのデッドラインとして変換します。これは、標準ストリームの操作ごとのデッドラインヒューリスティックに相当します。
  • プライオリティ(優先度):これは通常、アプリケーションがストレージデバイスが提供できるより大きい帯域幅を必要とする場合に使用されます。この場合、Stream Manager は優先度の高いストリームの要求を履行します。標準ストリームの操作ごとの優先ヒューリスティックに相当します。
  • ループ:ループするストリーム内でループ位置を指定することができます。これにより、Stream Manager のメモリ管理を支援することができます。ループが解放された場合、ヒューリスティックを “非ループ” に設定(uLoopEnd を 0 に設定)することをお勧めします。これは単なるヒューリスティックであることに注意してください:ストリーム位置は、クライアントが SetPosition() を呼ばない限り変更されません。しかし、ループヒューリスティックに関する予期しない位置の変更は、通常データのフラッシュにつながります。
  • uMinClientBuffers: これは、クライアントが同時にどれぐらいのバッファを保持しようとしているかを示します。通常、バッファは同時に1つだけ保持されるべきです。時として、同時に2つのバッファを保持するよう要求される場合があります。この場合には、uMinClientBuffers を2に設定してください。Stream Manager は少なくとも( uMinClientBuffers + 1)のバッファを使用してストリームをバッファリングする必要があります。uMinClientBuffers(デフォルト値)に 0 を指定するのは 1 と同等であることに注意してください。

一般的な注意点とその他の考慮事項

ブロックサイズ

Stream Manager は、バッファサイズがブロックサイズの倍数であることを確認するために、バッファサイズの選択に先立って特定ファイルのブロックサイズを低レベル I/O にクエリします。従って、自動ストリームのユーザーは、ストリームを別の位置へ強制しない限り、低レベルのブロックサイズを意識する必要はありません。この場合、 AK::IAkAutoStream::GetBlockSize() から取得したブロックサイズ、または、 AK::IAkAutoStream::SetPosition() が返す実際の絶対オフセットを考慮する必要があります。

ストリーム位置

ストリーム位置は、ユーザーの観点から評価され、Get/SetPosition() メソッドによりクエリおよび設定されます。Stream Manager のバッファへ低レベル I/O から転送されるデータは、位置の計算では考慮されません。このデータは、バッファがユーザーにより解放される時に更新されます。AK::IAkAutoStream::SetPosition() が呼び出された時に、低レベル I/O から既に転送されてしまったデータは、通常フラッシュされます。

注釈: ユーザーは、可能な限り AK::IAkAutoStream::SetPosition() の呼び出しを避けてください。これを使用する必要がある場合は、できるだけ早期に呼び出す必要があります。例えば、サウンドエンジンで、ループ中のサウンドソース(音源)は、Stream Manager からバッファを取得する時に、ループエンドがこのバッファに含まれているかどうかを確認します。そうであれば、AK::IAkAutoStream::SetPosition() が直ちに(つまり、ReleaseBuffer() のかなり前に)呼び出され、無用なデータをストリーミングするリスクを最小限に抑えようとします。また、ループヒューリスティックを指定すると、内部スケジューラが低レベル I/O への要求に関してより優れた意思決定をできるよう支援することができます。

Tip: AK::IAkAutoStream::SetPosition() は、バッファがロックされた状態でもロックされていない状態でも呼び出し可能ですが、無用にデータをストリーミングするリスクを最小限に抑えるため、できるだけ早期の位置変更をお勧めします。ストリームを適切に停止することで、帯域幅の浪費を最小限に抑えることができます。

AK::IAkAutoStream::SetPosition() は、クライアントに保持されているバッファを解放しません。クライアントは、ReleaseBuffer() を明示的に呼び出すことにより、バッファがいつ解放されるかを決定します。AK::IAkAutoStream::SetPosition() は、実際に GetBuffer() への次の呼び出しに対してクライアントが期待する位置を示します。

AK::IAkAutoStream::GetPosition() は、現在クライアントが保持している最初のバッファの位置を返します。クライアントがバッファを保持していない場合、GetBuffer() への次の呼び出しで付与されるバッファの位置を返します。

AK::IAkAutoStream::GetBuffer() のAK_NoMoreData リターンコードは、ストリームの位置から決定されます。AK::IAkAutoStream::GetPosition() に返される out_bEndOfStream オプションフラグも、ストリーム位置にバインドされています。これは、以下のような場合のみ True を返します:

  • uLoopEnd ヒューリスティックが0(ループしない)に設定されている。
  • 低レベルI/Oから転送されるデータがない。
  • ユーザーがすべてのバッファを解放した。

保留中の低レベル操作でブロックするメソッド

自動ストリームAPIは、 AK::IAkAutoStream::GetBuffer() 呼び出しをブロックするのを除き、ユーザーが低レベル I/Oとの保留中のトランザクションを決してブロックしないようにデザインされています。 AK::IAkAutoStream::Destroy() さえもブロックされません。通常、ストリームが破棄されたにも関わらず、低レベルI/Oと相互作用をしている場合、低レベルI/Oとの現在の転送が終了するまでこのストリームは内部で行き続けます。

Manager のオーバーライド

Stream Manager 全体をオーバーライドするには、ゲームタイトルは IAkStreamMgr.h で定義されているすべてのインターフェースを実装している必要があります。実装は、このセクションの他の部分で説明されている各規則に従わなければなりません。

スタティックライブラリ AkStreamMgr.lib をゲーム独自のスタティックライブラリと置き換えることができます。作成関数やその他の実装に固有な設定や定義、例えば低レベルI/O APIなどは、AkStreamMgrModule.h にあるので、Stream Manager の一部ではありません。

サウンドエンジンとのリンケージ

サウンドエンジンは、インラインスタティック AK::IAkStreamMgr::Get() メソッドを呼び出すことで Stream Manager にアクセスします。これは、AK::IAkStreamMgr のプロテクトメンバとして定義されている、AK::IAkStreamMgr インターフェースへのポインタを返します。カスタム実装が宣言する必要があるのは変数1つのみで( AK::IAkStreamMgr::m_pStreamMgr )、リンケージは自動的に行われます。Stream Manager とサウンドエンジンが、同一の実行可能ファイルまたはDLL内でリンクされていない場合は、 AK::IAkStreamMgr::m_pStreamMgr が __dllexport 属性を持っている必要があります。AKSTREAMMGR_API マクロは、カスタム Stream Manager ライブラリのコンパイラ設定で定義されている AKSTREAMMGR_EXPORTS と一緒に使用可能です。

プロファイリング

プロファイリングインターフェースも、サウンドエンジンの非 AK_OPTIMIZED バージョンとのリンクを可能にするために実装される必要があります。このインターフェースはかなり自己説明的です。これを実装することで、Wwiseでのプロファイリングが可能になります。プロファイリングが必要でない場合は、 AK::IAkStreamMgr::GetStreamMgrProfile() がNULLを返し、インターフェースは空のコードで実装されます。この場合、Wwise では、プロファイリング情報は Wwise に表示されません。

サンプルコード

以下のコードは、文章で説明するよりもコードでの方がより良く説明可能ないくつかの考慮事項を示すためのもので。Stream Manager の実装をオーバーライドまたは変更する場合に特に便利です。このコードは、特に注意する必要のある事項を指摘できるよう、故意にボリュームのあるものになっています。

AkUInt32 uLoopStart
Set to the start of loop (byte offset from the beginning of the stream) for streams that loop,...
Definition: IAkStreamMgr.h:126
static IAkStreamMgr * Get()
Definition: IAkStreamMgr.h:697
@ AK_Fail
The operation failed.
Definition: AkTypes.h:202
virtual AkUInt64 GetPosition(bool *out_pbEndOfStream)=0
@ AK_DataReady
The provider has available data.
Definition: AkTypes.h:227
virtual AKRESULT ReleaseBuffer()=0
AkUInt32 uLoopEnd
Set to the end of loop (byte offset from the beginning of the stream) for streams that loop,...
Definition: IAkStreamMgr.h:127
virtual void GetInfo(AkStreamInfo &out_info)=0
virtual AkUInt32 GetBlockSize()=0
virtual AKRESULT SetPosition(AkInt64 in_iMoveOffset, AkMoveMethod in_eMoveMethod, AkInt64 *out_piRealOffset)=0
AKRESULT
Standard function call result.
Definition: AkTypes.h:199
@ AK_NoDataReady
The provider does not have available data.
Definition: AkTypes.h:228
@ AK_OpenModeReadWrite
Read and write access
Definition: IAkStreamMgr.h:76
@ AK_NoMoreData
No more data is available from the source.
Definition: AkTypes.h:212
@ AK_OpenModeRead
Read-only access
Definition: IAkStreamMgr.h:73
char AkOSChar
Generic character string
Definition: AkTypes.h:60
virtual AkStmStatus GetStatus()=0
virtual AKRESULT Read(void *in_pBuffer, AkUInt32 in_uReqSize, bool in_bWait, AkPriority in_priority, AkReal32 in_fDeadline, AkUInt32 &out_uSize)=0
@ AK_MoveBegin
Move offset from the start of the stream
Definition: IAkStreamMgr.h:65
#define NULL
Definition: AkTypes.h:46
@ AK_Success
The operation was successful.
Definition: AkTypes.h:201
static const AkPriority AK_DEFAULT_PRIORITY
Default sound / I/O priority
Definition: AkTypes.h:180
virtual AKRESULT SetHeuristics(const AkAutoStmHeuristics &in_heuristics)=0
AkReal32 fThroughput
Average throughput in bytes/ms
Definition: IAkStreamMgr.h:125
virtual AKRESULT SetPosition(AkInt64 in_iMoveOffset, AkMoveMethod in_eMoveMethod, AkInt64 *out_piRealOffset)=0
virtual AKRESULT CreateAuto(const AkOSChar *in_pszFileName, AkFileSystemFlags *in_pFSFlags, const AkAutoStmHeuristics &in_heuristics, AkAutoStmBufSettings *in_pBufferSettings, IAkAutoStream *&out_pStream, bool in_bSyncOpen)=0
@ AK_MoveCurrent
Move offset from the current stream position
Definition: IAkStreamMgr.h:66
AkForceInline void AkSleep(AkUInt32 in_ulMilliseconds)
Platform Independent Helper
virtual AKRESULT CreateStd(const AkOSChar *in_pszFileName, AkFileSystemFlags *in_pFSFlags, AkOpenMode in_eOpenMode, IAkStdStream *&out_pStream, bool in_bSyncOpen)=0
virtual void Destroy()=0
virtual AKRESULT GetBuffer(void *&out_pBuffer, AkUInt32 &out_uSize, bool in_bWait)=0
virtual void GetHeuristics(AkAutoStmHeuristics &out_heuristics)=0
int64_t AkInt64
Signed 64-bit integer
uint64_t AkUInt64
Unsigned 64-bit integer
@ AK_StmStatusCompleted
Operation completed / Automatic stream reached end
Definition: IAkStreamMgr.h:53
AkStmStatus
Stream status.
Definition: IAkStreamMgr.h:51
AkUInt64 uSize
Total stream/file size in bytes
Definition: IAkStreamMgr.h:118
virtual AKRESULT Start()=0
uint32_t AkUInt32
Unsigned 32-bit integer
@ AK_StmStatusError
The low-level I/O reported an error
Definition: IAkStreamMgr.h:56
virtual void Destroy()=0
AkPriority priority
The stream priority. it should be between AK_MIN_PRIORITY and AK_MAX_PRIORITY (included).
Definition: IAkStreamMgr.h:132
virtual void Cancel()=0
virtual AKRESULT Write(void *in_pBuffer, AkUInt32 in_uReqSize, bool in_bWait, AkPriority in_priority, AkReal32 in_fDeadline, AkUInt32 &out_uSize)=0
Automatic streams heuristics.
Definition: IAkStreamMgr.h:124
virtual AkUInt64 GetPosition(bool *out_pbEndOfStream)=0
@ AK_StmStatusCancelled
Operation cancelled
Definition: IAkStreamMgr.h:55

このページはお役に立ちましたか?

サポートは必要ですか?

ご質問や問題、ご不明点はございますか?お気軽にお問い合わせください。

サポートページをご確認ください

あなたのプロジェクトについて教えてください。ご不明な点はありませんか。

プロジェクトを登録していただくことで、ご利用開始のサポートをいたします。

Wwiseからはじめよう