Error while trying to retrieve Metadata from a rem

2019-08-03 18:13发布

问题:

I'm working on a Radio Streming application for Android. The music is well recieved and played by the MediaPlayer class, but the problem is when I try to retrieve the Metadata, the App blocks and returns errors. This is the code:

package com.tests.mediaplayer1;
import java.io.IOException;
import android.media.AudioManager;
import android.media.MediaMetadataRetriever;
import android.media.MediaPlayer;
import android.os.Bundle;
import android.app.Activity;
import android.content.Context;
import android.util.Log;
import android.view.Menu;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.SeekBar;
import android.widget.SeekBar.OnSeekBarChangeListener;
import android.widget.TextView;

public class MainActivity extends Activity {

private Button btn_prev;
private Button btn_pause;
private Button btn_play;
private Button btn_next;
private TextView txt_song_title;
private SeekBar seekBar_volume;

private MediaPlayer mediaPlayer;
private MediaMetadataRetriever retriever;
private String url = "http://support.k-designed.net/test-z/music/Accordossie.mp3"; 
private AudioManager audioManager;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    btn_prev = (Button) findViewById(R.id.btn_prev);
    btn_pause = (Button) findViewById(R.id.btn_pause);
    btn_play = (Button) findViewById(R.id.btn_play);
    btn_next = (Button) findViewById(R.id.btn_next);
    txt_song_title = (TextView) findViewById(R.id.txt_song_title);
    seekBar_volume = (SeekBar) findViewById(R.id.seekBar_volume);
    mediaPlayer = new MediaPlayer();
    mediaPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC);

     audioManager = (AudioManager)getSystemService(Context.AUDIO_SERVICE);
     int maxVolume = audioManager.getStreamMaxVolume(AudioManager.STREAM_MUSIC);
     int curVolume = audioManager.getStreamVolume(AudioManager.STREAM_MUSIC);

     seekBar_volume.setMax(maxVolume);
     seekBar_volume.setProgress(curVolume);

     seekBar_volume.setOnSeekBarChangeListener(new OnSeekBarChangeListener() {

        @Override
        public void onStopTrackingTouch(SeekBar seekBar) {
            // TODO Auto-generated method stub

        }

        @Override
        public void onStartTrackingTouch(SeekBar seekBar) {
            // TODO Auto-generated method stub

        }

        @Override
        public void onProgressChanged(SeekBar seekBar, int progress,
                boolean fromUser) {
            audioManager.setStreamVolume(AudioManager.STREAM_MUSIC, progress, 0);

        }
    });

    btn_play.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(View v) {
            try {
                mediaPlayer.setDataSource(url);
                retriever.setDataSource(url);
                mediaPlayer.prepare(); // might take long! (for buffering, etc)
                mediaPlayer.start();
                txt_song_title.setText(retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_TITLE));
            } catch(Exception e) {
                e.printStackTrace();
            }
        }
    });

    btn_pause.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(View v) {
            mediaPlayer.pause();

        }
    });
}

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    // Inflate the menu; this adds items to the action bar if it is present.
    getMenuInflater().inflate(R.menu.main, menu);
    return true;
}
  }

And this is the error I get:

 java.lang.IllegalStateException
at android.media.MediaPlayer.setDataSource(Native Method)
at com.tests.mediaplayer1.MainActivity$2.onClick(MainActivity.java:84)
at android.view.View.performClick(View.java:2485)
at android.view.View$PerformClick.run(View.java:9080)
at android.os.Handler.handleCallback(Handler.java:587)
at android.os.Handler.dispatchMessage(Handler.java:92)
at android.os.Looper.loop(Looper.java:130)
at android.app.ActivityThread.main(ActivityThread.java:3687)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:507)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:867)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:625)
at dalvik.system.NativeStart.main(Native Method)

回答1:

From the error code, we can observe the reported error as below

java.lang.IllegalStateException
at android.media.MediaPlayer.setDataSource(Native Method)

If you refer to the native implementation of MediaPlayer, IllegalStateException is thrown when MediaPlayer object is null.

From your source, if we check for retriever, we can observe that you have declared this variable, but haven't created an object. In your sources, please try the following code before creating mediaPlayer object.

retreiver = new MediaMetadataRetriever();

With this change, retriever object would be created and your call to setDataSource i.e. retriever.setDataSource(url); would be successful.