Spec-Zone .ru
спецификации, руководства, описания, API
Содержание документации

<Содержание

Глава 5: Получение Аудио

Получение обращается к процессу получения сигнала снаружи компьютера. Общее применение аудио получения записывает, такие как запись ввода микрофона к звуковому файлу. Однако, получение не синонимично с записью, потому что запись подразумевает, что приложение всегда сохраняет звуковые данные, это входит. Приложение, которое получает аудио, не обязательно хранит аудио. Вместо этого это могло бы сделать что-то с данными, поскольку это входит — те, которые записывают речь в текст — но тогда отбрасывают каждый буфер аудио, как только это заканчивается с тем буфером.

Как обсуждено в Главе 2, "Краткий обзор Выбранного Пакета," типичная система звукового входа в реализации API Звука Java состоит из:

  1. Входной порт, такой как порт микрофона или строка - в порту, который подает его входящие аудиоданные в:
  2. Микшер, который помещает входные данные в:
  3. Один или более целевые строки данных, от которых приложение может получить данные.

    Обычно, только один входной порт может быть открытым за один раз, но микшер звукового входа, который смешивает аудио от многократных портов, также возможен. Другой сценарий состоит из микшера, который не имеет никаких портов, но вместо этого получает его звуковой вход по сети.

    TargetDataLine интерфейс был представлен кратко под "Иерархией Интерфейса Строки" в Главе 2, "Краткий обзор Выбранного Пакета." TargetDataLine непосредственно походит SourceDataLine интерфейс, который был обсужден экстенсивно в Главе 4, "Воспроизводя Аудио." Вспомните что SourceDataLine интерфейс состоит из:

Точно так же TargetDataLine состоит из:

Установка TargetDataLine

Процесс получения целевой строки данных был описан в Главе 3, "Получая доступ к Ресурсам Аудиосистемы," но мы повторяем это здесь для удобства:

TargetDataLine line;
DataLine.Info info = new DataLine.Info(TargetDataLine.class, 
format); // format is an AudioFormat object
if (!AudioSystem.isLineSupported(info)) { // Handle the error ... } // Obtain and open the line. try {
line = (TargetDataLine) AudioSystem.getLine(info);
line.open(format); } catch (LineUnavailableException ex) { // Handle the error ... }
Вы могли вместо этого вызвать Mixer's getLine метод, а не AudioSystem's.

Как показано в этом примере, как только Вы получили целевую строку данных, Вы резервируете ее для использования своего приложения, вызывая DataLine метод open, точно, как был описан в случае строки исходных данных в Главе 4, "Воспроизводя Аудио." Версия единственного параметра open метод заставляет буфер строки иметь размер по умолчанию. Можно вместо этого установить размер буфера согласно потребностям своего приложения, вызывая версию с двумя параметрами:

    void open(AudioFormat format, int bufferSize) 
Выбирая размер буфера, имейте в виду компромисс между задержками, понесенными длинными буферами, с одной стороны, и риском разрывов в аудио, если буферы настолько коротки, что невозможно получить данные достаточно быстро с другой стороны. Получая аудио, Вы рискуете переполнением данных, если Вы не вытягиваете данные от заполненных буферов достаточно быстро. Если переполнение произойдет, то некоторые из полученных данных будут отброшены, который, вероятно, вызовет слышимые щелчки и пропуски в звуке. Это - противоположная ситуация от воспроизведения, где Вы рискуете потерей значимости данных, которая может привести к разрывам в звуке. (См. Главу 4, "Воспроизводя Аудио," для больше при выборе буферных размеров.)

Чтение Данных от TargetDataLine

Как только строка открыта, это готово начать получать данные, но это еще не активно. Чтобы фактически начать аудио получение, используйте DataLine метод start. Это начинает поставлять входные аудиоданные буферу строки для Вашего приложения, чтобы читать. Ваше приложение должно вызвать, запускаются только, когда это готово начать читать из строки; иначе большая обработка тратится впустую на заполнение накопительного буфера, только чтобы иметь это переполнение (то есть, данные отбрасывания).

Чтобы начать получать данные от буфера, вызвать TargetDataLine's метод чтения:

int read(byte[] b, int offset, int length) 
Этот метод пытается читать length байты данных в массив b, запуск в позиции байта offset в массиве. Метод возвращает число байтов фактически чтение.

Как с SourceDataLine's write метод, можно запросить больше данных чем, фактически помещается в буфер, потому что блоки метода до требуемого объема данных были поставлены, даже если Вы запрашиваете ценность многих буферов данных.

Чтобы избежать иметь Ваше приложение зависают во время записи, можно вызвать метод чтения в пределах цикла, пока Вы не получили весь звуковой вход, как в этом примере:

// Assume that the TargetDataLine, line, has already
// been obtained and opened.
ByteArrayOutputStream out  = new ByteArrayOutputStream();
int numBytesRead;
byte[] data = new byte[line.getBufferSize() / 5];

// Begin audio capture.
line.start();

// Here, stopped is a global boolean set by another thread.
while (!stopped) {
   // Read the next chunk of data from the TargetDataLine.
   numBytesRead =  line.read(data, 0, data.length);
   // Save this chunk of data.
   out.write(data, 0, numBytesRead);
}     
Заметьте, что в этом примере, размер байтового массива, в который читаются данные, устанавливается быть одной пятой размер буфера строки. Если Вы вместо этого делаете это столь же большим как буфер строки и попытка считать весь буфер, Вы должны быть очень точными в своей синхронизации, потому что данные будут выведены, если микшер должен поставить данные строке, в то время как Вы читаете из этого. При использовании некоторой части размера буфера строки, как показано здесь, Ваше приложение будет более успешным в совместном использовании доступа к буферу строки с микшером.

read метод TargetDataLine берет три параметра: байтовый массив, смещение в массив, и число байтов входных данных, которые требуется считать. В этом примере третьим параметром является просто длина Вашего байтового массива. read метод возвращает число байтов, которые были фактически считаны в Ваш массив.

Как правило, Вы читаете данные из строки в цикле, как в этом примере. В пределах while цикл, каждый блок полученных данных обрабатывается любым способом, является подходящим для приложения — здесь, это пишется a ByteArrayOutputStream. Не показанный здесь использование отдельного потока, чтобы установить булевскую переменную stopped, который завершает цикл. Значение этой булевской переменной могло бы быть установлено в true когда пользователь щелкает по Кнопке остановки, и также когда слушатель получает a CLOSE или STOP событие от строки. Слушатель необходим для CLOSE события и рекомендуемый для STOP события. Иначе, если строка останавливается так или иначе без остановленного, устанавливаемого в true, while цикл получит нулевые байты на каждой итерации, работая быстро и тратя впустую циклы ЦП. Более полный пример кода показал бы цикл, повторно вводимый, если получение становится активным снова.

Как со строкой исходных данных, возможно истощить или сбросить целевую строку данных. Например, если Вы запишете ввод к файлу, то Вы будете, вероятно, хотеть вызвать drain метод, когда пользователь щелкает по Кнопке остановки. drain метод заставит остающиеся данные микшера быть поставленными целевому буферу строки данных. Если Вы не истощаете данные, полученный звук, могло бы казаться, был бы усеченным преждевременно в конце.

Могли бы быть некоторые случаи, где Вы вместо этого хотите сбросить данные. В любом случае, если Вы ни не сбросите, ни истощите данные, то это оставят в микшере. Это означает, что, когда получение возобновляет, будет некоторый оставшийся звук в начале новой записи, которая могла бы быть нежелательным. Может быть полезно, тогда, сбросить целевую строку данных прежде, чем перезапустить получение.

Контроль Состояния Строки

Поскольку TargetDataLine интерфейс расширяется DataLine, целевые строки данных генерируют события таким же образом, строки исходных данных делают. Можно зарегистрировать объект получить события всякий раз, когда целевая строка данных открывается, завершения, запускается, или остановки. Для получения дополнительной информации см. "Контроль Состояния Строки" в Главе 4, "Воспроизводя Аудио."

Обработка Входящего Аудио

Как некоторые строки исходных данных, у целевых строк данных некоторых микшеров есть обрабатывающие сигнал средства управления, такие как усиление, панорамирование, реверберация, или средства управления демонстрационного уровня. Входные порты могли бы иметь подобные средства управления, особенно получить средства управления. Для получения дополнительной информации по тому, как определить, есть ли у строки такие средства управления, и как использовать их, если она делает, см. Главу 6, "Обрабатывая Аудио со Средствами управления."

 


Oracle и/или его филиалы Авторское право © 1993, 2011, Oracle и/или его филиалы. Все права защищены.
Свяжитесь с Нами