mirror of
https://github.com/NiciDieNase/chaosflix
synced 2024-11-23 04:43:07 +00:00
replace last usage of butterknife with databinding and add Playback-Item to decouple player from Entities
This commit is contained in:
parent
c2c39e8c4d
commit
27d53e8081
7 changed files with 219 additions and 174 deletions
|
@ -81,8 +81,6 @@ dependencies {
|
|||
implementation 'com.github.medyo:android-about-page:1.2.2'
|
||||
implementation 'com.google.android.exoplayer:exoplayer:r2.5.2'
|
||||
implementation 'com.squareup.picasso:picasso:2.5.2'
|
||||
implementation 'com.jakewharton:butterknife:8.5.1'
|
||||
kapt 'com.jakewharton:butterknife-compiler:8.5.1'
|
||||
|
||||
debugImplementation 'com.facebook.stetho:stetho:1.4.2'
|
||||
debugImplementation 'com.facebook.stetho:stetho-okhttp3:1.4.2'
|
||||
|
|
|
@ -2,6 +2,7 @@ package de.nicidienase.chaosflix.touch.playback;
|
|||
|
||||
import android.arch.lifecycle.ViewModelProviders;
|
||||
import android.content.Context;
|
||||
import android.databinding.DataBindingUtil;
|
||||
import android.net.Uri;
|
||||
import android.os.Bundle;
|
||||
import android.os.Handler;
|
||||
|
@ -9,15 +10,12 @@ import android.support.annotation.Nullable;
|
|||
import android.support.design.widget.Snackbar;
|
||||
import android.support.v4.app.Fragment;
|
||||
import android.support.v7.app.AppCompatActivity;
|
||||
import android.support.v7.widget.Toolbar;
|
||||
import android.text.TextUtils;
|
||||
import android.util.Log;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.view.WindowManager;
|
||||
import android.widget.ProgressBar;
|
||||
import android.widget.TextView;
|
||||
|
||||
import com.google.android.exoplayer2.C;
|
||||
import com.google.android.exoplayer2.DefaultLoadControl;
|
||||
|
@ -35,7 +33,6 @@ import com.google.android.exoplayer2.source.smoothstreaming.DefaultSsChunkSource
|
|||
import com.google.android.exoplayer2.source.smoothstreaming.SsMediaSource;
|
||||
import com.google.android.exoplayer2.trackselection.AdaptiveTrackSelection;
|
||||
import com.google.android.exoplayer2.trackselection.DefaultTrackSelector;
|
||||
import com.google.android.exoplayer2.ui.SimpleExoPlayerView;
|
||||
import com.google.android.exoplayer2.upstream.DataSource;
|
||||
import com.google.android.exoplayer2.upstream.DefaultBandwidthMeter;
|
||||
import com.google.android.exoplayer2.upstream.DefaultDataSourceFactory;
|
||||
|
@ -44,50 +41,38 @@ import com.google.android.exoplayer2.upstream.DefaultHttpDataSourceFactory;
|
|||
import com.google.android.exoplayer2.upstream.HttpDataSource;
|
||||
import com.google.android.exoplayer2.util.Util;
|
||||
|
||||
import butterknife.BindView;
|
||||
import butterknife.ButterKnife;
|
||||
import de.nicidienase.chaosflix.R;
|
||||
import de.nicidienase.chaosflix.common.entities.recording.persistence.PersistentEvent;
|
||||
import de.nicidienase.chaosflix.common.entities.recording.persistence.PersistentRecording;
|
||||
import de.nicidienase.chaosflix.databinding.ExoPlaybackControlsoverlayBinding;
|
||||
import de.nicidienase.chaosflix.databinding.FragmentExoPlayerBinding;
|
||||
import de.nicidienase.chaosflix.touch.ViewModelFactory;
|
||||
|
||||
public class ExoPlayerFragment extends Fragment implements PlayerEventListener.PlayerStateChangeListener {
|
||||
private static final String TAG = ExoPlayerFragment.class.getSimpleName();
|
||||
public static final String PLAYBACK_STATE = "playback_state";
|
||||
private static final String ARG_EVENT = "event";
|
||||
private static final String ARG_RECORDING = "recording";
|
||||
private static final String PLAYBACK_STATE = "playback_state";
|
||||
private static final String ARG_item = "item";
|
||||
|
||||
private OnMediaPlayerInteractionListener listener;
|
||||
private final DefaultBandwidthMeter BANDWIDTH_METER = new DefaultBandwidthMeter();
|
||||
|
||||
@BindView(R.id.video_view)
|
||||
SimpleExoPlayerView videoView;
|
||||
@BindView(R.id.progressBar)
|
||||
ProgressBar progressBar;
|
||||
|
||||
@Nullable
|
||||
@BindView(R.id.toolbar)
|
||||
Toolbar toolbar;
|
||||
@Nullable
|
||||
@BindView(R.id.subtitle_text)
|
||||
TextView subtitleText;
|
||||
|
||||
private String userAgent;
|
||||
private Handler mainHandler = new Handler();
|
||||
private boolean playbackState = true;
|
||||
private PersistentEvent event;
|
||||
private PersistentRecording recording;
|
||||
private SimpleExoPlayer exoPlayer;
|
||||
private PlayerViewModel viewModel;
|
||||
private PlaybackItem item;
|
||||
|
||||
FragmentExoPlayerBinding binding;
|
||||
ExoPlaybackControlsoverlayBinding overlayBinding;
|
||||
|
||||
public ExoPlayerFragment() {
|
||||
}
|
||||
|
||||
public static ExoPlayerFragment newInstance(PersistentEvent event, PersistentRecording recording) {
|
||||
public static ExoPlayerFragment newInstance(PlaybackItem item) {
|
||||
ExoPlayerFragment fragment = new ExoPlayerFragment();
|
||||
Bundle args = new Bundle();
|
||||
args.putParcelable(ARG_EVENT, event);
|
||||
args.putParcelable(ARG_RECORDING, recording);
|
||||
args.putParcelable(ARG_item, item);
|
||||
fragment.setArguments(args);
|
||||
return fragment;
|
||||
}
|
||||
|
@ -96,8 +81,7 @@ public class ExoPlayerFragment extends Fragment implements PlayerEventListener.P
|
|||
public void onCreate(Bundle savedInstanceState) {
|
||||
super.onCreate(savedInstanceState);
|
||||
if (getArguments() != null) {
|
||||
event = getArguments().getParcelable(ARG_EVENT);
|
||||
recording = getArguments().getParcelable(ARG_RECORDING);
|
||||
item = getArguments().getParcelable(ARG_item);
|
||||
}
|
||||
if (savedInstanceState != null) {
|
||||
playbackState = savedInstanceState.getBoolean(PLAYBACK_STATE, true);
|
||||
|
@ -107,17 +91,20 @@ public class ExoPlayerFragment extends Fragment implements PlayerEventListener.P
|
|||
|
||||
@Override
|
||||
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
|
||||
return inflater.inflate(R.layout.fragment_exo_player, container, false);
|
||||
binding = DataBindingUtil.inflate(inflater, R.layout.fragment_exo_player, container, false);
|
||||
// overlayBinding = DataBindingUtil.findBinding(binding.videoView.getOverlayFrameLayout());
|
||||
overlayBinding = DataBindingUtil.inflate(inflater, R.layout.exo_playback_controlsoverlay, null, false);
|
||||
overlayBinding.setItem(item);
|
||||
// binding.videoView.getOverlayFrameLayout().removeAllViews();
|
||||
// binding.videoView.getOverlayFrameLayout().addView(overlayBinding.getRoot());
|
||||
return binding.getRoot();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onViewCreated(View view, @Nullable Bundle savedInstanceState) {
|
||||
super.onViewCreated(view, savedInstanceState);
|
||||
ButterKnife.bind(this, view);
|
||||
if (toolbar != null) {
|
||||
toolbar.setTitle(event.getTitle());
|
||||
toolbar.setSubtitle(event.getSubtitle());
|
||||
((AppCompatActivity) getActivity()).setSupportActionBar(toolbar);
|
||||
if (overlayBinding != null) {
|
||||
((AppCompatActivity) getActivity()).setSupportActionBar(overlayBinding.toolbar);
|
||||
((AppCompatActivity) getActivity()).getSupportActionBar().setDisplayHomeAsUpEnabled(true);
|
||||
}
|
||||
if (exoPlayer == null) {
|
||||
|
@ -130,12 +117,12 @@ public class ExoPlayerFragment extends Fragment implements PlayerEventListener.P
|
|||
super.onResume();
|
||||
if (exoPlayer != null) {
|
||||
exoPlayer.setPlayWhenReady(playbackState);
|
||||
viewModel.getPlaybackProgress(event.getEventId()).observe(this, playbackProgress -> {
|
||||
viewModel.getPlaybackProgress(item.getEventId()).observe(this, playbackProgress -> {
|
||||
if (playbackProgress != null) {
|
||||
exoPlayer.seekTo(playbackProgress.getProgress());
|
||||
}
|
||||
});
|
||||
videoView.setPlayer(exoPlayer);
|
||||
binding.videoView.setPlayer(exoPlayer);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -150,7 +137,7 @@ public class ExoPlayerFragment extends Fragment implements PlayerEventListener.P
|
|||
public void onPause() {
|
||||
super.onPause();
|
||||
if (exoPlayer != null) {
|
||||
viewModel.setPlaybackProgress(event, exoPlayer.getCurrentPosition());
|
||||
viewModel.setPlaybackProgress(item.getEventId(), exoPlayer.getCurrentPosition());
|
||||
exoPlayer.setPlayWhenReady(false);
|
||||
}
|
||||
}
|
||||
|
@ -172,7 +159,7 @@ public class ExoPlayerFragment extends Fragment implements PlayerEventListener.P
|
|||
|
||||
private SimpleExoPlayer setupPlayer() {
|
||||
Log.d(TAG, "Setting up Player.");
|
||||
videoView.setKeepScreenOn(true);
|
||||
binding.videoView.setKeepScreenOn(true);
|
||||
|
||||
userAgent = Util.getUserAgent(getContext(), getResources().getString(R.string.app_name));
|
||||
|
||||
|
@ -189,7 +176,7 @@ public class ExoPlayerFragment extends Fragment implements PlayerEventListener.P
|
|||
|
||||
exoPlayer.setPlayWhenReady(playbackState);
|
||||
|
||||
exoPlayer.prepare(buildMediaSource(Uri.parse(recording.getRecordingUrl()), ""));
|
||||
exoPlayer.prepare(buildMediaSource(Uri.parse(item.getUrl()), ""));
|
||||
return exoPlayer;
|
||||
}
|
||||
|
||||
|
@ -211,29 +198,30 @@ public class ExoPlayerFragment extends Fragment implements PlayerEventListener.P
|
|||
|
||||
@Override
|
||||
public void notifyLoadingStart() {
|
||||
if (progressBar != null) {
|
||||
progressBar.setVisibility(View.VISIBLE);
|
||||
if (binding.progressBar != null) {
|
||||
binding.progressBar.setVisibility(View.VISIBLE);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void notifyLoadingFinished() {
|
||||
if (progressBar != null) {
|
||||
progressBar.setVisibility(View.INVISIBLE);
|
||||
if (binding.progressBar != null) {
|
||||
binding.progressBar.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void notifyError(String errorMessage) {
|
||||
Snackbar.make(videoView, errorMessage, Snackbar.LENGTH_LONG).show();
|
||||
Snackbar.make(binding.videoView, errorMessage, Snackbar.LENGTH_LONG).show();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void notifyEnd() {
|
||||
viewModel.deletePlaybackProgress(event);
|
||||
viewModel.deletePlaybackProgress(item.getEventId());
|
||||
}
|
||||
|
||||
public interface OnMediaPlayerInteractionListener {}
|
||||
public interface OnMediaPlayerInteractionListener {
|
||||
}
|
||||
|
||||
private MediaSource buildMediaSource(Uri uri, String overrideExtension) {
|
||||
DataSource.Factory mediaDataSourceFactory = buildDataSourceFactory(true);
|
||||
|
|
|
@ -0,0 +1,36 @@
|
|||
package de.nicidienase.chaosflix.touch.playback
|
||||
|
||||
import android.os.Parcel
|
||||
import android.os.Parcelable
|
||||
|
||||
data class PlaybackItem (val title: String, val subtitle: String, val eventId: Long, val url: String) : Parcelable {
|
||||
|
||||
constructor(parcel: Parcel) : this(
|
||||
parcel.readString(),
|
||||
parcel.readString(),
|
||||
parcel.readLong(),
|
||||
parcel.readString()) {
|
||||
}
|
||||
|
||||
override fun writeToParcel(parcel: Parcel, flags: Int) {
|
||||
parcel.writeString(title)
|
||||
parcel.writeString(subtitle)
|
||||
parcel.writeLong(eventId)
|
||||
parcel.writeString(url)
|
||||
}
|
||||
|
||||
override fun describeContents(): Int {
|
||||
return 0
|
||||
}
|
||||
|
||||
companion object CREATOR : Parcelable.Creator<PlaybackItem> {
|
||||
override fun createFromParcel(parcel: Parcel): PlaybackItem {
|
||||
return PlaybackItem(parcel)
|
||||
}
|
||||
|
||||
override fun newArray(size: Int): Array<PlaybackItem?> {
|
||||
return arrayOfNulls(size)
|
||||
}
|
||||
}
|
||||
|
||||
}
|
|
@ -25,7 +25,8 @@ class PlayerActivity : AppCompatActivity(), ExoPlayerFragment.OnMediaPlayerInter
|
|||
|
||||
if (savedInstanceState == null) {
|
||||
val ft = supportFragmentManager.beginTransaction()
|
||||
val playerFragment = ExoPlayerFragment.newInstance(event, recording)
|
||||
val playbackItem = PlaybackItem(event.title, event.subtitle ?: "", event.eventId, recording.recordingUrl)
|
||||
val playerFragment = ExoPlayerFragment.newInstance(playbackItem)
|
||||
ft.replace(R.id.fragment_container, playerFragment)
|
||||
ft.commit()
|
||||
}
|
||||
|
|
|
@ -3,7 +3,6 @@ package de.nicidienase.chaosflix.touch.playback
|
|||
import android.arch.lifecycle.LiveData
|
||||
import android.arch.lifecycle.ViewModel
|
||||
import de.nicidienase.chaosflix.common.entities.ChaosflixDatabase
|
||||
import de.nicidienase.chaosflix.common.entities.recording.persistence.PersistentEvent
|
||||
import de.nicidienase.chaosflix.common.entities.userdata.PlaybackProgress
|
||||
import de.nicidienase.chaosflix.common.network.RecordingService
|
||||
import de.nicidienase.chaosflix.common.network.StreamingService
|
||||
|
@ -16,15 +15,15 @@ internal class PlayerViewModel(val database: ChaosflixDatabase,
|
|||
fun getPlaybackProgress(apiID: Long): LiveData<PlaybackProgress>
|
||||
= database.playbackProgressDao().getProgressForEvent(apiID)
|
||||
|
||||
fun setPlaybackProgress(event: PersistentEvent, progress: Long) {
|
||||
fun setPlaybackProgress(eventId: Long, progress: Long) {
|
||||
Single.fromCallable {
|
||||
database.playbackProgressDao().saveProgress(PlaybackProgress(event.eventId, progress))
|
||||
database.playbackProgressDao().saveProgress(PlaybackProgress(eventId, progress))
|
||||
}.subscribeOn(Schedulers.io()).subscribe()
|
||||
}
|
||||
|
||||
fun deletePlaybackProgress(event: PersistentEvent) {
|
||||
fun deletePlaybackProgress(eventId: Long) {
|
||||
Single.fromCallable {
|
||||
database.playbackProgressDao().deleteItem(event.eventId)
|
||||
database.playbackProgressDao().deleteItem(eventId)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,7 +1,16 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
<layout
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
xmlns:tools="http://schemas.android.com/tools">
|
||||
|
||||
<data>
|
||||
<variable
|
||||
name="item"
|
||||
type="de.nicidienase.chaosflix.touch.playback.PlaybackItem"/>
|
||||
</data>
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:orientation="vertical">
|
||||
|
@ -9,21 +18,21 @@
|
|||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="@drawable/player_controls_background"
|
||||
android:layout_alignParentTop="true"
|
||||
android:background="@drawable/player_controls_background"
|
||||
android:orientation="vertical">
|
||||
|
||||
<android.support.v7.widget.Toolbar
|
||||
android:id="@+id/toolbar"
|
||||
style="@style/ToolbarStyle"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="@android:color/transparent"
|
||||
android:minHeight="?attr/actionBarSize"
|
||||
style="@style/ToolbarStyle"
|
||||
app:title="Title"
|
||||
app:titleTextColor="@color/white"
|
||||
app:subtitle="subtitle"
|
||||
app:subtitleTextColor="@color/white"/>
|
||||
app:subtitle="@{item.subtitle}"
|
||||
app:subtitleTextColor="@color/white"
|
||||
app:title="@{item.title}"
|
||||
app:titleTextColor="@color/white"/>
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
|
@ -37,15 +46,15 @@
|
|||
|
||||
<ImageButton
|
||||
android:id="@id/exo_play"
|
||||
style="@style/ExoMediaButton.Play"
|
||||
android:scaleX="2"
|
||||
android:scaleY="2"
|
||||
style="@style/ExoMediaButton.Play"/>
|
||||
android:scaleY="2"/>
|
||||
|
||||
<ImageButton
|
||||
android:id="@id/exo_pause"
|
||||
style="@style/ExoMediaButton.Pause"
|
||||
android:scaleX="2"
|
||||
android:scaleY="2"
|
||||
style="@style/ExoMediaButton.Pause"/>
|
||||
android:scaleY="2"/>
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
|
@ -98,4 +107,6 @@
|
|||
|
||||
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
|
||||
</layout>
|
|
@ -1,22 +1,34 @@
|
|||
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
<layout
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools">
|
||||
|
||||
<FrameLayout xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:animateLayoutChanges="true"
|
||||
android:background="@color/black"
|
||||
tools:context="de.nicidienase.chaosflix.touch.playback.ExoPlayerFragment">
|
||||
|
||||
<com.google.android.exoplayer2.ui.SimpleExoPlayerView
|
||||
android:id="@+id/video_view"
|
||||
android:layout_height="match_parent"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
app:controller_layout_id="@layout/exo_playback_controlsoverlay"/>
|
||||
|
||||
<ProgressBar
|
||||
<FrameLayout
|
||||
android:id="@+id/progressBar"
|
||||
style="?android:attr/progressBarStyle"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_vertical|center_horizontal"/>
|
||||
android:layout_gravity="center_vertical|center_horizontal">
|
||||
|
||||
</FrameLayout>
|
||||
<de.nicidienase.chaosflix.touch.ChaosflixLoadingSpinner
|
||||
android:layout_width="120dp"
|
||||
android:layout_height="120dp"
|
||||
android:src="@drawable/vector_loading_icon"
|
||||
app:duration="2000"/>
|
||||
|
||||
</FrameLayout>
|
||||
|
||||
</FrameLayout>
|
||||
|
||||
</layout>
|
Loading…
Reference in a new issue