Ответ 1
AVAudioPlayer очень мала для игрового аудио. Решение AudioQueue или OpenAL путем адаптации одного из примеров - это, безусловно, путь. Таким образом, латентность гораздо более контролируема.
У меня есть игра с высокой интенсивностью игры, в которую я хотел бы добавить звуки. Кажется, что есть три основных варианта: (1) AVAudioPlayer
, (2) Очереди аудио и (3) OpenAL. Я ненавижу писать страницы низкоуровневого кода, просто чтобы воспроизвести образец, чтобы я хотел использовать AVAudioPlayer
. Проблема в том, что она, кажется, убивает performace - я сделал простое измерение, используя CFAbsoluteTimeGetCurrent
, а сообщение play
, по-видимому, займет от 9 до 30 мс для завершения. Это довольно жалко, учитывая, что 25 мс == 40 кадров в секунду.
Конечно, существует метод prepareToPlay
, который должен ускорить процесс. Вот почему я написал простой класс, который держит несколько AVAudioPlayer
в своем распоряжении, готовит их заранее, а затем воспроизводит образец с помощью подготовленного игрока. Никакой сигары, все же это займет около 20 мс, о котором я упоминал выше.
Такая производительность непригодна для игр, поэтому что вы используете для воспроизведения звуков с достойной производительностью на iPhone? Я делаю что-то не так с AVAudioPlayer
? Вы воспроизводите звуки с помощью звуковых очередей? (Ive написал нечто похожее на AVAudioPlayer до выхода 2.2, и я бы с удовольствием позаботился об этом.) Используете ли вы OpenAL? Если да, есть ли простой способ воспроизведения звуков с помощью OpenAL, или вам нужно писать страницы кода?
Обновление: Да, воспроизведение звуков с помощью OpenAL довольно просто.
AVAudioPlayer очень мала для игрового аудио. Решение AudioQueue или OpenAL путем адаптации одного из примеров - это, безусловно, путь. Таким образом, латентность гораздо более контролируема.
Если вы вызываете play
в основном потоке, попробуйте запустить его в отдельном потоке. То, что я закончил, это:
#include <dispatch/dispatch.h>
dispatch_queue_t playQueue = dispatch_queue_create("com.example.playqueue", NULL);
AVAudioPlayer* player = ...
dispatch_async(playQueue, ^{
[player play];
});
который фиксировал худшее из затухания частоты кадров, которое я испытывал.
Я использую OpenAL и классы, которые поставляются с примером кода CrashLanding. До сих пор он отлично работал, чтобы воспроизводить сэмплы и воспроизводить музыку с петлями в одно и то же время. В настоящее время я изучаю, как освободить память, которую я выделил для звука (.wav файл), когда, например, я хочу воспроизвести какую-то интро-музыку только один раз.
Используйте CocosDenshion - это бесплатно, легко и работает. Он обертывает AVAudioPlayer
для фоновых дорожек и OpenAL для звуков.
Вы хотите проверить буферизацию с помощью используемой вами реализации? Это может быть как-то связано с задержкой в 20 мс, которую вы испытываете. т.е. попытаться воспроизвести размер буфера.