Android Audio
System operacyjny Android zapewnia szeroką obsługę multimediów, obejmujących zarówno dźwięk, jak i wideo. Ten przewodnik koncentruje się na dźwiękach w systemie Android i obejmuje odtwarzanie i nagrywanie dźwięku przy użyciu wbudowanych klas odtwarzacza audio i rejestratora, a także interfejsu API audio niskiego poziomu. Obejmuje również pracę ze zdarzeniami audio emitowanych przez inne aplikacje, dzięki czemu deweloperzy mogą tworzyć dobrze zachowywane aplikacje.
Omówienie
Nowoczesne urządzenia przenośne przyjęły funkcje, które wcześniej wymagały dedykowanych urządzeń – kamer, odtwarzaczy muzycznych i rejestratorów wideo. W związku z tym struktury multimedialne stały się pierwszą klasą funkcji w mobilnych interfejsach API.
System Android zapewnia rozbudowaną obsługę multimediów. W tym artykule omówiono pracę z dźwiękiem w systemie Android i omówiono następujące tematy
Odtwarzanie dźwięku za pomocą odtwarzacza MediaPlayer — używanie wbudowanej
MediaPlayer
klasy do odtwarzania dźwięku, w tym lokalnych plików audio i strumieniowego przesyłania strumieniowego plików audio z klasąAudioTrack
.Nagrywanie dźwięku — używanie wbudowanej
MediaRecorder
klasy do nagrywania dźwięku.Praca z powiadomieniami audio — za pomocą powiadomień dźwiękowych można tworzyć dobrze zachowywane aplikacje, które prawidłowo reagują na zdarzenia (takie jak przychodzące połączenia telefoniczne), zawieszając lub anulując dane wyjściowe audio.
Praca z dźwiękem niskiego poziomu — odtwarzanie dźwięku
AudioTrack
przy użyciu klasy przez zapisywanie bezpośrednio w buforach pamięci. Nagrywanie dźwiękuAudioRecord
przy użyciu klasy i odczytywania bezpośrednio z buforów pamięci.
Wymagania
Ten przewodnik wymaga systemu Android 2.0 (poziom interfejsu API 5) lub nowszego. Należy pamiętać, że debugowanie dźwięku w systemie Android musi być wykonywane na urządzeniu.
Należy zażądać RECORD_AUDIO
uprawnień w AndroidManifest.XML:
Odtwarzanie dźwięku za pomocą klasy MediaPlayer
Najprostszym sposobem odtwarzania dźwięku w systemie Android jest wbudowana klasa MediaPlayer .
MediaPlayer
program może odtwarzać pliki lokalne lub zdalne, przekazując ścieżkę pliku. Jednak MediaPlayer
jest bardzo wrażliwe na stan i wywoływanie jednej z jego metod w niewłaściwym stanie spowoduje zgłoszenie wyjątku. Ważne jest, aby wchodzić w interakcję z usługą MediaPlayer
w podanej poniżej kolejności, aby uniknąć błędów.
Inicjowanie i odtwarzanie
Odtwarzanie dźwięku z MediaPlayer
programem wymaga następującej sekwencji:
Utwórz wystąpienie nowego obiektu MediaPlayer .
Skonfiguruj plik do odtwarzania za pomocą metody SetDataSource .
Wywołaj metodę Prepare , aby zainicjować odtwarzacz.
Wywołaj metodę Start , aby rozpocząć odtwarzanie dźwięku.
Poniższy przykład kodu ilustruje to użycie:
protected MediaPlayer player;
public void StartPlayer(String filePath)
{
if (player == null) {
player = new MediaPlayer();
} else {
player.Reset();
player.SetDataSource(filePath);
player.Prepare();
player.Start();
}
}
Wstrzymywanie i wznawianie odtwarzania
Odtwarzanie można wstrzymać, wywołując metodę Pause :
player.Pause();
Aby wznowić wstrzymane odtwarzanie, wywołaj metodę Start . Spowoduje to wznowienie działania z wstrzymanej lokalizacji w odtwarzaniu:
player.Start();
Wywołanie metody Stop na odtwarzaczu kończy trwające odtwarzanie:
player.Stop();
Gdy gracz nie jest już potrzebny, zasoby muszą zostać zwolnione przez wywołanie metody Release :
player.Release();
Używanie klasy MediaRecorder do rejestrowania dźwięku
Corollary do MediaPlayer
nagrywania dźwięku w systemie Android jest klasa MediaRecorder . Podobnie jak w przypadku MediaPlayer
elementu , jest ona wrażliwa na stan i przechodzi przez kilka stanów, aby przejść do punktu, w którym można rozpocząć nagrywanie. Aby można było nagrywać dźwięk, RECORD_AUDIO
należy ustawić uprawnienie. Aby uzyskać instrukcje dotyczące ustawiania uprawnień aplikacji, zobacz Praca z AndroidManifest.xml.
Inicjowanie i nagrywanie
Nagrywanie dźwięku za pomocą instrukcji MediaRecorder
wymaga wykonania następujących kroków:
Utwórz wystąpienie nowego obiektu MediaRecorder .
Określ, które urządzenie sprzętowe ma być używane do przechwytywania danych wejściowych dźwięku za pośrednictwem metody SetAudioSource .
Ustaw format audio pliku wyjściowego przy użyciu metody SetOutputFormat . Aby uzyskać listę obsługiwanych typów audio, zobacz Obsługiwane formaty multimediów systemu Android.
Wywołaj metodę SetAudioEncoder , aby ustawić typ kodowania audio.
Wywołaj metodę SetOutputFile , aby określić nazwę pliku wyjściowego, do którego są zapisywane dane dźwiękowe.
Wywołaj metodę Prepare, aby zainicjować rejestrator.
Wywołaj metodę Start, aby rozpocząć nagrywanie.
Poniższy przykładowy kod ilustruje następującą sekwencję:
protected MediaRecorder recorder;
void RecordAudio (String filePath)
{
try {
if (File.Exists (filePath)) {
File.Delete (filePath);
}
if (recorder == null) {
recorder = new MediaRecorder (); // Initial state.
} else {
recorder.Reset ();
recorder.SetAudioSource (AudioSource.Mic);
recorder.SetOutputFormat (OutputFormat.ThreeGpp);
recorder.SetAudioEncoder (AudioEncoder.AmrNb);
// Initialized state.
recorder.SetOutputFile (filePath);
// DataSourceConfigured state.
recorder.Prepare (); // Prepared state
recorder.Start (); // Recording state.
}
} catch (Exception ex) {
Console.Out.WriteLine( ex.StackTrace);
}
}
Zatrzymywanie nagrywania
Aby zatrzymać nagrywanie, wywołaj metodę Stop
w pliku MediaRecorder
:
recorder.Stop();
Czyszczenie
Po zatrzymaniu MediaRecorder
wywołaj metodę Reset , aby przywrócić stan bezczynności:
recorder.Reset();
MediaRecorder
Gdy element nie jest już potrzebny, jego zasoby muszą zostać zwolnione przez wywołanie metody Release:
recorder.Release();
Zarządzanie powiadomieniami audio
Klasa AudioManager
Klasa AudioManager zapewnia dostęp do powiadomień dźwiękowych, które poinformują aplikacje o wystąpieniu zdarzeń dźwiękowych. Ta usługa zapewnia również dostęp do innych funkcji dźwiękowych, takich jak sterowanie głośnością i trybem dzwonka. Aplikacja AudioManager
umożliwia aplikacji obsługę powiadomień dźwiękowych w celu sterowania odtwarzaniem dźwięku.
Zarządzanie fokusem audio
Zasoby audio urządzenia (wbudowanego odtwarzacza i rejestratora) są współużytkowane przez wszystkie uruchomione aplikacje.
Koncepcyjnie jest to podobne do aplikacji na komputerze stacjonarnym, gdzie tylko jedna aplikacja ma fokus klawiatury: po wybraniu jednej z uruchomionych aplikacji, klikając ją myszą, dane wejściowe klawiatury są przesyłane tylko do tej aplikacji.
Fokus audio jest podobny i uniemożliwia więcej niż jednej aplikacji odtwarzanie lub nagrywanie dźwięku w tym samym czasie. Jest to bardziej skomplikowane niż fokus klawiatury, ponieważ jest dobrowolne — aplikacja może zignorować fakt, że obecnie nie ma fokusu audio i odtwarzania niezależnie od tego — i ponieważ istnieje różne typy fokusu audio, które można zażądać. Jeśli na przykład żądającego dźwięk ma być odtwarzany tylko przez bardzo krótki czas, może zażądać przejściowego fokusu.
Fokus audio może być udzielany natychmiast lub początkowo odmawiany i udzielany później. Jeśli na przykład aplikacja żąda fokusu audio podczas rozmowy telefonicznej, zostanie odrzucona, ale fokus może być udzielany po zakończeniu rozmowy telefonicznej. W takim przypadku odbiornik jest zarejestrowany w celu odpowiedniego reagowania, jeśli fokus audio zostanie zabrany. Żądanie fokusu audio służy do określania, czy jest ok, aby odtwarzać lub nagrywać dźwięk.
Aby uzyskać więcej informacji na temat koncentracji uwagi audio, zobacz Zarządzanie fokusem audio.
Rejestrowanie wywołania zwrotnego dla fokusu audio
Rejestrowanie wywołania zwrotnego FocusChangeListener
z obiektu IOnAudioChangeListener
jest ważną częścią uzyskiwania i wydawania fokusu audio. Dzieje się tak, ponieważ przyznanie fokusu audio może zostać odroczone do późniejszego czasu. Na przykład aplikacja może zażądać odtwarzania muzyki, gdy trwa rozmowa telefoniczna. Fokus audio nie zostanie udzielony do momentu zakończenia rozmowy telefonicznej.
Z tego powodu obiekt wywołania zwrotnego jest przekazywany jako parametr do GetAudioFocus
metody AudioManager
, i jest to wywołanie, które rejestruje wywołanie zwrotne. Jeśli fokus audio jest początkowo odrzucany, ale później udzielany, aplikacja jest informowana przez wywołanie OnAudioFocusChange
zwrotne. Ta sama metoda służy do określania aplikacji, że fokus audio jest zabierany.
Po zakończeniu korzystania z zasobów dźwiękowych aplikacja wywołuje AbandonFocus
metodę AudioManager
, a następnie ponownie przekazuje wywołanie zwrotne. Spowoduje to wyrejestrowanie wywołania zwrotnego i wydanie zasobów audio, dzięki czemu inne aplikacje mogą uzyskać fokus audio.
Żądanie fokusu audio
Kroki wymagane do żądania zasobów dźwiękowych urządzenia są następujące:
Uzyskaj dojście do usługi systemowej
AudioManager
.Utwórz wystąpienie klasy wywołania zwrotnego.
Zażądaj zasobów dźwiękowych urządzenia, wywołując metodę
RequestAudioFocus
wAudioManager
pliku . Parametry to obiekt wywołania zwrotnego, typ strumienia (muzyka, połączenie głosowe, pierścień itp.) oraz typ żądanego prawa dostępu (zasoby audio mogą być żądane chwilowo lub przez nieokreślony okres).Jeśli żądanie zostanie przyznane,
playMusic
metoda jest wywoływana natychmiast, a dźwięk zaczyna odtwarzać.Jeśli żądanie zostanie odrzucone, nie zostanie podjęta żadna dalsza akcja. W takim przypadku dźwięk będzie odtwarzany tylko wtedy, gdy żądanie zostanie przyznane później.
Poniższy przykładowy kod przedstawia następujące kroki:
Boolean RequestAudioResources(INotificationReceiver parent)
{
AudioManager audioMan = (AudioManager) GetSystemService(Context.AudioService);
AudioManager.IOnAudioFocusChangeListener listener = new MyAudioListener(this);
var ret = audioMan.RequestAudioFocus (listener, Stream.Music, AudioFocus.Gain );
if (ret == AudioFocusRequest.Granted) {
playMusic();
return (true);
} else if (ret == AudioFocusRequest.Failed) {
return (false);
}
return (false);
}
Zwalnianie fokusu audio
Po zakończeniu odtwarzania ścieżki wywoływana AbandonFocus
jest metoda przy AudioManager
użyciu metody . Dzięki temu inna aplikacja może uzyskać zasoby audio urządzenia. Inne aplikacje otrzymają powiadomienie o zmianie fokusu audio, jeśli zarejestrowali własne odbiorniki.
Interfejs API audio niskiego poziomu
Interfejsy API audio niskiego poziomu zapewniają większą kontrolę nad odtwarzaniem i nagrywaniem dźwięku, ponieważ wchodzą w interakcje bezpośrednio z buforami pamięci zamiast przy użyciu identyfikatorów URI plików. Istnieje kilka scenariuszy, w których takie podejście jest preferowane. Takie scenariusze obejmują:
Podczas odtwarzania z zaszyfrowanych plików audio.
Podczas odtwarzania kolejnych krótkich klipów.
Przesyłanie strumieniowe audio.
AudioTrack, klasa
Klasa AudioTrack używa interfejsów API audio niskiego poziomu do nagrywania i jest niskim poziomem odpowiednika MediaPlayer
klasy.
Inicjowanie i odtwarzanie
Aby odtwarzać dźwięk, należy utworzyć wystąpienie nowego wystąpienia AudioTrack
programu . Lista argumentów przekazana do konstruktora określa sposób odtwarzania przykładu audio zawartego w buforze. Argumenty to:
Typ strumienia — głos, dzwonek, muzyka, system lub alarm.
Częstotliwość — częstotliwość próbkowania wyrażona w Hz.
Konfiguracja kanału — mono lub stereo.
Format audio — kodowanie 8-bitowe lub 16-bitowe.
Rozmiar buforu — w bajtach.
Tryb buforu — przesyłanie strumieniowe lub statyczne.
Po zakończeniu AudioTrack
budowy wywoływana jest metoda Play, aby skonfigurować ją do rozpoczęcia gry. Zapisywanie buforu audio na AudioTrack
początku odtwarzania:
void PlayAudioTrack(byte[] audioBuffer)
{
AudioTrack audioTrack = new AudioTrack(
// Stream type
Stream.Music,
// Frequency
11025,
// Mono or stereo
ChannelOut.Mono,
// Audio encoding
Android.Media.Encoding.Pcm16bit,
// Length of the audio clip.
audioBuffer.Length,
// Mode. Stream or static.
AudioTrackMode.Stream);
audioTrack.Play();
audioTrack.Write(audioBuffer, 0, audioBuffer.Length);
}
Wstrzymanie i zatrzymywanie odtwarzania
Wywołaj metodę Wstrzymania, aby wstrzymać odtwarzanie:
audioTrack.Pause();
Wywołanie metody Stop spowoduje trwałe zakończenie odtwarzania:
audioTrack.Stop();
Czyszczenie
AudioTrack
Gdy element nie jest już potrzebny, jego zasoby muszą zostać zwolnione przez wywołanie polecenia Release:
audioTrack.Release();
Klasa AudioRecord
Klasa AudioRecord jest odpowiednikiem AudioTrack
po stronie nagrywania. Podobnie jak AudioTrack
, używa buforów pamięci bezpośrednio, zamiast plików i identyfikatorów URI. Wymaga RECORD_AUDIO
to ustawienia uprawnienia w manifeście.
Inicjowanie i nagrywanie
Pierwszym krokiem jest utworzenie nowego obiektu AudioRecord . Lista argumentów przekazana do konstruktora zawiera wszystkie informacje wymagane do nagrywania. W przeciwieństwie do klasy , AudioTrack
gdzie argumenty są w dużej mierze wyliczane, równoważne argumenty w AudioRecord
elemencie są liczbami całkowitymi. Są to:
Sprzętowe źródło danych wejściowych audio, takie jak mikrofon.
Typ strumienia — głos, dzwonek, muzyka, system lub alarm.
Częstotliwość — częstotliwość próbkowania wyrażona w Hz.
Konfiguracja kanału — mono lub stereo.
Format audio — kodowanie 8-bitowe lub 16-bitowe.
Rozmiar buforu w bajtach
Po skonstruowaniu AudioRecord
metody StartRecording jest wywoływana. Teraz jest gotowy do rozpoczęcia nagrywania. Funkcja AudioRecord
stale odczytuje bufor audio dla danych wejściowych i zapisuje te dane wejściowe w pliku audio.
void RecordAudio()
{
byte[] audioBuffer = new byte[100000];
var audRecorder = new AudioRecord(
// Hardware source of recording.
AudioSource.Mic,
// Frequency
11025,
// Mono or stereo
ChannelIn.Mono,
// Audio encoding
Android.Media.Encoding.Pcm16bit,
// Length of the audio clip.
audioBuffer.Length
);
audRecorder.StartRecording();
while (true) {
try
{
// Keep reading the buffer while there is audio input.
audRecorder.Read(audioBuffer, 0, audioBuffer.Length);
// Write out the audio file.
} catch (Exception ex) {
Console.Out.WriteLine(ex.Message);
break;
}
}
}
Zatrzymywanie nagrania
Wywołanie metody Stop kończy nagrywanie:
audRecorder.Stop();
Czyszczenie
AudioRecord
Gdy obiekt nie jest już potrzebny, wywołanie metody Release zwalnia wszystkie skojarzone z nim zasoby:
audRecorder.Release();
Podsumowanie
System operacyjny Android zapewnia zaawansowaną platformę do odtwarzania, nagrywania i zarządzania dźwiękiem. W tym artykule opisano sposób odtwarzania i rejestrowania dźwięku przy użyciu wysokiego poziomu MediaPlayer
i MediaRecorder
klas. Następnie dowiesz się, jak używać powiadomień audio do udostępniania zasobów dźwiękowych urządzenia między różnymi aplikacjami. Na koniec omówiliśmy sposób odtwarzania i rejestrowania dźwięku przy użyciu interfejsów API niskiego poziomu, które interfejsy bezpośrednio z buforami pamięci.