Package cn. c; import java. io. file; import java. io. IOException; import android. app. activity; import android. media. mediaPlayer; import android. media. mediaPlayer. onCompletionListener; import android. media. mediaPlayer. onErrorListener; import android. media. mediaPlayer. onInfoListener; import android. media. mediaPlayer. onPreparedListener; import android. media. mediaPlayer. onSeekCompleteListener; import android. media. MediaPlayer. onVideoSizeChangedListener; import android. OS. bundle; import android. OS. environment; import android. view. display; import android. view. surfaceHolder; import android. view. surfaceView; import android. widget. linearLayout;/*** video playback using MidiaPlayer * involves SurfaceView and SurfaceHolder * MediaPlayer, which are mainly used to play audio, it does not provide an output interface for the output image * now we can use the SurfaceView control to combine it with MediaPlayer * To achieve video output. if SurfaceView is used to draw (Display) a video *, then Su RfaceHolder is the * process used to control SurfaceView: * 1 sets the video * mMediaPlayer to be played by the MediaPlayer. setDataSource (path); * 2 set the video output interface of the MediaPlayer * mMediaPlayer. setDisplay (mSurfaceHolder); * 3 MediaPlayer for decoding * mMediaPlayer. prepareAsync (); * 4 MediaPlayer starts playing * mMediaPlayer. start (); * // *** reference: http://www.embedu.org/Column/Column503.htm * the general process of playing a video using MidiaPlayer: * Create A Player Object --> set the source of the video to be played --> * prepare for decoding the video --> start playing --> (pause/ Restart) Stop playing * corresponding to these processes, the related methods are defined in MediaPlayer; * Moreover, after these methods are called, The MediaPlayer can enter different states. * These methods and statuses are well understood. You can refer to them for details. * In addition, after you set the video data source for the video to be played, you need to decode the video (call the prepare () method). * This is a time-consuming operation, to avoid application blocking, * You can use its prepareAsync () method with the OnPreparedListener listener for asynchronous operations. * Note: Only after preparation for MediaPlayer is complete can you start playing the video. * MediaPlayer itself cannot display the video content. It can only control video playback. * if you want to use MediaPlayer to play the video, you also need to use SurfaceView to display the video * and play the video data decoded in the MediaPlayer in SurfaceView. You need to call MediaPlay SetDisplay () * in er accepts a SurfaceHolder object. You can use the SurfaceHolder object corresponding to * SurfaceView used for video playback as the parameter *. In this way, MediaPlayer and SurfaceView are associated. */public class MainActivity extends Activity implements OnCompletionListener, OnErrorListener, OnInfoListener, OnPreparedListener, OnSeekCompleteListener, OnVideoSizeChangedListener, SurfaceHolder. callback {private SurfaceView mSurfaceView; private SurfaceHolder mSurfaceHolder; pr Ivate Display mDisplay; private MediaPlayer mMediaPlayer; int videoWidth = 0; int videoHeight = 0; @ Override public void onCreate (Bundle savedInstanceState) {super. onCreate (savedInstanceState); setContentView (R. layout. main); mDisplay = getWindowManager (). getdefadisplay display (); mSurfaceView = (SurfaceView) findViewById (R. id. surfaceView); mSurfaceHolder = mSurfaceView. getHolder (); // SurfaceHolder is used to manage SurfaceVi Ew object // how is it managed? Use mSurfaceHolder // to add a callback, that is, addCallback. // This class implements SurfaceHolder. callback interface, so addCallback (this) // In SurfaceHolder. there are three methods in the Callback interface to manage the // SurfaceView object: // surfaceCreated () // surfaceChanged () // surfaceDestroyed () // Overview: surfaceHolder is mainly used to monitor the underlying situation of mSurfaceHolder. addCallback (this); mSurfaceHolder. setType (SurfaceHolder. SURFACE_TYPE_PUSH_BUFFERS); mMediaPlayer = new MediaPlayer (); mMediaPlayer. setOnCompletion Listener (this); mMediaPlayer. setOnErrorListener (this); mMediaPlayer. setOnInfoListener (this); mMediaPlayer. setOnPreparedListener (this); mMediaPlayer. setOnSeekCompleteListener (this); mMediaPlayer. setOnVideoSizeChangedListener (this); String path = Environment. getExternalStorageDirectory (). getPath () + File. separator + "Test_Movie.m4v"; try {// set the video mMediaPlayer to be played by the MediaPlayer. setDataSource (path);} catch (I LlegalArgumentException e) {e. printStackTrace (); finish ();} catch (IllegalStateException e) {e. printStackTrace (); finish ();} catch (IOException e) {e. printStackTrace (); finish () ;}// from SurfaceHolder. callback interface // this method is called when SurfaceView is created. public void surfaceCreated (SurfaceHolder holder) {// set the video output interface of the MediaPlayer. // This method is not called when only the audio is displayed but the video is not displayed. setDisplay (mSurfaceHolder); try {// prepare for playing and call mMediaPlayer. prepa ReAsync (); // After the method is executed, the overwritten // public void onPrepared (MediaPlayer mp) // Note: // you can also call prepare () decoding, but for a synchronous operation mMediaPlayer. prepareAsync ();} catch (Exception e) {e. printStackTrace (); finish () ;}// from SurfaceHolder. callback interface // when the width, height, or other parameters of SurfaceView change, this method is called public void surfaceChanged (SurfaceHolder holder, int format, int width, int height) {}// from SurfaceHolder. callback interface // this method is called when SurfaceView is destroyed EDestroyed (SurfaceHolder holder) {}// from MediaPlayer. onVideoSizeChangedListener API // call this method when the video width or height changes. public void onVideoSizeChanged (MediaPlayer mp, int width, int height) {}// from MediaPlayer. onSeekCompleteListener interface public void onSeekComplete (MediaPlayer mp) {}// from MediaPlayer. onPreparedListener interface // once this method is called, The MediaPlayer enters the "ready" status and is ready to start playing. // this field can be used to dynamically set the SurfaceView width and height !!! Public void onPrepared (MediaPlayer mediaPlayer) {videoWidth = mediaPlayer. getVideoWidth (); videoHeight = mediaPlayer. getVideoHeight (); if (videoWidth> mDisplay. getWidth () | videoHeight> mDisplay. getHeight () {float heightRatio = (float) videoHeight/(float) mDisplay. getHeight (); float widthRatio = (float) videoWidth/(float) mDisplay. getWidth (); if (heightRatio> 1 | widthRatio> 1) {if (heightRatio> widthRatio) {videoHeight = (int) Math. ceil (float) videoHeight/(float) heightRatio); videoWidth = (int) Math. ceil (float) videoWidth/(float) heightRatio);} else {videoHeight = (int) Math. ceil (float) videoHeight/(float) widthRatio); videoWidth = (int) Math. ceil (float) videoWidth/(float) widthRatio) ;}}// set the width and height of SurfaceView mSurfaceView. setLayoutParams (new LinearLayout. layoutParams (videoWidth, videoHeight); // The MediaPlayer starts playing the mediaPlayer. start ();} // from MediaPlayer. onInfoListener interface // This method will be called when specific information about the playing media is displayed or a warning is required. // For example, start buffering, buffer end, and download speed change (this row is awaiting verification)) // Summary: all these Info items are MediaPlayer. public boolean onInfo (MediaPlayer mp, int what, int extra) {if (what = MediaPlayer. MEDIA_INFO_BAD_INTERLEAVING) {// This prompt is displayed when audio and video data are incorrectly staggered. in a // correctly staggered media file, audio and video samples are arranged in sequence so that the video can be played effectively and stably.} if (what = MediaPlayer. MEDIA_INFO_NOT_SEEKABLE) {// This prompt is displayed when the media cannot be correctly located. // This means it may be an online stream} if (what = MediaPlayer. MEDIA_INFO_VIDEO_TRACK_LAGGING) {// This prompt is displayed when the device cannot play the video. // For example, the video is too complex or the bit rate is too high.} if (what = MediaPlayer. MEDIA_INFO_METADATA_UPDATE) {// This prompt will appear when the new metadata is available} if (what = MediaPlayer. MEDIA_INFO_UNKNOWN) {// other unknown message} return false;} // from MediaPlayer. onErrorListener interface // This method will be called when a MediaPlayer error occurs // There are only the following three errors. // conclusion: all these errors are MediaPlayer. MEDIA_ERROR. public boolean onError (MediaPlayer mp, int what, int extra) {if (what = MediaPlayer. MEDIA_ERROR_NOT_VALID_FOR_PROGRESSIVE_PLAYBACK) {System. out. println ("first error");} if (what = MediaPlayer. MEDIA_ERROR_SERVER_DIED) {System. out. println ("second error");} if (what = MediaPlayer. MEDIA_ERROR_UNKNOWN) {System. out. println ("third error");} return false;} // from MediaPlayer. onCompletionListener interface // this method is called when the MediaPlayer finishes playing the file. // you can perform other operations at this time, such as playing the next video public void onCompletion (MediaPlayer mp) {finish ();}}