Boteco Digital

Reproduzindo áudio no Android com MediaPlayer

A classe MediaPlayer é utilizada para tocar uma boa variedade de formatos de áudio e vídeo, podendo reproduzir áudio armazenados nos recursos da aplicação (raw resources), no sdcard do dispositivo ou no formato de stream vindo de uma conexão de internet.

O modo mais fácil é armazenando o conteúdo a ser reproduzido dentro da pasta de recursos da aplicação, para isso crie a pasta raw dentro do seu projeto e coloque seu conteúdo lá, no nosso exemplo foi “musica.mp3”.

MediaPlayer musica = MediaPlayer.create(this, R.raw.musica);
musica.play();

Algo que vale lembrar é que o MediaPlayer funciona como uma máquina de estados conforme o diagrama abaixo e os métodos que podemos chamar para trocar os estados(mais detalhes). Ao criar o MediaPlayer através do método create ele já o deixa no estado prepared.

mediaplayer_state_diagram

Também podemos reproduzir áudio armazenado no cartão de memória(sdcard) e não podemos nos esquecer de adicionar a permissão de leitura no sdcard dentro do arquivo AndroidManifest.xml.

<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />

Vamos ao código:

try {
	Uri uri = Uri.parse( Environment.getExternalStorageDirectory().getAbsolutePath()+"/Music/zumbis_do_espaco__cemiterio_maldito.mp3" ) ;
	musica = new MediaPlayer();
    musica.setAudioStreamType(AudioManager.STREAM_MUSIC);
	musica.setDataSource( getApplicationContext() , uri);
	musica.prepare();
	musica.start();
} catch (IllegalArgumentException e) {
	e.printStackTrace();
} catch (SecurityException e) {
	e.printStackTrace();
} catch (IllegalStateException e) {
	e.printStackTrace();
} catch (IOException e) {
	e.printStackTrace();
}

Na linha 2 criamos um objeto Uri para identificar nosso arquivo que queremos reproduzir, lembrando que utilizamos o Environment.getExternalStorageDirectory().getAbsolutePath() para pegar o caminho absoluto da raiz do sdcard. Na lina 3 criamos um objeto MediaPlayer().

Na linha 4 configuramos o MediaPlayer para stream de áudio.

Na linha 5 configuramos a fonte de dados, passando o contexto da aplicação e a uri que identifica o recurso a ser reproduzido.

Na linha 6 chamamos prepare() que deixa o objeto pronto para reprodução(isso pode levar algum tempo). E na linha 7 ele é iniciado.

Para reproduzir através da internet não é muito diferente, apenas criamos uma nova uri e não podemos esquecer de dar permissão para o aplicativo acessar a internet.

<uses-permission android:name="android.permission.INTERNET" />

Segue o código para reprodução pela internet.

try {
  	Uri uri = Uri.parse( "http://www.botecodigital.info/exemplos/audio/battlestargalatica_main_tite.mp3" ) ;
   	musica = MediaPlayer.create(this, uri);
   	musica.setAudioStreamType(AudioManager.STREAM_MUSIC);
	musica.setDataSource( getApplicationContext() , uri );
	musica.prepare();
	musica.start();
} catch (IllegalArgumentException e) {
	e.printStackTrace();
} catch (SecurityException e) {
	e.printStackTrace();
} catch (IllegalStateException e) {
	e.printStackTrace();
} catch (IOException e) {
	e.printStackTrace();
}

Segue alguns métodos importantes de MediaPlayer:

isPlaying(): Verifica se existe um áudio/vídeo tocando.

getDuration(): Retorna a duração do arquivo em milissegundos.

getCurrentPosition(): Retorna a posição atual da reprodução em milissegundos.

stop(): Para a reprodução.

release() : libera o recurso associado ao MediaPlayer

seekTo(int): Posiciona a reprodução na posição passada por parâmetro.

Uma funcionalidade associada a um player de música muito utilizada é acompanhar o tempo de duração em uma barra de progresso e para isso devemos criar um processo separado que verifique o quanto da música já foi reproduzida e atualizar o processo da tela(UI Thread), para isso utilizamos o objeto Handler para entregar as thread de atualização para o processo de tela já que nenhum processo externo pode atualizar a UI thread.

private Handler handler = new Handler();

public void play(View v){
    if( !musica.isPlaying() ){
         musica.start();
         progress.setMax( musica.getDuration() );
    	 tvPlay.setText("PAUSE");
         update = new Runnable() {
				
		@Override
		public void run() {
				
			SimpleDateFormat sdf = new SimpleDateFormat("mm:ss");
			Date d = new Date( musica.getCurrentPosition() );
					
			tvTempo.setText( sdf.format( d ) );
			progress.setProgress( musica.getCurrentPosition() );
			handler.postDelayed( this , 1000);
		}
	};
			
	handler.postDelayed(update, 100);
    }else{
    	musica.pause();
    	tvPlay.setText("PLAY");
    }
}

Na linha 1 criamos nosso objeto Handler, na linha 3 temos o método que será chamado quando o botão play do nosso aplicativo for acionado. Na linha 4 testamos se o áudio não está tocando !musica.isPlaying() então chamamos o método start() para iniciar o áudio(linha 5), configuramos o objeto SeekBar, que é a nossa barra de progresso do áudio, para que seu máximo seja a duração total do áudio que esta sendo reproduzido(linha 6), e mudamos o texto do botão de play para pause(linha 7).

Na linha 8 é onde realmente fazemos a parte importante, criamos uma classe interna anônima que implementa a interface Runnable declarando o método run. Este método é o que irá atualizar os componentes de interface para modificar a barra de progresso(SeekBar) e TextView com o tempo decorrido da música, pego através da chamado do método getCurrentPosition(). Dentro do próprio método run realizamos a chamada do método postDelayed do objeto Handler, este método faz uma entrega “atrasada” de uma thread para a UI Thread executar recebendo como parâmetros um Runnable que irá ser executado e o tempo de “atraso” desta execução em milissegundos. Como estamos chamando o método postDelayed dentro do método que ele mesmo irá executar criamos uma “espécie de loop” ou recursão que irá atualizar constantemente a interface em intervalos constantes.

Na linha 22 fazemos a primeira chamada ao método postDelayed para iniciar o nosso ciclo.

Para baixar um exemplo “meia boca” clique aqui.

Espero que tenha ajudado. 🙂

Tags
Categorias Android
comments powered by Disqus