/*
 * ServeStream: A HTTP stream browser/player for Android
 * Copyright 2012 William Seemann
 * 
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package net.sourceforge.servestream.player;

import android.os.Handler;
import android.os.Parcel;
import android.os.Parcelable;
import android.util.Log;
import android.view.SurfaceHolder;

import java.io.IOException;

import net.sourceforge.servestream.utils.URLUtils;
import net.sourceforge.servestream.service.MediaPlaybackService;

/**
 * Provides a unified interface for dealing with midi files and
 * other media files.
 */
public class FFmpegMediaPlayer extends AbstractMediaPlayer implements Parcelable {
	private static final String TAG = FFmpegMediaPlayer.class.getName();
	
	private FFmpegPlayer mMediaPlayer = new FFmpegPlayer();
    private Handler mHandler;
    private boolean mIsInitialized = false;

    public FFmpegMediaPlayer() {
        super();
    }

    public void setDataSource(String path, boolean isLocalFile) {
        try {
            mMediaPlayer.reset();
            mMediaPlayer.setOnPreparedListener(onPreparedListener);
            mMediaPlayer.setOnCompletionListener(completionListener);
            mMediaPlayer.setOnErrorListener(errorListener);            
            if (isLocalFile) {
                mMediaPlayer.setDataSource(path);
            	mMediaPlayer.prepare();
            } else {
            	try {
                    mMediaPlayer.setDataSource(URLUtils.encodeURL(path));
            		mMediaPlayer.prepareAsync();
            	} catch (IllegalStateException e) {
            		//setDataSource(path, isLocalFile);
            	}
            }
            Log.v(TAG, "Preparing media plyer");
        } catch (IOException ex) {
        	Log.v(TAG, "Error initializing");
            mIsInitialized = false;
            mHandler.sendMessageDelayed(mHandler.obtainMessage(MediaPlaybackService.PLAYER_ERROR), 2000);
        } catch (IllegalArgumentException ex) {
        	Log.v(TAG, "Error initializing");
            mIsInitialized = false;
            mHandler.sendMessageDelayed(mHandler.obtainMessage(MediaPlaybackService.PLAYER_ERROR), 2000);
        }
    }
        
    public boolean isInitialized() {
        return mIsInitialized;
    }

    public void start() {
        Log.v(TAG, "MultiPlayer.start called");
        mMediaPlayer.start();
    }

    public void stop() {
        mMediaPlayer.reset();
        mIsInitialized = false;
    }

    /**
     * You CANNOT use this player anymore after calling release()
     */
    public void release() {
        stop();
        mMediaPlayer.release();
    }
        
    public void pause() {
        mMediaPlayer.pause();
    }
        
    public void setHandler(Handler handler) {
        mHandler = handler;
    }

    FFmpegPlayer.OnPreparedListener onPreparedListener = new FFmpegPlayer.OnPreparedListener() {
		public void onPrepared(FFmpegPlayer mp) {
			
			Log.v(TAG, "media player is prepared");
	        mIsInitialized = true;
			mHandler.sendEmptyMessage(MediaPlaybackService.PLAYER_PREPARED);
		}
    };
    
    FFmpegPlayer.OnCompletionListener completionListener = new FFmpegPlayer.OnCompletionListener() {
        public void onCompletion(FFmpegPlayer mp) {
            
        	Log.v(TAG, "onCompletionListener called");
        	
            // Acquire a temporary wakelock, since when we return from
            // this callback the MediaPlayer will release its wakelock
            // and allow the device to go to sleep.
            // This temporary wakelock is released when the RELEASE_WAKELOCK
            // message is processed, but just in case, put a timeout on it.
            if (mIsInitialized) {
            	mHandler.sendEmptyMessage(MediaPlaybackService.TRACK_ENDED);
            }
        }
    };

    FFmpegPlayer.OnErrorListener errorListener = new FFmpegPlayer.OnErrorListener() {
        public boolean onError(FFmpegPlayer mp, int what, int extra) {
        	Log.d(TAG, "Error: " + what + "," + extra);
        	
            switch (what) {
            case FFmpegPlayer.MEDIA_ERROR_SERVER_DIED:
                mIsInitialized = false;
                mMediaPlayer.release();
                mMediaPlayer = new FFmpegPlayer(); 
                mHandler.sendMessageDelayed(mHandler.obtainMessage(MediaPlaybackService.SERVER_DIED), 2000);
                return true;
            default:
                mIsInitialized = false;
                mHandler.sendEmptyMessage(MediaPlaybackService.PLAYER_ERROR);
                break;
            }
            return false;
        }
    };

    public long duration() {
        return mMediaPlayer.getDuration();
    }

    public long position() {
        return mMediaPlayer.getCurrentPosition();
    }

    public long seek(long whereto) {
        mMediaPlayer.seekTo((int) whereto);
        return whereto;
    }

    public void setVolume(float vol) {
        mMediaPlayer.setVolume(vol, vol);
    }

    public void setDisplay(SurfaceHolder holder) {
    	mMediaPlayer.setDisplay(holder);
    }
    
	public int describeContents() {
		return 0;
	}

	public void writeToParcel(Parcel dest, int flags) {

	}
	
	public static final Parcelable.Creator<FFmpegPlayer> CREATOR = new
	Parcelable.Creator<FFmpegPlayer>() {
	    public FFmpegPlayer createFromParcel(Parcel in) {
	    	return new FFmpegPlayer();
	    }

	    public FFmpegPlayer[] newArray(int size) {
	    	return new FFmpegPlayer[size];
	    }
	};
}
@@ -869,16 +869,117 @@
 ption;%0A%0A
+import net.sourceforge.servestream.transport.MMS;%0Aimport net.sourceforge.servestream.transport.MMSH;%0A
 import n
@@ -2003,24 +2003,198 @@
      %09try %7B%0A
+            %09%09if (path.startsWith(MMS.getProtocolName())) %7B%0A            %09%09%09path = path.replace(MMS.getProtocolName(), MMSH.getProtocolName());%0A            %09%09%7D%0A            %09%09%0A
             

Convert mms streams to mmsh (FFmpeg trac ticket #998)