簡體   English   中英

如何在旋轉時恢復exoplayer的狀態

[英]How to restore the state of exoplayer on rotations

我想恢復旋轉時exoplayer的狀態。 這就是我所做的。 但這是行不通的。 當我暫停應用程序然后恢復應用程序時,代碼運行良好。 但是旋轉時,視頻從頭開始。

import android.content.res.Configuration;
import android.net.Uri;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.v4.app.Fragment;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;

import com.google.android.exoplayer2.C;
import com.google.android.exoplayer2.DefaultLoadControl;
import com.google.android.exoplayer2.ExoPlayerFactory;
import com.google.android.exoplayer2.LoadControl;
import com.google.android.exoplayer2.SimpleExoPlayer;
import com.google.android.exoplayer2.extractor.DefaultExtractorsFactory;
import com.google.android.exoplayer2.extractor.ExtractorsFactory;
import com.google.android.exoplayer2.source.ExtractorMediaSource;
import com.google.android.exoplayer2.source.MediaSource;
import com.google.android.exoplayer2.trackselection.AdaptiveVideoTrackSelection;
import com.google.android.exoplayer2.trackselection.DefaultTrackSelector;
import com.google.android.exoplayer2.trackselection.TrackSelector;
import com.google.android.exoplayer2.ui.SimpleExoPlayerView;
import com.google.android.exoplayer2.upstream.BandwidthMeter;
import com.google.android.exoplayer2.upstream.DefaultBandwidthMeter;
import com.google.android.exoplayer2.upstream.DefaultHttpDataSourceFactory;
import com.google.android.exoplayer2.util.Util;
import com.squareup.picasso.Picasso;

import butterknife.BindView;
import butterknife.ButterKnife;

public class StepDetailFragment extends Fragment {

@BindView(R.id.step_full_description)
TextView fullDescriptionTv;
@BindView(R.id.step_thumbnail)
ImageView stepThumbnailView;
@BindView(R.id.playerView)
SimpleExoPlayerView stepVideoView;

SimpleExoPlayer exoPlayer;

private String mStepDescription;
private String mStepVideoURL;
private String mStepThumbnail;

private boolean startAutoPlay;
private int startWindow;
private long startPosition;

private static final String KEY_WINDOW = "window";
private static final String KEY_POSITION = "position";
private static final String KEY_AUTO_PLAY = "auto_play";

public void setmStepThumbnail(String mStepThumbnail) {
    this.mStepThumbnail = mStepThumbnail;
}

public void setmStepDescription(String mStepDescription) {
    this.mStepDescription = mStepDescription;
}

public void setmStepVideoURL(String mStepVideoURL) {
    this.mStepVideoURL = mStepVideoURL;
}

public StepDetailFragment() {

}


@Override

public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {


    if (savedInstanceState != null) {

        startAutoPlay = savedInstanceState.getBoolean(KEY_AUTO_PLAY);
        startWindow = savedInstanceState.getInt(KEY_WINDOW);
        startPosition = savedInstanceState.getLong(KEY_POSITION);
    } else {

        clearStartPosition();

    }

    View rootView = inflater.inflate(R.layout.fragment_recipe_step_detail, container, false);

    ButterKnife.bind(this,rootView);

    fullDescriptionTv.setText(mStepDescription);

    /*if(mStepThumbnail != null){
    Picasso.with(getContext()).load(mStepThumbnail).placeholder(R.drawable.ic_launcher_background)
            .error(R.drawable.ic_launcher_background)
            .into(stepThumbnailView);
    }*/

    if (mStepVideoURL != null) {

        initializePlayer();

    } else {
        Log.v("StepDetailFragment", "null url");
    }

    return rootView;

}

這是初始化播放器的方法。

private void initializePlayer() {
    if (exoPlayer == null) {
        try {
            BandwidthMeter bandwidthMeter = new DefaultBandwidthMeter();
            TrackSelector trackSelector = new DefaultTrackSelector(new AdaptiveVideoTrackSelection.Factory(bandwidthMeter));
            LoadControl loadControl = new DefaultLoadControl();
            exoPlayer = ExoPlayerFactory.newSimpleInstance(getContext(), trackSelector, loadControl);


            Uri videoURI = Uri.parse(mStepVideoURL);

            DefaultHttpDataSourceFactory dataSourceFactory = new DefaultHttpDataSourceFactory("exoplayer_video");
            ExtractorsFactory extractorsFactory = new DefaultExtractorsFactory();
            MediaSource mediaSource = new ExtractorMediaSource(videoURI, dataSourceFactory, extractorsFactory, null, null);

            stepVideoView.setPlayer(exoPlayer);
            boolean haveStartPosition = startWindow != C.INDEX_UNSET;

            if (haveStartPosition) {

                exoPlayer.seekTo(startWindow, startPosition);

            }
            exoPlayer.prepare(mediaSource, !haveStartPosition, false);
            exoPlayer.setPlayWhenReady(startAutoPlay);
        } catch (Exception e) {
            Log.v("StepDetailFragment", "error occurred: " + e);
        }
    }


}

這是釋放播放器的方法。

    private void releasePlayer() {
    if(exoPlayer != null){
        updateStartPosition();
        exoPlayer.stop();
        exoPlayer.release();
        exoPlayer = null;
    }

}


@Override

public void onStart() {
    super.onStart();
    if (Util.SDK_INT > 23) {
        initializePlayer();
    }

}

@Override

public void onResume() {
    super.onResume();
    if (Util.SDK_INT <= 23 || exoPlayer == null) {
        initializePlayer();
    }

}
@Override

public void onPause() {
    super.onPause();
    if (Util.SDK_INT <= 23) {
        releasePlayer();
    }

}

private void updateStartPosition() {

    if (exoPlayer != null) {

        startAutoPlay = exoPlayer.getPlayWhenReady();

        startWindow = exoPlayer.getCurrentWindowIndex();

        startPosition = Math.max(0, exoPlayer.getCurrentPosition());

    }

}

private void clearStartPosition() {

    startAutoPlay = true;
    startWindow = C.INDEX_UNSET;
    startPosition = C.TIME_UNSET;

}

我也使用onSavedInstanceState通過了要點。

    @Override
    public void onSaveInstanceState(@NonNull Bundle outState) {
        super.onSaveInstanceState(outState);

        updateStartPosition();
        outState.putBoolean(KEY_AUTO_PLAY, startAutoPlay);
        outState.putInt(KEY_WINDOW, startWindow);
        outState.putLong(KEY_POSITION, startPosition);

    }

    @Override
    public void onStop() {
        super.onStop();
        if (Util.SDK_INT > 23) {
            releasePlayer();
        }

    }

}

實現VideoListener並在其中放置seek調用。

@Override
public void onRenderedFirstFrame()
{
    boolean haveStartPosition = startWindow != C.INDEX_UNSET;

    if (haveStartPosition) {
        exoPlayer.seekTo(startWindow, startPosition);
    }
}

您可以像這樣添加偵聽器。

exoPlayer.getVideoComponent().addVideoListener(videoListener);

但不要忘記通過調用刪除監聽器

exoPlayer.getVideoComponent().removeVideoListener(videoListener);

使用exoPlayer完成操作后。

這就是我解決此問題的方法。 以下是相同的代碼:

private void playerTime() {
    new Handler().postDelayed(() -> {
        seconds = player.getCurrentPosition() / 1000;
        Logger.d("current time: " + seconds);
        mAppSDK.setPlayheadPosition(seconds);
        if (getTime) {
            playerTime();
        }
    }, 1000);
}


private void startPlayer() {
    if (player != null) {
        player.setPlayWhenReady(true);
        player.getPlaybackState();
        mAppSDK.loadMetadata(contentMetadata);
        mAppSDK.setPlayheadPosition(seconds);
    }
}

@Override
protected void onResume() {
    super.onResume();
    getTime = true;
    startPlayer();
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM