mediacodec解析mp4( 四 )


if (doRender){
callback.preRender(mBufferInfo.presentationTimeUs)
}
//释放资源
decoder.releaseOutputBuffer(decoderStatus,doRender)
if (doRender ) {
callback.postRender()
}
if (doLoop){
Log.d(TAG,"")
extractor.seekTo(0, MediaExtractor.SEEK_TO_CLOSEST_SYNC)
inputDOne= false
decoder.flush()
}
}
}
}
}
}
class PlayTask(
player: MediaCodecDemo,
) :
Runnable {
private val mPlayer: MediaCodecDemo
private var mDoLoop = false
private var mThread: Thread? = null
private val mLocalHandler: LocalHandler
private val mStopLock = java.lang.Object()
private var mStopped = false
fun setLoopMode(loopMode: Boolean) {
mDoLoop = loopMode
}
fun execute() {
mThread = Thread(this, "Movie Player")
mThread?.start()
}
fun waitForStop() {
synchronized(mStopLock) {
while (!mStopped) {
try {
mStopLock.wait()
} catch (ie: InterruptedException) {
// discard
}
}
}
}
override fun run() {
try {
mPlayer.play()
} catch (ioe: IOException) {
throw RuntimeException(ioe)
} finally {
// tell anybody waiting on us that we're done
synchronized(mStopLock) {
mStopped = true
mStopLock.notifyAll()
}
}
}
private class LocalHandler : Handler() {
override fun handleMessage(msg: Message) {
val what = msg.what
when (what) {
MSG_PLAY_STOPPED -> {
val fb: PlayerFeedback = msg.obj as PlayerFeedback
fb.playbackStopped()
}
else -> throw RuntimeException("Unknown msg $what")
}
}
}
companion object {
private const val MSG_PLAY_STOPPED = 0
}
/**
* Prepares new PlayTask.
*
* @param player The player object, configured with control and output.
* @param feedback UI feedback object.
*/
init {
mPlayer = player
mLocalHandler = LocalHandler()
}
}
}
interface PlayerFeedback {
fun playbackStopped()
}

interface FrameCallback {
fun preRender(presentationTimeUsec: Long)
fun postRender()
fun loopReset()
}
package com.example.videodemo
import android.util.Log
import com.example.videodemo.SpeedControlCallback
class SpeedControlCallback : FrameCallback {
private var mPrevPresentUsec: LOng= 0
private var mPrevMonoUsec: LOng= 0
private var mFixedFrameDurationUsec: LOng= 0
private var mLoopReset = false
fun setFixedPlaybackRate(fps: Int) {
mFixedFrameDuratiOnUsec= ONE_MILLION / fps
}
// runs on decode thread
override fun preRender(presentationTimeUsec: Long) {
if (mPrevMOnoUsec== 0L) {
mPrevMOnoUsec= System.nanoTime() / 1000
mPrevPresentUsec = presentationTimeUsec
} else {
// Compute the desired time delta between the previous frame and this frame.
var frameDelta: Long
if (mLoopReset) {
mPrevPresentUsec = presentationTimeUsec - ONE_MILLION / 30
mLoopReset = false
}
frameDelta = if (mFixedFrameDurationUsec != 0L) {


mFixedFrameDurationUsec
} else {
presentationTimeUsec - mPrevPresentUsec
}
if (frameDelta < 0) {
Log.w(TAG, "Weird, video times went backward")
frameDelta = 0
} else if (frameDelta == 0L) {


Log.i(TAG, "Warning: current frame and previous frame had same timestamp")
} else if (frameDelta > 10 * ONE_MILLION) {


Log.i(
TAG, "Inter-frame pause was " + frameDelta / ONE_MILLION +
"sec, capping at 5 sec"
)
frameDelta = 5 * ONE_MILLION

推荐阅读