Потоковая передача аудиоустройства Remote IO с одного iPhone на другой
Я нашел 3-4 примера, которые показывают использование аудиоустройств Remote IO. как здесь, здесь и т. д. Они скрывают аналоговые аудиоданные с микрофона iPhone, оцифровывают их и затем воспроизводят. До этого момента все работало нормально, и теперь у меня хорошее понимание аудиоустройств.
Теперь вместо того, чтобы воспроизводить записанное аудио, хранящееся в AudioBufferList на том же устройстве, я хочу передать его на другое устройство.
Ниже показано, как я конвертирую AudioBufferList в nsdata и отправляю его на другое устройство.
NSMutableDictionary *dict = [NSMutableDictionary dictionaryWithObject:@(bufferList->mNumberBuffers) forKey:@"buffersCount"];
NSMutableArray *buffers = [NSMutableArray array];
for ( int i=0; i< bufferList->mNumberBuffers; i++ ) {
NSData *data = [NSData dataWithBytes:bufferList->mBuffers[i].mData length:bufferList->mBuffers[i].mDataByteSize];
NSDictionary *obj = @{@"data":data, @"channels":@(bufferList->mBuffers[i].mNumberChannels)};
[buffers addObject:obj];
}
[dict setValue:buffers forKey:@"buffers"];
NSData *packet = [NSKeyedArchiver archivedDataWithRootObject:dict];
Ниже показано, как я преобразовываю nsdata обратно в AudioBufferList на принимающем устройстве и копирую его в tempBuffer, который затем воспроизводится.
NSDictionary *dict = (NSDictionary*) [NSKeyedUnarchiver unarchiveObjectWithData:voiceData];
int numberOfBuffers = [dict[@"buffersCount"] intValue];
AudioBufferList *audio = malloc(sizeof(AudioBufferList) + (numberOfBuffers-1)*sizeof(AudioBuffer));
if ( !audio ) {
return;
}
for (int i=0; i < audio->mNumberBuffers; i++) { // in practice we will only ever have 1 buffer, since audio format is mono
AudioBuffer buffer = audio->mBuffers[i];
NSLog(@"Buffer %d has %d channels and wants %d bytes of data.", i, (unsigned int)buffer.mNumberChannels, buffer.mDataByteSize);
// copy temporary buffer data to output buffer
UInt32 size = min(buffer.mDataByteSize, [iosAudio tempBuffer].mDataByteSize); // dont copy more data then we have, or then fits
memcpy(buffer.mData, [iosAudio tempBuffer].mData, size);
buffer.mDataByteSize = size; // indicate how much data we wrote in the buffer
}
Но на другом устройстве я ничего не слышу.
Пожалуйста, ознакомьтесь с тем, что может быть не так.
2 ответа
Вы не получили никаких данных из словаря, только количество буферов.
NSDictionary *dict = [NSKeyedUnarchiver unarchiveObjectWithData:data];
NSLog(@"%@", dict);
int numberOfBuffers = [dict[@"buffersCount"] intValue];
NSLog(@"%d", numberOfBuffers);
AudioBufferList *audioBufferList = (AudioBufferList *)malloc(sizeof(AudioBufferList));
if (NULL == audioBufferList) {
NSLog(@"*** malloc failure for allocating audioBufferList memory");
return;
}
audioBufferList->mNumberBuffers = (int)dict[@"buffersCount"];
for(NSDictionary *obj in dict[@"buffers"]){
NSMutableData *data = [NSMutableData dataWithData:obj[@"data"]];
audioBufferList->mBuffers[0].mNumberChannels = (int)obj[@"channels"];
audioBufferList->mBuffers[0].mDataByteSize = (int)[data length];
audioBufferList->mBuffers[0].mData = (AudioBuffer *)malloc([data length]);
if (NULL == audioBufferList->mBuffers[0].mData) {
NSLog(@"*** malloc failure for allocating mData memory");
return;
}
memcpy(audioBufferList->mBuffers[0].mData, [data mutableBytes], [data length]);
NSLog(@"Buffer has %d channels and wants %d bytes of data.", (unsigned int)audioBufferList->mBuffers[0].mNumberChannels, (unsigned int)audioBufferList->mBuffers[0].mDataByteSize);
}
Существует несколько способов открыть сетевое соединение между двумя устройствами. Вы хотите сделать это и просто упаковать данные в любом формате, который хотите, чтобы передать их с устройства A на устройство B.
Начните здесь: http://nshipster.com/multipeer-connectivity/