В настоящее время я создаю приложение, которое получает список видео из API, а затем воспроизводит их последовательно, используя ExoPlayer
.Вчера все работало нормально, но сейчас я не могу воспроизвести видео.Плеер пытается воспроизвести видео, но застревает в состоянии буферизации.
Чтобы убедиться, что видео на нашем сервере не являются причиной того, что мое приложение не работает, я искал в Интернете пример видео mp4 и обнаружил это .Это все еще не играло.Ответы на другие вопросы SO также не сработали.
Это коды, которые я использую для инициализации ExoPlayer
.Я использую PlayerView
, если вам, ребята, нужна эта информация.
private void initializePlayer() {
if (exoPlayer == null) {
mainHandler = new Handler();
bandwidthMeter = new DefaultBandwidthMeter();
trackSelectionFactory = new AdaptiveTrackSelection.Factory(bandwidthMeter);
trackSelector = new DefaultTrackSelector(trackSelectionFactory);
LoadControl loadControl = new DefaultLoadControl();
exoPlayer = ExoPlayerFactory.newSimpleInstance(this, trackSelector, loadControl);
playerView.setPlayer(exoPlayer);
exoPlayer.addListener(exoPlayEventListener);
}
}
Это код для EventListener
.
Player.EventListener exoPlayEventListener = new Player.EventListener() {
@Override
public void onTimelineChanged(Timeline timeline, @Nullable Object manifest, int reason) {
}
@Override
public void onTracksChanged(TrackGroupArray trackGroups, TrackSelectionArray trackSelections) {
}
@Override
public void onLoadingChanged(boolean isLoading) {
}
@Override
public void onPlayerStateChanged(boolean playWhenReady, int playbackState) {
switch (playbackState){
case Player.DISCONTINUITY_REASON_PERIOD_TRANSITION:
Log.d(TAG, "eventListen onPlayerStateChanged DISCONTINUITY_REASON_PERIOD_TRANSITION");
break;
case Player.STATE_BUFFERING:
Log.d(TAG, "Buffering . . . .");
break;
case Player.STATE_READY:
Log.d(TAG, "Ready!!!");
break;
case Player.STATE_ENDED:
Log.d(TAG, "player ended");
playLoopVideo();
break;
}
}
@Override
public void onRepeatModeChanged(int repeatMode) {
}
@Override
public void onPlayerError(ExoPlaybackException error) {
switch (error.type) {
case ExoPlaybackException.TYPE_SOURCE:
Log.d(TAG, "ERR TYPE_SOURCE: " + error.getSourceException().getMessage());
playLoopVideo();
break;
case ExoPlaybackException.TYPE_RENDERER:
Log.d(TAG, "ERR TYPE_RENDERER: " + error.getRendererException().getMessage());
playLoopVideo();
break;
case ExoPlaybackException.TYPE_UNEXPECTED:
Log.d(TAG, "ERR TYPE_UNEXPECTED: " + error.getUnexpectedException().getMessage());
playLoopVideo();
break;
}
}
@Override
public void onPositionDiscontinuity(int reason) {
if (reason == Player.DISCONTINUITY_REASON_PERIOD_TRANSITION) {
}
}
@Override
public void onPlaybackParametersChanged(PlaybackParameters playbackParameters) {
}
};
Этот код я использую для изменениявидео для воспроизведения.Я вызываю это после того, как получаю свой список видео из API.
private void playLoopVideo() {
toPlayVidIndex = playedVidIndex;
String toPlayVidURL = "";
if(playedVidIndex == 7 && !isDefaultPlayed){
toPlayVidURL = defaultUrl;
playedVidIndex--;
isDefaultPlayed = true;
}else{
if (playedVidIndex >= vidArrLst.size()){
playedVidIndex = 0;
toPlayVidIndex = playedVidIndex;
}
toPlayVidURL = vidArrLst.get(toPlayVidIndex).getUrl();
isDefaultPlayed = false;
}
startStream(toPlayVidURL);
playedVidIndex++;
}
Это код для воспроизведения видеопотока.
private void startStream(String streamLink){
Uri mediaUri = Uri.parse(streamLink);
DefaultBandwidthMeter defaultBandwidthMeter = new DefaultBandwidthMeter();
DataSource.Factory dataSourceFactory = new DefaultDataSourceFactory(ctx.getApplicationContext(),
Util.getUserAgent(ctx.getApplicationContext(),
"Streamer"), defaultBandwidthMeter);
ExtractorsFactory extractorsFactory = new DefaultExtractorsFactory();
MediaSource mediaSource = new ExtractorMediaSource.Factory(dataSourceFactory).createMediaSource(mediaUri);
exoPlayer.setPlayWhenReady(true);
exoPlayer.prepare(mediaSource, true, false);
currentStreamMediaSource = mediaSource;
}
In onStop()
и onDestroy()
,Я называю этот код для освобождения игрока.
private void releasePlayer() {
if (exoPlayer != null) {
playbackPosition = exoPlayer.getCurrentPosition();
currentWindow = exoPlayer.getCurrentWindowIndex();
playWhenReady = exoPlayer.getPlayWhenReady();
exoPlayer.release();
exoPlayer = null;
}
}
Это мой build.gradle (приложение), если вам это нужно.
apply plugin: 'com.android.application'
android {
compileSdkVersion 28
defaultConfig {
applicationId "biz.net.com.streamer"
minSdkVersion 17
targetSdkVersion 28
versionCode 1
versionName "1.0"
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
}
compileOptions {
sourceCompatibility 1.8
targetCompatibility 1.8
}
}
dependencies {
implementation fileTree(include: ['*.jar'], dir: 'libs')
implementation 'com.android.support:appcompat-v7:28.0.0'
implementation 'com.android.support.constraint:constraint-layout:1.1.3'
testImplementation 'junit:junit:4.12'
androidTestImplementation 'com.android.support.test:runner:1.0.2'
androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.0.2'
implementation 'com.google.android.exoplayer:exoplayer:2.9.1'
implementation 'com.android.volley:volley:1.1.1'
}
ОБНОВЛЕНИЕ:
СегодняЯ попытался воспроизвести видео напрямую, используя метод startStream, и он воспроизвел пример видео mp4 и видео с нашего сервера.
Этот код я использую для получения нашего локального API видео.По какой-то причине, если я воспроизведу видео внутри этого метода, он не будет воспроизводиться, но напрямую с помощью startStream () воспроизводит видео.
public void getVideoAds(String serverURL){
String url = "http://"+serverURL+"/video/";
StringRequest stringRequest = new StringRequest(url, new Response.Listener<String>() {
@Override
public void onResponse(String response) {
Log.d(TAG, "getVidAds res: "+response);
try {
JSONObject jsonObj = new JSONObject(response);
JSONObject defaultObj = jsonObj.getJSONObject("default");
JSONArray videoObj = jsonObj.getJSONArray("videos");
defaultUrl = defaultObj.getString("url");
for (int i = 0; i < videoObj.length(); i++){
JSONObject video = videoObj.getJSONObject(i);
VideoAd v = new VideoAd();
v.setName(getVideoNameFromLink(video.getString("url")));
v.setUrl(video.getString("url"));
v.setVideoId(video.getInt("id"));
v.setVersion(video.getInt("version"));
v.setLocalPath("");
vidArrLst.add(v);
}
playLoopVideo();
} catch (Exception e) {
}
}
}, new Response.ErrorListener() {
@Override
public void onErrorResponse(VolleyError error) {
Log.d(TAG, "getVidAds err: " + error.getMessage());
}
});
queue.add(stringRequest);
}
ОБНОВЛЕНИЕ:
Привет, я сделал еще один SOвопрос здесь о том, как иногда Volley не работает должным образом и [немного странно] влияет на ExoPlayer
, когда он застревает в состоянии BUFFERING.Если вы хотите узнать больше, пожалуйста, посмотрите на другой вопрос, потому что я не хочу повторять все, что я разместил здесь.