Я разрабатываю приложение React Native, которое получает аудиоданные PCM через WebSocket, декодирует их из строки base64 и пытается воспроизвести их в реальном времени, используя настройку AVAudioEngine в Swift. Несмотря на подтверждение того, что аудиоданные получены правильно путем записи в файл и его воспроизведения в Audacity, воспроизведение в моем приложении представляет собой только шум. Я не могу определить причину.
Код JavaScript:
const handleAudioOutput = async (event) => {
const arrayBuffer = event.data;
const base64Data = Buffer.from(arrayBuffer).toString('base64');
// await RNFS.appendFile(`${RNFS.DocumentDirectoryPath}/audioData.raw`, base64Data, 'base64');
audioPlayer.current.playAudioData(base64Data);
};
useEffect(() => {
audioOutputWs.current = new WebSocket(audioOutputUrl);
audioOutputWs.current.onopen = () => console.log("Audio output ws open");
audioOutputWs.current.binaryType = 'arraybuffer';
audioOutputWs.current.onmessage = handleAudioOutput;
}, []);
На быстрой стороне мы буферизуем полученный звук и воспроизводим из буфера в другом потоке.
Реализация на быстрой стороне:
import Foundation
import AVFoundation
@objc(AudioPlayer)
class AudioPlayer: NSObject {
private var audioEngine: AVAudioEngine
private var audioPlayerNode: AVAudioPlayerNode
private var audioFormat: AVAudioFormat
private var audioQueue: [Data]
private let queueLock = NSLock()
private var isProcessing = false
override init() {
audioEngine = AVAudioEngine()
audioPlayerNode = AVAudioPlayerNode()
// Try using a common sample rate and format
let sampleRate: Double = 24000.0
let channelCount: AVAudioChannelCount = 1
let commonFormat: AVAudioCommonFormat = .pcmFormatInt16
guard let format = AVAudioFormat(commonFormat: commonFormat, sampleRate: sampleRate, channels: channelCount, interleaved: false) else {
fatalError("Failed to create AVAudioFormat")
}
audioFormat = format
audioQueue = []
super.init()
audioEngine.attach(audioPlayerNode)
// If I did format: audioFormat the constructor would crash So I found the below solution from some corner of the internet.
audioEngine.connect(audioPlayerNode, to: audioEngine.outputNode, format: AVAudioFormat.init(standardFormatWithSampleRate: 24000.0, channels: 1)!)
do {
try audioEngine.start()
} catch {
print("Failed to start AVAudioEngine: \(error)")
}
DispatchQueue.global(qos: .background).async {
self.processAudioQueue()
}
}
@objc(multiply:withB:withResolver:withRejecter:)
func multiply(a: Float, b: Float, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
resolve(a * b)
}
@objc(add:withB:withResolver:withRejecter:)
func add(a: Float, b: Float, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
resolve(a + b)
}
@objc(playAudioData:withResolver:withRejecter:)
func playAudioData(base64String: String, resolve: RCTPromiseResolveBlock, reject: RCTPromiseRejectBlock) -> Void {
guard let data = Data(base64Encoded: base64String) else {
reject("error", "Invalid base64 string", nil)
return
}
queueLock.lock()
audioQueue.append(data)
queueLock.unlock()
resolve(true) // Immediately resolve to not block the JS thread
}
private func processAudioQueue() {
isProcessing = true
while isProcessing {
queueLock.lock()
if !audioQueue.isEmpty {
let data: Data = audioQueue.removeFirst()
queueLock.unlock()
let frameCount = AVAudioFrameCount(data.count / MemoryLayout.size)
guard let audioBuffer = AVAudioPCMBuffer(pcmFormat: audioFormat, frameCapacity: frameCount) else {
continue
}
audioBuffer.frameLength = frameCount
// Safe memory transfer using buffer pointers
data.withUnsafeBytes { rawBufferPointer in
guard let bufferPointer = rawBufferPointer.bindMemory(to: Int16.self).baseAddress else {
return
}
guard let channelData = audioBuffer.int16ChannelData else {
return
}
for frameIndex in 0..
Подробнее здесь: https://stackoverflow.com/questions/787 ... -websocket
Во время воспроизведения аудиоданных PCM, передаваемых через WebSocket, в React Native и Swift наблюдается только шум ⇐ IOS
-
- Похожие темы
- Ответы
- Просмотры
- Последнее сообщение
-
-
Ударный шум при воспроизведении части волнового файла с интерфейсом ALSA PCM
Anonymous » » в форуме Linux - 0 Ответы
- 16 Просмотры
-
Последнее сообщение Anonymous
-
-
-
5.1 PCM Sound to 5.1 Dolby Digital в Windows C ++ для воспроизведения SPDIF
Anonymous » » в форуме C++ - 0 Ответы
- 4 Просмотры
-
Последнее сообщение Anonymous
-