ストリーミングサウンドウェーブ
Voice Activity Detection (VAD)については、このページを参照してください。
ストリーミングサウンドウェーブは、再生中でも動的にオーディオデータを追加できるタイプのインポートされたサウンドウェーブです。巻き戻しなどのインポートされたサウンドウェーブと同じ機能を提供し、SoundCueなどで使用できます。
ストリーミグサウンドウェーブの作成
まずストリーミング サウンドウェーブを作成する必要があります。早期破棄を防ぐため、強力な参照として扱う必要があることに注意してください(例:Blueprintsで別の変数に割り当てるか、C++でUPROPERTY()
を使用する)。
- Blueprint
- C++
UStreamingSoundWave* StreamingSoundWave = UStreamingSoundWave::CreateStreamingSoundWave();
音声波形の再生
その後、その音声波形を再生することができます。ただし、今すぐ行う必要はなく、後で音声波形の再生を開始することも可能です。
オーディオデータの事前割り当て
オプションとして、新しいオーディオデータが追加されるたびにPCMバッファ全体を再割り当てするのを避けるために、オーディオデータ(バイト)を事前に割り当てることができます。
- Blueprint
- C++
// Assuming StreamingSoundWave is a UE reference to a UStreamingSoundWave object (or its derived type, such as UCapturableSoundWave)
StreamingSoundWave->PreAllocateAudioData(12582912, FOnPreAllocateAudioDataResultNative::CreateWeakLambda(this, [StreamingSoundWave](bool bSucceeded)
{
// Handle the result
}));
オーディオデータの追加
既存のバッファの末尾にオーディオデータを追加するには、動的にオーディオデータを追加するための適切な関数を使用します。再生はこれらの追加のキュー順に従って行われます。
- Blueprint
- C++
// Assuming StreamingSoundWave is a UE reference to a UStreamingSoundWave object (or its derived type, such as UCapturableSoundWave)
// Example of appending encoded audio data
TArray<uint8> AudioData = ...; // Fill with audio data
StreamingSoundWave->AppendAudioDataFromEncoded(AudioData, ERuntimeAudioFormat::Auto);
// Or, if you have raw audio data
TArray<uint8> RawAudioData = ...; // Fill with raw audio data
StreamingSoundWave->AppendAudioDataFromRAW(RawAudioData, ERuntimeRAWAudioFormat::Float32, 44100, 2);
加速または歪んだオーディオ再生の回避
サウンドウェーブの再生中にオーディオデータをストリーミングすると、特定のシナリオで再生が加速したり歪んだりする場合があります。この問題は通常、以下の状況で発生します:
- サウンドウェーブの再生が現在のバッファの終端近く/終端に達している
- 新しいオーディオデータがストリーミングサウンドウェーブに継続的にキューイングされている
- 再生が受信データストリームに追いついてしまう
オーディオデータの投入はいつでも問題なく停止できます。ただし、リアルタイムオーディオストリーミングなどの継続的なストリーミングが必要なシナリオでは、オーディオデータストリーミングの信頼性に応じて2つのアプローチがあります:
信頼性が高く一貫したストリーミングの場合: OnPopulateAudioState デリゲートを使用して、最初のチャンクを受信した直後に再生を開始します。
信頼性の低いストリーミング(ネットワーク問題、断続的な データ)の場合: OnPopulateAudioState がトリガーされた後でも追加の遅延を設け、再生開始前に大きなバッファを構築します。
- Blueprint
- C++
// Approach 1: For reliable streaming - start immediately after first chunk
bool bHasStartedPlayback = false;
StreamingSoundWave->OnPopulateAudioStateNative.AddWeakLambda(this, [this, &bHasStartedPlayback]()
{
if (!bHasStartedPlayback)
{
UGameplayStatics::PlaySound2D(GetWorld(), StreamingSoundWave);
bHasStartedPlayback = true;
}
});
// Approach 2: For unreliable streaming - add delay after first chunk
bool bHasStartedPlayback = false;
StreamingSoundWave->OnPopulateAudioStateNative.AddWeakLambda(this, [this, &bHasStartedPlayback]()
{
if (!bHasStartedPlayback)
{
// Add delay to build up buffer for unreliable streaming
GetWorld()->GetTimerManager().SetTimer(PlaybackDelayTimer, [this]()
{
UGameplayStatics::PlaySound2D(GetWorld(), StreamingSoundWave);
}, 0.5f, false); // Half-second delay
bHasStartedPlayback = true;
}
});
注記: オーディオデータの送信はいつでも停止しても再生に問題は発生しません。正確なアプローチはオーディオデータストリーミングの信頼性に依存します - 安定したストリームには即時再生を、信頼性の低いストリーム(例:ネットワーク接続問題)には追加のバッファリング遅延を使用してください。
使用例
最終的に、実装は次のようになるかもしれません:
- Blueprint
- C++
これはストリーミングサ ウンドウェーブにオーディオデータを追加する基本的なコード例です。
この例では、EXAMPLEMODULE
モジュール内のUAppendAudioClassExample
クラスにあるAppendAudioExample
関数を使用しています。
注: この例を正常に実行するには、** .Build.csファイルのPublicDependencyModuleNames
またはPrivateDependencyModuleNames
、およびプロジェクトの.uproject**ファイルにRuntimeAudioImporter
モジュールを追加してください。
#pragma once
#include "CoreMinimal.h"
#include "UObject/Object.h"
#include "AppendAudioClassExample.generated.h"
UCLASS(BlueprintType)
class EXAMPLEMODULE_API UAppendAudioClassExample : public UObject
{
GENERATED_BODY()
public:
UFUNCTION(BlueprintCallable)
void AppendAudioExample();
private:
// Please pay attention to making the StreamingSoundWave a hard reference, such as using UPROPERTY(), to prevent it from being prematurely garbage collected
UPROPERTY()
class UStreamingSoundWave* StreamingSoundWave;
};
#include "AppendAudioClassExample.h"
#include "Sound/StreamingSoundWave.h"
void UAppendAudioClassExample::AppendAudioExample()
{
// Create a streaming sound wave
StreamingSoundWave = UStreamingSoundWave::CreateStreamingSoundWave();
// Append audio data
TArray<uint8> StreamedAudioDataToAdd = ...; // Fill with audio data
StreamingSoundWave->AppendAudioDataFromEncoded(StreamedAudioDataToAdd, ERuntimeAudioFormat::Auto);
// Play the sound wave
UGameplayStatics::PlaySound2D(GetWorld(), StreamingSoundWave);
}
オーディオ状態のポピュレート時
OnPopulateAudioState デリゲートは OnPopulateAudioData と同様に機能しますが、ポピュレートされたオーディオデータをブロードキャストしません。これは、パフ ォーマンスを向上させるために、ポピュレートされたオーディオデータの配列を渡すことなく、オーディオデータがポピュレートされたタイミングを追跡したい場合に便利です。
- Blueprint
- C++
// Assuming StreamingSoundWave is a UE reference to a UStreamingSoundWave object (or its derived type, such as UCapturableSoundWave)
StreamingSoundWave->OnPopulateAudioStateNative.AddWeakLambda(this, [this]()
{
// Handle the result
});
PCMデータの操作
再生中のPCMデータにリアルタイムでアクセスするには、PCMデータ処理を参照してください。