aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChristian Schneppe <christian.schneppe@pix-art.de>2020-01-31 14:28:27 +0100
committerChristian Schneppe <christian.schneppe@pix-art.de>2020-01-31 14:28:27 +0100
commit83c976f2d7cf35d27e040281eab4a2fd40c6d08b (patch)
treeda62e26fff1f42267be0103eeb8ae2a264d425eb
parent6bb9db368638dbd129ac49db15c8308deaf1a5a7 (diff)
use ExoPlayer for video playback
-rw-r--r--build.gradle3
-rw-r--r--libs/android-transcoder/src/main/java/net/ypresto/androidtranscoder/engine/MediaTranscoderEngine.java14
-rw-r--r--libs/android-transcoder/src/main/java/net/ypresto/androidtranscoder/format/AndroidStandardFormatStrategy.java3
-rw-r--r--src/main/java/de/pixart/messenger/services/AttachFileToConversationRunnable.java4
-rw-r--r--src/main/java/de/pixart/messenger/ui/MediaViewerActivity.java85
-rw-r--r--src/main/java/de/pixart/messenger/utils/MimeUtils.java1
-rw-r--r--src/main/res/layout/activity_media_viewer.xml2
-rw-r--r--src/main/res/values/about.xml2
8 files changed, 71 insertions, 43 deletions
diff --git a/build.gradle b/build.gradle
index 83729b11f..a54f7a517 100644
--- a/build.gradle
+++ b/build.gradle
@@ -71,7 +71,8 @@ dependencies {
implementation 'com.google.android.material:material:1.0.0'
implementation 'androidx.cardview:cardview:1.0.0'
implementation 'com.davemorrissey.labs:subsampling-scale-image-view:3.10.0'
- implementation project(':libs:fullscreenvideoview')
+ implementation 'com.google.android.exoplayer:exoplayer-core:2.11.1'
+ implementation 'com.google.android.exoplayer:exoplayer-ui:2.11.1'
implementation 'pub.devrel:easypermissions:3.0.0' // version >= 3.0.0 needs android X libraries
implementation 'com.wefika:flowlayout:0.4.1'
implementation 'com.googlecode.ez-vcard:ez-vcard:0.10.5'
diff --git a/libs/android-transcoder/src/main/java/net/ypresto/androidtranscoder/engine/MediaTranscoderEngine.java b/libs/android-transcoder/src/main/java/net/ypresto/androidtranscoder/engine/MediaTranscoderEngine.java
index 274d91cac..86637fd0e 100644
--- a/libs/android-transcoder/src/main/java/net/ypresto/androidtranscoder/engine/MediaTranscoderEngine.java
+++ b/libs/android-transcoder/src/main/java/net/ypresto/androidtranscoder/engine/MediaTranscoderEngine.java
@@ -19,11 +19,9 @@ import android.media.MediaExtractor;
import android.media.MediaFormat;
import android.media.MediaMetadataRetriever;
import android.media.MediaMuxer;
-import android.os.Build;
import android.util.Log;
import net.ypresto.androidtranscoder.format.MediaFormatStrategy;
-import net.ypresto.androidtranscoder.utils.ISO6709LocationParser;
import net.ypresto.androidtranscoder.utils.MediaExtractorUtils;
import java.io.FileDescriptor;
@@ -139,18 +137,6 @@ public class MediaTranscoderEngine {
// skip
}
- if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
- String locationString = mediaMetadataRetriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_LOCATION);
- if (locationString != null) {
- float[] location = new ISO6709LocationParser().parse(locationString);
- if (location != null) {
- mMuxer.setLocation(location[0], location[1]);
- } else {
- Log.d(TAG, "Failed to parse the location metadata: " + locationString);
- }
- }
- }
-
try {
mDurationUs = Long.parseLong(mediaMetadataRetriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_DURATION)) * 1000;
} catch (NumberFormatException e) {
diff --git a/libs/android-transcoder/src/main/java/net/ypresto/androidtranscoder/format/AndroidStandardFormatStrategy.java b/libs/android-transcoder/src/main/java/net/ypresto/androidtranscoder/format/AndroidStandardFormatStrategy.java
index 822c45fbd..6b1990e69 100644
--- a/libs/android-transcoder/src/main/java/net/ypresto/androidtranscoder/format/AndroidStandardFormatStrategy.java
+++ b/libs/android-transcoder/src/main/java/net/ypresto/androidtranscoder/format/AndroidStandardFormatStrategy.java
@@ -18,9 +18,10 @@ package net.ypresto.androidtranscoder.format;
import android.media.MediaCodecInfo;
import android.media.MediaFormat;
import android.os.Build;
-import androidx.annotation.RequiresApi;
import android.util.Log;
+import androidx.annotation.RequiresApi;
+
class AndroidStandardFormatStrategy implements MediaFormatStrategy {
public static final int AUDIO_BITRATE_AS_IS = -1;
public static final int AUDIO_CHANNELS_AS_IS = -1;
diff --git a/src/main/java/de/pixart/messenger/services/AttachFileToConversationRunnable.java b/src/main/java/de/pixart/messenger/services/AttachFileToConversationRunnable.java
index bb907a5cd..e8d6524d2 100644
--- a/src/main/java/de/pixart/messenger/services/AttachFileToConversationRunnable.java
+++ b/src/main/java/de/pixart/messenger/services/AttachFileToConversationRunnable.java
@@ -182,10 +182,6 @@ public class AttachFileToConversationRunnable implements Runnable, MediaTranscod
}
}
- private String getVideoCompression() {
- return getVideoCompression(mXmppConnectionService);
- }
-
public static String getVideoCompression(final Context context) {
final SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(context);
return preferences.getString("video_compression", context.getResources().getString(R.string.video_compression));
diff --git a/src/main/java/de/pixart/messenger/ui/MediaViewerActivity.java b/src/main/java/de/pixart/messenger/ui/MediaViewerActivity.java
index 04d44e142..b9dff18c7 100644
--- a/src/main/java/de/pixart/messenger/ui/MediaViewerActivity.java
+++ b/src/main/java/de/pixart/messenger/ui/MediaViewerActivity.java
@@ -22,7 +22,6 @@ import android.view.MotionEvent;
import android.view.View;
import android.view.WindowManager;
import android.webkit.MimeTypeMap;
-import android.widget.ImageView;
import android.widget.Toast;
import androidx.appcompat.app.ActionBar;
@@ -30,10 +29,17 @@ import androidx.appcompat.app.AlertDialog;
import androidx.databinding.DataBindingUtil;
import com.davemorrissey.labs.subscaleview.ImageSource;
+import com.google.android.exoplayer2.ExoPlaybackException;
+import com.google.android.exoplayer2.Player;
+import com.google.android.exoplayer2.SimpleExoPlayer;
+import com.google.android.exoplayer2.source.MediaSource;
+import com.google.android.exoplayer2.source.ProgressiveMediaSource;
+import com.google.android.exoplayer2.upstream.DataSource;
+import com.google.android.exoplayer2.upstream.DefaultDataSourceFactory;
+import com.google.android.exoplayer2.util.Util;
import java.io.File;
import java.io.FileNotFoundException;
-import java.io.IOException;
import java.io.InputStream;
import java.util.List;
@@ -49,7 +55,7 @@ import static de.pixart.messenger.persistance.FileBackend.close;
public class MediaViewerActivity extends XmppActivity implements AudioManager.OnAudioFocusChangeListener {
Integer oldOrientation;
- ImageView mFullscreenbutton;
+ SimpleExoPlayer player;
Uri mFileUri;
File mFile;
int height = 0;
@@ -86,8 +92,6 @@ public class MediaViewerActivity extends XmppActivity implements AudioManager.On
showFab();
return super.onDown(e);
}
-
-
});
ActionBar actionBar = getSupportActionBar();
@@ -104,7 +108,6 @@ public class MediaViewerActivity extends XmppActivity implements AudioManager.On
getWindow().setAttributes(layout);
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
getWindow().addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
- mFullscreenbutton = findViewById(R.id.vcv_img_fullscreen);
binding.speedDial.inflate(R.menu.media_viewer);
binding.speedDial.setOnActionSelectedListener(actionItem -> {
switch (actionItem.getId()) {
@@ -226,9 +229,8 @@ public class MediaViewerActivity extends XmppActivity implements AudioManager.On
}
}
- private void DisplayImage(final File file, final Uri FileUri) {
- boolean gif = false;
- gif = "image/gif".equalsIgnoreCase(getMimeType(file.toString()));
+ private void DisplayImage(final File file, final Uri uri) {
+ final boolean gif = "image/gif".equalsIgnoreCase(getMimeType(file.toString()));
BitmapFactory.Options options = new BitmapFactory.Options();
options.inJustDecodeBounds = true;
BitmapFactory.decodeFile(new File(file.getPath()).getAbsolutePath(), options);
@@ -242,12 +244,11 @@ public class MediaViewerActivity extends XmppActivity implements AudioManager.On
try {
if (gif) {
binding.messageGifView.setVisibility(View.VISIBLE);
- binding.messageGifView.setImageURI(FileUri);
+ binding.messageGifView.setImageURI(uri);
binding.messageGifView.setOnTouchListener((view, motionEvent) -> gestureDetector.onTouchEvent(motionEvent));
} else {
binding.messageImageView.setVisibility(View.VISIBLE);
- binding.messageImageView.setOrientation(rotation);
- binding.messageImageView.setImage(ImageSource.uri(FileUri));
+ binding.messageImageView.setImage(ImageSource.uri(uri));
binding.messageImageView.setOnTouchListener((view, motionEvent) -> gestureDetector.onTouchEvent(motionEvent));
}
} catch (Exception e) {
@@ -262,7 +263,7 @@ public class MediaViewerActivity extends XmppActivity implements AudioManager.On
retriever.setDataSource(uri.getPath());
Bitmap bitmap = null;
try {
- bitmap = retriever.getFrameAtTime();
+ bitmap = retriever.getFrameAtTime(0);
height = bitmap.getHeight();
width = bitmap.getWidth();
} catch (Exception e) {
@@ -273,21 +274,35 @@ public class MediaViewerActivity extends XmppActivity implements AudioManager.On
bitmap.recycle();
}
}
- rotation = Integer.valueOf(retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_VIDEO_ROTATION));
+ try {
+ rotation = Integer.valueOf(retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_VIDEO_ROTATION));
+ } catch (Exception e) {
+ rotation = 0;
+ }
Log.d(Config.LOGTAG, "Video height: " + height + ", width: " + width + ", rotation: " + rotation);
if (useAutoRotateScreen()) {
rotateScreen(width, height, rotation);
}
binding.messageVideoView.setVisibility(View.VISIBLE);
- binding.messageVideoView.setVideoURI(uri);
- mFullscreenbutton.setVisibility(View.INVISIBLE);
- binding.messageVideoView.setShouldAutoplay(true);
+ player = new SimpleExoPlayer.Builder(this).build();
+ player.setPlayWhenReady(true);
+ player.addListener(new SimpleExoPlayer.EventListener() {
+ @Override
+ public void onPlayerError(ExoPlaybackException error) {
+ open();
+ }
+ });
+ player.setRepeatMode(Player.REPEAT_MODE_OFF);
+ binding.messageVideoView.setPlayer(player);
+ DataSource.Factory dataSourceFactory = new DefaultDataSourceFactory(this, Util.getUserAgent(this, "de.pixart.messenger"));
+ MediaSource videoSource = new ProgressiveMediaSource.Factory(dataSourceFactory).createMediaSource(uri);
+ player.prepare(videoSource);
requestAudioFocus();
setVolumeControlStream(AudioManager.STREAM_MUSIC);
binding.messageVideoView.setOnTouchListener((view, motionEvent) -> gestureDetector.onTouchEvent(motionEvent));
} catch (Exception e) {
- open();
e.printStackTrace();
+ open();
}
}
@@ -331,6 +346,34 @@ public class MediaViewerActivity extends XmppActivity implements AudioManager.On
}
}
+ private void pausePlayer() {
+ if (isVideo && isPlaying()) {
+ player.setPlayWhenReady(false);
+ player.getPlaybackState();
+ }
+ }
+
+ private void startPlayer() {
+ if (isVideo && !isPlaying()) {
+ player.setPlayWhenReady(true);
+ player.getPlaybackState();
+ }
+ }
+
+ private void stopPlayer() {
+ if (isVideo && isPlaying()) {
+ player.stop(true);
+ player.release();
+ }
+ }
+
+ private boolean isPlaying() {
+ return player != null
+ && player.getPlaybackState() != Player.STATE_ENDED
+ && player.getPlaybackState() != Player.STATE_IDLE
+ && player.getPlayWhenReady();
+ }
+
@Override
public void onConfigurationChanged(Configuration newConfig) {
super.onConfigurationChanged(newConfig);
@@ -344,13 +387,13 @@ public class MediaViewerActivity extends XmppActivity implements AudioManager.On
}
getWindow().setAttributes(layout);
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
- binding.messageVideoView.setShouldAutoplay(true);
+ startPlayer();
super.onResume();
}
@Override
public void onPause() {
- binding.messageVideoView.reset();
+ pausePlayer();
WindowManager.LayoutParams layout = getWindow().getAttributes();
if (useMaxBrightness()) {
layout.screenBrightness = -1;
@@ -363,7 +406,7 @@ public class MediaViewerActivity extends XmppActivity implements AudioManager.On
@Override
public void onStop() {
- binding.messageVideoView.reset();
+ stopPlayer();
releaseAudiFocus();
WindowManager.LayoutParams layout = getWindow().getAttributes();
if (useMaxBrightness()) {
diff --git a/src/main/java/de/pixart/messenger/utils/MimeUtils.java b/src/main/java/de/pixart/messenger/utils/MimeUtils.java
index 4ca8eb01a..8603a8a89 100644
--- a/src/main/java/de/pixart/messenger/utils/MimeUtils.java
+++ b/src/main/java/de/pixart/messenger/utils/MimeUtils.java
@@ -376,6 +376,7 @@ public final class MimeUtils {
add("video/mpeg", "mpg");
add("video/mpeg", "mpe");
add("video/mp4", "mp4");
+ add("video/mp4", "gifv");
add("video/mpeg", "VOB");
add("video/quicktime", "qt");
add("video/quicktime", "mov");
diff --git a/src/main/res/layout/activity_media_viewer.xml b/src/main/res/layout/activity_media_viewer.xml
index cca277e51..2b64fb81a 100644
--- a/src/main/res/layout/activity_media_viewer.xml
+++ b/src/main/res/layout/activity_media_viewer.xml
@@ -22,7 +22,7 @@
android:adjustViewBounds="true"
android:visibility="gone" />
- <com.github.rtoshiro.view.video.FullscreenVideoLayout
+ <com.google.android.exoplayer2.ui.SimpleExoPlayerView
android:id="@+id/messageVideoView"
android:layout_width="match_parent"
android:layout_height="match_parent"
diff --git a/src/main/res/values/about.xml b/src/main/res/values/about.xml
index ee702a7de..c5e82dff5 100644
--- a/src/main/res/values/about.xml
+++ b/src/main/res/values/about.xml
@@ -38,7 +38,7 @@
\n\nhttps://github.com/square/picasso\n(Apache License, Version 2.0)
\n\nhttps://github.com/davemorrissey/subsampling-scale-image-view\n(Apache License, Version 2.0)
\n\nhttps://github.com/koral--/android-gif-drawable\n(The MIT License (MIT))
- \n\nhttps://github.com/rtoshiro/FullscreenVideoView\n(Apache License, Version 2.0)
+ \n\nhttps://github.com/google/ExoPlayer\n(Apache License, Version 2.0)
\n\nhttps://github.com/mangstadt/ez-vcard\n(FreeBSD)
\n\nhttps://github.com/googlesamples/easypermissions\n(Apache License, Version 2.0)
\n\nhttps://github.com/blazsolar/FlowLayout\n(Apache License, Version 2.0)