From 1d42e45d785b955f7f2dfc38c4da168cd7601e27 Mon Sep 17 00:00:00 2001
From: Stypox
Date: Sun, 18 Oct 2020 20:19:50 +0200
Subject: [PATCH 1/7] Unify all ways of opening VideoDetailFragment
---
.../java/org/schabi/newpipe/MainActivity.java | 40 ++--
.../org/schabi/newpipe/RouterActivity.java | 87 +------
.../fragments/detail/VideoDetailFragment.java | 99 ++++----
.../fragments/list/BaseListFragment.java | 5 +-
.../list/channel/ChannelFragment.java | 2 +-
.../list/playlist/PlaylistFragment.java | 2 +-
.../history/StatisticsPlaylistFragment.java | 12 +-
.../local/playlist/LocalPlaylistFragment.java | 11 +-
.../newpipe/player/ServicePlayerActivity.java | 9 +-
.../newpipe/player/VideoPlayerImpl.java | 2 +-
.../newpipe/player/playqueue/PlayQueue.java | 44 ----
.../schabi/newpipe/util/NavigationHelper.java | 215 ++++++++----------
app/src/main/res/values/settings_keys.xml | 1 -
13 files changed, 201 insertions(+), 328 deletions(-)
diff --git a/app/src/main/java/org/schabi/newpipe/MainActivity.java b/app/src/main/java/org/schabi/newpipe/MainActivity.java
index e72d4609e..1d911c944 100644
--- a/app/src/main/java/org/schabi/newpipe/MainActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/MainActivity.java
@@ -30,9 +30,7 @@ import android.os.Build;
import android.os.Bundle;
import android.os.Handler;
import android.os.Looper;
-import androidx.preference.PreferenceManager;
import android.util.Log;
-
import android.view.KeyEvent;
import android.view.LayoutInflater;
import android.view.Menu;
@@ -46,6 +44,7 @@ import android.widget.FrameLayout;
import android.widget.ImageView;
import android.widget.Spinner;
import android.widget.TextView;
+
import androidx.annotation.NonNull;
import androidx.appcompat.app.ActionBar;
import androidx.appcompat.app.ActionBarDrawerToggle;
@@ -55,6 +54,7 @@ import androidx.core.view.GravityCompat;
import androidx.drawerlayout.widget.DrawerLayout;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentManager;
+import androidx.preference.PreferenceManager;
import com.google.android.material.bottomsheet.BottomSheetBehavior;
import com.google.android.material.navigation.NavigationView;
@@ -71,8 +71,8 @@ import org.schabi.newpipe.player.VideoPlayer;
import org.schabi.newpipe.player.event.OnKeyDownListener;
import org.schabi.newpipe.player.playqueue.PlayQueue;
import org.schabi.newpipe.report.ErrorActivity;
-import org.schabi.newpipe.util.DeviceUtils;
import org.schabi.newpipe.util.Constants;
+import org.schabi.newpipe.util.DeviceUtils;
import org.schabi.newpipe.util.KioskTranslator;
import org.schabi.newpipe.util.Localization;
import org.schabi.newpipe.util.NavigationHelper;
@@ -758,32 +758,36 @@ public class MainActivity extends AppCompatActivity {
if (intent.hasExtra(Constants.KEY_LINK_TYPE)) {
final String url = intent.getStringExtra(Constants.KEY_URL);
final int serviceId = intent.getIntExtra(Constants.KEY_SERVICE_ID, 0);
- final String title = intent.getStringExtra(Constants.KEY_TITLE);
- switch (((StreamingService.LinkType) intent
- .getSerializableExtra(Constants.KEY_LINK_TYPE))) {
+ String title = intent.getStringExtra(Constants.KEY_TITLE);
+ if (title == null) {
+ title = "";
+ }
+
+ final StreamingService.LinkType linkType = ((StreamingService.LinkType) intent
+ .getSerializableExtra(Constants.KEY_LINK_TYPE));
+ assert linkType != null;
+ switch (linkType) {
case STREAM:
- final boolean autoPlay = intent
- .getBooleanExtra(VideoDetailFragment.AUTO_PLAY, false);
- final String intentCacheKey = intent
- .getStringExtra(VideoPlayer.PLAY_QUEUE_KEY);
+ final String intentCacheKey = intent.getStringExtra(
+ VideoPlayer.PLAY_QUEUE_KEY);
final PlayQueue playQueue = intentCacheKey != null
? SerializedCache.getInstance()
.take(intentCacheKey, PlayQueue.class)
: null;
- NavigationHelper.openVideoDetailFragment(getSupportFragmentManager(),
- serviceId, url, title, autoPlay, playQueue);
+
+ final boolean switchingPlayers = intent.getBooleanExtra(
+ VideoDetailFragment.KEY_SWITCHING_PLAYERS, false);
+ NavigationHelper.openVideoDetailFragment(
+ getApplicationContext(), getSupportFragmentManager(),
+ serviceId, url, title, playQueue, switchingPlayers);
break;
case CHANNEL:
NavigationHelper.openChannelFragment(getSupportFragmentManager(),
- serviceId,
- url,
- title);
+ serviceId, url, title);
break;
case PLAYLIST:
NavigationHelper.openPlaylistFragment(getSupportFragmentManager(),
- serviceId,
- url,
- title);
+ serviceId, url, title);
break;
}
} else if (intent.hasExtra(Constants.KEY_OPEN_SEARCH)) {
diff --git a/app/src/main/java/org/schabi/newpipe/RouterActivity.java b/app/src/main/java/org/schabi/newpipe/RouterActivity.java
index 388d7683a..ca145bb9a 100644
--- a/app/src/main/java/org/schabi/newpipe/RouterActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/RouterActivity.java
@@ -60,8 +60,6 @@ import org.schabi.newpipe.views.FocusOverlayView;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.Arrays;
-import java.util.Collection;
-import java.util.HashSet;
import java.util.List;
import icepick.Icepick;
@@ -116,8 +114,6 @@ public class RouterActivity extends AppCompatActivity {
}
}
- internalRoute = getIntent().getBooleanExtra(INTERNAL_ROUTE_KEY, false);
-
setTheme(ThemeHelper.isLightThemeSelected(this)
? R.style.RouterActivityThemeLight : R.style.RouterActivityThemeDark);
}
@@ -492,10 +488,6 @@ public class RouterActivity extends AppCompatActivity {
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(intent -> {
- if (!internalRoute) {
- intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
- intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK);
- }
startActivity(intent);
finish();
@@ -515,7 +507,7 @@ public class RouterActivity extends AppCompatActivity {
@SuppressLint("CheckResult")
private void openDownloadDialog() {
- ExtractorHelper.getStreamInfo(currentServiceId, currentUrl, true)
+ disposables.add(ExtractorHelper.getStreamInfo(currentServiceId, currentUrl, true)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe((@NonNull StreamInfo result) -> {
@@ -532,10 +524,10 @@ public class RouterActivity extends AppCompatActivity {
downloadDialog.setSelectedVideoStream(selectedVideoStreamIndex);
downloadDialog.show(fm, "downloadDialog");
fm.executePendingTransactions();
- downloadDialog.getDialog().setOnDismissListener(dialog -> finish());
+ downloadDialog.requireDialog().setOnDismissListener(dialog -> finish());
}, (@NonNull Throwable throwable) -> {
showUnsupportedUrlDialog(currentUrl);
- });
+ }));
}
@Override
@@ -553,66 +545,6 @@ public class RouterActivity extends AppCompatActivity {
}
}
- /*//////////////////////////////////////////////////////////////////////////
- // Service Fetcher
- //////////////////////////////////////////////////////////////////////////*/
-
- private String removeHeadingGibberish(final String input) {
- int start = 0;
- for (int i = input.indexOf("://") - 1; i >= 0; i--) {
- if (!input.substring(i, i + 1).matches("\\p{L}")) {
- start = i + 1;
- break;
- }
- }
- return input.substring(start);
- }
-
- /*//////////////////////////////////////////////////////////////////////////
- // Utils
- //////////////////////////////////////////////////////////////////////////*/
-
- private String trim(final String input) {
- if (input == null || input.length() < 1) {
- return input;
- } else {
- String output = input;
- while (output.length() > 0 && output.substring(0, 1).matches(REGEX_REMOVE_FROM_URL)) {
- output = output.substring(1);
- }
- while (output.length() > 0
- && output.substring(output.length() - 1).matches(REGEX_REMOVE_FROM_URL)) {
- output = output.substring(0, output.length() - 1);
- }
- return output;
- }
- }
-
- /**
- * Retrieves all Strings which look remotely like URLs from a text.
- * Used if NewPipe was called through share menu.
- *
- * @param sharedText text to scan for URLs.
- * @return potential URLs
- */
- protected String[] getUris(final String sharedText) {
- final Collection result = new HashSet<>();
- if (sharedText != null) {
- final String[] array = sharedText.split("\\p{Space}");
- for (String s : array) {
- s = trim(s);
- if (s.length() != 0) {
- if (s.matches(".+://.+")) {
- result.add(removeHeadingGibberish(s));
- } else if (s.matches(".+\\..+")) {
- result.add("http://" + s);
- }
- }
- }
- }
- return result.toArray(new String[0]);
- }
-
private static class AdapterChoiceItem {
final String description;
final String key;
@@ -739,11 +671,11 @@ public class RouterActivity extends AppCompatActivity {
playQueue = new SinglePlayQueue((StreamInfo) info);
if (playerChoice.equals(videoPlayerKey)) {
- openMainPlayer(playQueue, choice);
+ NavigationHelper.playOnMainPlayer(this, playQueue);
} else if (playerChoice.equals(backgroundPlayerKey)) {
- NavigationHelper.enqueueOnBackgroundPlayer(this, playQueue, true);
+ NavigationHelper.playOnBackgroundPlayer(this, playQueue, true);
} else if (playerChoice.equals(popupPlayerKey)) {
- NavigationHelper.enqueueOnPopupPlayer(this, playQueue, true);
+ NavigationHelper.playOnPopupPlayer(this, playQueue, true);
}
}
}
@@ -754,7 +686,7 @@ public class RouterActivity extends AppCompatActivity {
: new PlaylistPlayQueue((PlaylistInfo) info);
if (playerChoice.equals(videoPlayerKey)) {
- openMainPlayer(playQueue, choice);
+ NavigationHelper.playOnMainPlayer(this, playQueue);
} else if (playerChoice.equals(backgroundPlayerKey)) {
NavigationHelper.playOnBackgroundPlayer(this, playQueue, true);
} else if (playerChoice.equals(popupPlayerKey)) {
@@ -764,11 +696,6 @@ public class RouterActivity extends AppCompatActivity {
};
}
- private void openMainPlayer(final PlayQueue playQueue, final Choice choice) {
- NavigationHelper.playOnMainPlayer(this, playQueue, choice.linkType,
- choice.url, "", true, true);
- }
-
@Override
public void onDestroy() {
super.onDestroy();
diff --git a/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java b/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java
index d5da006f7..ffba7f521 100644
--- a/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java
+++ b/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java
@@ -110,6 +110,7 @@ import org.schabi.newpipe.views.LargeTextMovementMethod;
import java.util.Iterator;
import java.util.LinkedList;
import java.util.List;
+import java.util.Objects;
import java.util.concurrent.TimeUnit;
import icepick.State;
@@ -128,7 +129,7 @@ import static org.schabi.newpipe.player.helper.PlayerHelper.isClearingQueueConfi
import static org.schabi.newpipe.player.playqueue.PlayQueueItem.RECOVERY_UNSET;
import static org.schabi.newpipe.util.AnimationUtils.animateView;
-public class VideoDetailFragment
+public final class VideoDetailFragment
extends BaseStateFragment
implements BackPressable,
SharedPreferences.OnSharedPreferenceChangeListener,
@@ -136,7 +137,7 @@ public class VideoDetailFragment
View.OnLongClickListener,
PlayerServiceExtendedEventListener,
OnKeyDownListener {
- public static final String AUTO_PLAY = "auto_play";
+ public static final String KEY_SWITCHING_PLAYERS = "switching_players";
private static final int RELATED_STREAMS_UPDATE_FLAG = 0x1;
private static final int COMMENTS_UPDATE_FLAG = 0x2;
@@ -167,19 +168,23 @@ public class VideoDetailFragment
@State
protected int serviceId = Constants.NO_SERVICE_ID;
@State
- protected String name;
+ @NonNull
+ protected String title = "";
@State
- protected String url;
- protected static PlayQueue playQueue;
+ @Nullable
+ protected String url = null;
+ @Nullable
+ protected PlayQueue playQueue = null;
@State
int bottomSheetState = BottomSheetBehavior.STATE_EXPANDED;
@State
protected boolean autoPlayEnabled = true;
- private static StreamInfo currentInfo;
+ @Nullable
+ private StreamInfo currentInfo = null;
private Disposable currentWorker;
@NonNull
- private CompositeDisposable disposables = new CompositeDisposable();
+ private final CompositeDisposable disposables = new CompositeDisposable();
@Nullable
private Disposable positionSubscriber = null;
@@ -298,8 +303,10 @@ public class VideoDetailFragment
/*////////////////////////////////////////////////////////////////////////*/
- public static VideoDetailFragment getInstance(final int serviceId, final String videoUrl,
- final String name, final PlayQueue queue) {
+ public static VideoDetailFragment getInstance(final int serviceId,
+ @Nullable final String videoUrl,
+ @NonNull final String name,
+ @Nullable final PlayQueue queue) {
final VideoDetailFragment instance = new VideoDetailFragment();
instance.setInitialData(serviceId, videoUrl, name, queue);
return instance;
@@ -444,8 +451,8 @@ public class VideoDetailFragment
switch (requestCode) {
case ReCaptchaActivity.RECAPTCHA_REQUEST:
if (resultCode == Activity.RESULT_OK) {
- NavigationHelper
- .openVideoDetailFragment(getFM(), serviceId, url, name);
+ NavigationHelper.openVideoDetailFragment(requireContext(), getFM(),
+ serviceId, url, title, null, false);
} else {
Log.e(TAG, "ReCaptcha failed");
}
@@ -791,7 +798,7 @@ public class VideoDetailFragment
player.onPause();
}
restoreDefaultOrientation();
- setAutoplay(false);
+ setAutoPlay(false);
return true;
}
@@ -819,14 +826,11 @@ public class VideoDetailFragment
}
private void setupFromHistoryItem(final StackItem item) {
- setAutoplay(false);
+ setAutoPlay(false);
hideMainPlayer();
- setInitialData(
- item.getServiceId(),
- item.getUrl(),
- !TextUtils.isEmpty(item.getTitle()) ? item.getTitle() : "",
- item.getPlayQueue());
+ setInitialData(item.getServiceId(), item.getUrl(),
+ item.getTitle() == null ? "" : item.getTitle(), item.getPlayQueue());
startLoading(false);
// Maybe an item was deleted in background activity
@@ -860,18 +864,17 @@ public class VideoDetailFragment
}
}
- public void selectAndLoadVideo(final int sid, final String videoUrl, final String title,
- final PlayQueue queue) {
- // Situation when user switches from players to main player.
- // All needed data is here, we can start watching
- if (this.playQueue != null && this.playQueue.equals(queue)) {
- openVideoPlayer();
- return;
- }
- setInitialData(sid, videoUrl, title, queue);
- if (player != null) {
+ public void selectAndLoadVideo(final int newServiceId,
+ @Nullable final String newUrl,
+ @NonNull final String newTitle,
+ @Nullable final PlayQueue newQueue) {
+ if (player != null && newQueue != null && playQueue != null
+ && !Objects.equals(newQueue.getItem(), playQueue.getItem())) {
+ // Preloading can be disabled since playback is surely being replaced.
player.disablePreloadingOfCurrentTrack();
}
+
+ setInitialData(newServiceId, newUrl, newTitle, newQueue);
startLoading(false, true);
}
@@ -956,7 +959,7 @@ public class VideoDetailFragment
playQueue = new SinglePlayQueue(result);
}
if (stack.isEmpty() || !stack.peek().getPlayQueue().equals(playQueue)) {
- stack.push(new StackItem(serviceId, url, name, playQueue));
+ stack.push(new StackItem(serviceId, url, title, playQueue));
}
}
if (isAutoplayEnabled()) {
@@ -977,7 +980,7 @@ public class VideoDetailFragment
if (shouldShowComments()) {
pageAdapter.addFragment(
- CommentsFragment.getInstance(serviceId, url, name), COMMENTS_TAB_TAG);
+ CommentsFragment.getInstance(serviceId, url, title), COMMENTS_TAB_TAG);
}
if (showRelatedStreams && null == relatedStreamsLayout) {
@@ -1068,7 +1071,7 @@ public class VideoDetailFragment
}
}
- private void openVideoPlayer() {
+ public void openVideoPlayer() {
if (PreferenceManager.getDefaultSharedPreferences(activity)
.getBoolean(this.getString(R.string.use_external_video_player_key), false)) {
showExternalPlaybackDialog();
@@ -1143,8 +1146,8 @@ public class VideoDetailFragment
// Utils
//////////////////////////////////////////////////////////////////////////*/
- public void setAutoplay(final boolean autoplay) {
- this.autoPlayEnabled = autoplay;
+ public void setAutoPlay(final boolean autoPlay) {
+ this.autoPlayEnabled = autoPlay;
}
private void startOnExternalPlayer(@NonNull final Context context,
@@ -1166,7 +1169,7 @@ public class VideoDetailFragment
.getBoolean(getString(R.string.use_external_video_player_key), false);
}
- // This method overrides default behaviour when setAutoplay() is called.
+ // This method overrides default behaviour when setAutoPlay() is called.
// Don't auto play if the user selected an external player or disabled it in settings
private boolean isAutoplayEnabled() {
return autoPlayEnabled
@@ -1302,12 +1305,14 @@ public class VideoDetailFragment
contentRootLayoutHiding.setVisibility(View.VISIBLE);
}
- protected void setInitialData(final int sid, final String u, final String title,
- final PlayQueue queue) {
- this.serviceId = sid;
- this.url = u;
- this.name = !TextUtils.isEmpty(title) ? title : "";
- this.playQueue = queue;
+ protected void setInitialData(final int newServiceId,
+ @Nullable final String newUrl,
+ @NonNull final String newTitle,
+ @Nullable final PlayQueue newPlayQueue) {
+ this.serviceId = newServiceId;
+ this.url = newUrl;
+ this.title = newTitle;
+ this.playQueue = newPlayQueue;
}
private void setErrorImage(final int imageResource) {
@@ -1400,7 +1405,7 @@ public class VideoDetailFragment
animateView(detailPositionView, false, 100);
animateView(positionView, false, 50);
- videoTitleTextView.setText(name != null ? name : "");
+ videoTitleTextView.setText(title);
videoTitleTextView.setMaxLines(1);
animateView(videoTitleTextView, true, 0);
@@ -1445,7 +1450,7 @@ public class VideoDetailFragment
}
}
animateView(thumbnailPlayButton, true, 200);
- videoTitleTextView.setText(name);
+ videoTitleTextView.setText(title);
if (!TextUtils.isEmpty(info.getSubChannelName())) {
displayBothUploaderAndSubChannel(info);
@@ -1738,7 +1743,7 @@ public class VideoDetailFragment
if (DEBUG) {
Log.d(TAG, "onQueueUpdate() called with: serviceId = ["
+ serviceId + "], videoUrl = [" + url + "], name = ["
- + name + "], playQueue = [" + playQueue + "]");
+ + title + "], playQueue = [" + playQueue + "]");
}
// This should be the only place where we push data to stack.
@@ -1823,7 +1828,7 @@ public class VideoDetailFragment
currentInfo = info;
setInitialData(info.getServiceId(), info.getUrl(), info.getName(), queue);
- setAutoplay(false);
+ setAutoPlay(false);
// Delay execution just because it freezes the main thread, and while playing
// next/previous video you see visual glitches
// (when non-vertical video goes after vertical video)
@@ -2037,7 +2042,7 @@ public class VideoDetailFragment
private void checkLandscape() {
if ((!player.isPlaying() && player.getPlayQueue() != playQueue)
|| player.getPlayQueue() == null) {
- setAutoplay(true);
+ setAutoPlay(true);
}
player.checkLandscape();
@@ -2287,10 +2292,10 @@ public class VideoDetailFragment
});
}
- private void updateOverlayData(@Nullable final String title,
+ private void updateOverlayData(@Nullable final String overlayTitle,
@Nullable final String uploader,
@Nullable final String thumbnailUrl) {
- overlayTitleTextView.setText(TextUtils.isEmpty(title) ? "" : title);
+ overlayTitleTextView.setText(TextUtils.isEmpty(overlayTitle) ? "" : overlayTitle);
overlayChannelTextView.setText(TextUtils.isEmpty(uploader) ? "" : uploader);
overlayThumbnailImageView.setImageResource(R.drawable.dummy_thumbnail_dark);
if (!TextUtils.isEmpty(thumbnailUrl)) {
diff --git a/app/src/main/java/org/schabi/newpipe/fragments/list/BaseListFragment.java b/app/src/main/java/org/schabi/newpipe/fragments/list/BaseListFragment.java
index 79e1854e9..41263bc34 100644
--- a/app/src/main/java/org/schabi/newpipe/fragments/list/BaseListFragment.java
+++ b/app/src/main/java/org/schabi/newpipe/fragments/list/BaseListFragment.java
@@ -321,8 +321,9 @@ public abstract class BaseListFragment extends BaseStateFragment
private void onStreamSelected(final StreamInfoItem selectedItem) {
onItemSelected(selectedItem);
- NavigationHelper.openVideoDetailFragment(getFM(),
- selectedItem.getServiceId(), selectedItem.getUrl(), selectedItem.getName());
+ NavigationHelper.openVideoDetailFragment(requireContext(), getFM(),
+ selectedItem.getServiceId(), selectedItem.getUrl(), selectedItem.getName(),
+ null, false);
}
protected void onScrollToBottom() {
diff --git a/app/src/main/java/org/schabi/newpipe/fragments/list/channel/ChannelFragment.java b/app/src/main/java/org/schabi/newpipe/fragments/list/channel/ChannelFragment.java
index 58e28df49..6ec818909 100644
--- a/app/src/main/java/org/schabi/newpipe/fragments/list/channel/ChannelFragment.java
+++ b/app/src/main/java/org/schabi/newpipe/fragments/list/channel/ChannelFragment.java
@@ -517,7 +517,7 @@ public class ChannelFragment extends BaseListInfoFragment
monitorSubscription(result);
headerPlayAllButton.setOnClickListener(view -> NavigationHelper
- .playOnMainPlayer(activity, getPlayQueue(), true));
+ .playOnMainPlayer(activity, getPlayQueue()));
headerPopupButton.setOnClickListener(view -> NavigationHelper
.playOnPopupPlayer(activity, getPlayQueue(), false));
headerBackgroundButton.setOnClickListener(view -> NavigationHelper
diff --git a/app/src/main/java/org/schabi/newpipe/fragments/list/playlist/PlaylistFragment.java b/app/src/main/java/org/schabi/newpipe/fragments/list/playlist/PlaylistFragment.java
index 67f1a007a..71b51f9a1 100644
--- a/app/src/main/java/org/schabi/newpipe/fragments/list/playlist/PlaylistFragment.java
+++ b/app/src/main/java/org/schabi/newpipe/fragments/list/playlist/PlaylistFragment.java
@@ -319,7 +319,7 @@ public class PlaylistFragment extends BaseListInfoFragment {
.subscribe(getPlaylistBookmarkSubscriber());
headerPlayAllButton.setOnClickListener(view ->
- NavigationHelper.playOnMainPlayer(activity, getPlayQueue(), true));
+ NavigationHelper.playOnMainPlayer(activity, getPlayQueue()));
headerPopupButton.setOnClickListener(view ->
NavigationHelper.playOnPopupPlayer(activity, getPlayQueue(), false));
headerBackgroundButton.setOnClickListener(view ->
diff --git a/app/src/main/java/org/schabi/newpipe/local/history/StatisticsPlaylistFragment.java b/app/src/main/java/org/schabi/newpipe/local/history/StatisticsPlaylistFragment.java
index b4398d873..8cd4e4c7e 100644
--- a/app/src/main/java/org/schabi/newpipe/local/history/StatisticsPlaylistFragment.java
+++ b/app/src/main/java/org/schabi/newpipe/local/history/StatisticsPlaylistFragment.java
@@ -25,6 +25,7 @@ import org.reactivestreams.Subscription;
import org.schabi.newpipe.R;
import org.schabi.newpipe.database.LocalItem;
import org.schabi.newpipe.database.stream.StreamStatisticsEntry;
+import org.schabi.newpipe.database.stream.model.StreamEntity;
import org.schabi.newpipe.extractor.stream.StreamInfoItem;
import org.schabi.newpipe.extractor.stream.StreamType;
import org.schabi.newpipe.info_list.InfoItemDialog;
@@ -149,11 +150,10 @@ public class StatisticsPlaylistFragment
@Override
public void selected(final LocalItem selectedItem) {
if (selectedItem instanceof StreamStatisticsEntry) {
- final StreamStatisticsEntry item = (StreamStatisticsEntry) selectedItem;
- NavigationHelper.openVideoDetailFragment(getFM(),
- item.getStreamEntity().getServiceId(),
- item.getStreamEntity().getUrl(),
- item.getStreamEntity().getTitle());
+ final StreamEntity item =
+ ((StreamStatisticsEntry) selectedItem).getStreamEntity();
+ NavigationHelper.openVideoDetailFragment(requireContext(), getFM(),
+ item.getServiceId(), item.getUrl(), item.getTitle(), null, false);
}
}
@@ -325,7 +325,7 @@ public class StatisticsPlaylistFragment
}
headerPlayAllButton.setOnClickListener(view ->
- NavigationHelper.playOnMainPlayer(activity, getPlayQueue(), true));
+ NavigationHelper.playOnMainPlayer(activity, getPlayQueue()));
headerPopupButton.setOnClickListener(view ->
NavigationHelper.playOnPopupPlayer(activity, getPlayQueue(), false));
headerBackgroundButton.setOnClickListener(view ->
diff --git a/app/src/main/java/org/schabi/newpipe/local/playlist/LocalPlaylistFragment.java b/app/src/main/java/org/schabi/newpipe/local/playlist/LocalPlaylistFragment.java
index 32fac9de0..71df07a4b 100644
--- a/app/src/main/java/org/schabi/newpipe/local/playlist/LocalPlaylistFragment.java
+++ b/app/src/main/java/org/schabi/newpipe/local/playlist/LocalPlaylistFragment.java
@@ -30,6 +30,7 @@ import org.schabi.newpipe.R;
import org.schabi.newpipe.database.LocalItem;
import org.schabi.newpipe.database.history.model.StreamHistoryEntry;
import org.schabi.newpipe.database.playlist.PlaylistStreamEntry;
+import org.schabi.newpipe.database.stream.model.StreamEntity;
import org.schabi.newpipe.database.stream.model.StreamStateEntity;
import org.schabi.newpipe.extractor.stream.StreamInfoItem;
import org.schabi.newpipe.extractor.stream.StreamType;
@@ -178,10 +179,10 @@ public class LocalPlaylistFragment extends BaseLocalListFragment
- NavigationHelper.playOnMainPlayer(activity, getPlayQueue(), true));
+ NavigationHelper.playOnMainPlayer(activity, getPlayQueue()));
headerPopupButton.setOnClickListener(view ->
NavigationHelper.playOnPopupPlayer(activity, getPlayQueue(), false));
headerBackgroundButton.setOnClickListener(view ->
diff --git a/app/src/main/java/org/schabi/newpipe/player/ServicePlayerActivity.java b/app/src/main/java/org/schabi/newpipe/player/ServicePlayerActivity.java
index 8b606260a..fee189295 100644
--- a/app/src/main/java/org/schabi/newpipe/player/ServicePlayerActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/player/ServicePlayerActivity.java
@@ -367,7 +367,9 @@ public abstract class ServicePlayerActivity extends AppCompatActivity
final MenuItem detail = popupMenu.getMenu().add(RECYCLER_ITEM_POPUP_MENU_GROUP_ID, 1,
Menu.NONE, R.string.play_queue_stream_detail);
detail.setOnMenuItemClickListener(menuItem -> {
- onOpenDetail(item.getServiceId(), item.getUrl(), item.getTitle());
+ // playQueue is null since we don't want any queue change
+ NavigationHelper.openVideoDetail(
+ this, item.getServiceId(), item.getUrl(), item.getTitle(), null);
return true;
});
@@ -454,11 +456,6 @@ public abstract class ServicePlayerActivity extends AppCompatActivity
};
}
- private void onOpenDetail(final int serviceId, final String videoUrl,
- final String videoTitle) {
- NavigationHelper.openVideoDetail(this, serviceId, videoUrl, videoTitle);
- }
-
private void scrollToSelected() {
if (player == null) {
return;
diff --git a/app/src/main/java/org/schabi/newpipe/player/VideoPlayerImpl.java b/app/src/main/java/org/schabi/newpipe/player/VideoPlayerImpl.java
index 97007f0f6..765eb148b 100644
--- a/app/src/main/java/org/schabi/newpipe/player/VideoPlayerImpl.java
+++ b/app/src/main/java/org/schabi/newpipe/player/VideoPlayerImpl.java
@@ -785,7 +785,7 @@ public class VideoPlayerImpl extends VideoPlayer
intent.putExtra(Constants.KEY_LINK_TYPE, StreamingService.LinkType.STREAM);
intent.putExtra(Constants.KEY_URL, getVideoUrl());
intent.putExtra(Constants.KEY_TITLE, getVideoTitle());
- intent.putExtra(VideoDetailFragment.AUTO_PLAY, true);
+ intent.putExtra(VideoDetailFragment.KEY_SWITCHING_PLAYERS, true);
service.onDestroy();
context.startActivity(intent);
}
diff --git a/app/src/main/java/org/schabi/newpipe/player/playqueue/PlayQueue.java b/app/src/main/java/org/schabi/newpipe/player/playqueue/PlayQueue.java
index 4f35f98f5..b8bb677e0 100644
--- a/app/src/main/java/org/schabi/newpipe/player/playqueue/PlayQueue.java
+++ b/app/src/main/java/org/schabi/newpipe/player/playqueue/PlayQueue.java
@@ -1,12 +1,8 @@
package org.schabi.newpipe.player.playqueue;
-import android.util.Log;
-
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
-import org.reactivestreams.Subscriber;
-import org.reactivestreams.Subscription;
import org.schabi.newpipe.MainActivity;
import org.schabi.newpipe.player.playqueue.events.AppendEvent;
import org.schabi.newpipe.player.playqueue.events.ErrorEvent;
@@ -43,7 +39,6 @@ import io.reactivex.subjects.BehaviorSubject;
*
*/
public abstract class PlayQueue implements Serializable {
- private final String TAG = "PlayQueue@" + Integer.toHexString(hashCode());
public static final boolean DEBUG = MainActivity.DEBUG;
private ArrayList backup;
@@ -55,7 +50,6 @@ public abstract class PlayQueue implements Serializable {
private transient BehaviorSubject eventBroadcast;
private transient Flowable broadcastReceiver;
- private transient Subscription reportingReactor;
private transient boolean disposed;
@@ -87,10 +81,6 @@ public abstract class PlayQueue implements Serializable {
broadcastReceiver = eventBroadcast.toFlowable(BackpressureStrategy.BUFFER)
.observeOn(AndroidSchedulers.mainThread())
.startWith(new InitEvent());
-
- if (DEBUG) {
- broadcastReceiver.subscribe(getSelfReporter());
- }
}
/**
@@ -100,13 +90,9 @@ public abstract class PlayQueue implements Serializable {
if (eventBroadcast != null) {
eventBroadcast.onComplete();
}
- if (reportingReactor != null) {
- reportingReactor.cancel();
- }
eventBroadcast = null;
broadcastReceiver = null;
- reportingReactor = null;
disposed = true;
}
@@ -544,35 +530,5 @@ public abstract class PlayQueue implements Serializable {
eventBroadcast.onNext(event);
}
}
-
- private Subscriber getSelfReporter() {
- return new Subscriber() {
- @Override
- public void onSubscribe(final Subscription s) {
- if (reportingReactor != null) {
- reportingReactor.cancel();
- }
- reportingReactor = s;
- reportingReactor.request(1);
- }
-
- @Override
- public void onNext(final PlayQueueEvent event) {
- Log.d(TAG, "Received broadcast: " + event.type().name() + ". "
- + "Current index: " + getIndex() + ", play queue length: " + size() + ".");
- reportingReactor.request(1);
- }
-
- @Override
- public void onError(final Throwable t) {
- Log.e(TAG, "Received broadcast error", t);
- }
-
- @Override
- public void onComplete() {
- Log.d(TAG, "Broadcast is shutting down.");
- }
- };
- }
}
diff --git a/app/src/main/java/org/schabi/newpipe/util/NavigationHelper.java b/app/src/main/java/org/schabi/newpipe/util/NavigationHelper.java
index 6761fce59..a96730552 100644
--- a/app/src/main/java/org/schabi/newpipe/util/NavigationHelper.java
+++ b/app/src/main/java/org/schabi/newpipe/util/NavigationHelper.java
@@ -18,7 +18,6 @@ import androidx.core.content.ContextCompat;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentManager;
import androidx.fragment.app.FragmentTransaction;
-import androidx.preference.PreferenceManager;
import com.nostra13.universalimageloader.core.ImageLoader;
@@ -52,13 +51,14 @@ import org.schabi.newpipe.player.BackgroundPlayerActivity;
import org.schabi.newpipe.player.BasePlayer;
import org.schabi.newpipe.player.MainPlayer;
import org.schabi.newpipe.player.VideoPlayer;
+import org.schabi.newpipe.player.helper.PlayerHelper;
+import org.schabi.newpipe.player.helper.PlayerHolder;
import org.schabi.newpipe.player.playqueue.PlayQueue;
import org.schabi.newpipe.player.playqueue.PlayQueueItem;
import org.schabi.newpipe.settings.SettingsActivity;
import java.util.ArrayList;
-@SuppressWarnings({"unused"})
public final class NavigationHelper {
public static final String MAIN_FRAGMENT_TAG = "main_fragment_tag";
public static final String SEARCH_FRAGMENT_TAG = "search_fragment_tag";
@@ -130,42 +130,22 @@ public final class NavigationHelper {
}
public static void playOnMainPlayer(final AppCompatActivity activity,
- final PlayQueue queue,
- final boolean autoPlay) {
- playOnMainPlayer(activity.getSupportFragmentManager(), queue, autoPlay);
+ @NonNull final PlayQueue playQueue) {
+ final PlayQueueItem item = playQueue.getItem();
+ assert item != null;
+ openVideoDetailFragment(activity, activity.getSupportFragmentManager(),
+ item.getServiceId(), item.getUrl(), item.getTitle(), playQueue, false);
}
- public static void playOnMainPlayer(final FragmentManager fragmentManager,
- final PlayQueue queue,
- final boolean autoPlay) {
- final PlayQueueItem currentStream = queue.getItem();
- openVideoDetailFragment(
- fragmentManager,
- currentStream.getServiceId(),
- currentStream.getUrl(),
- currentStream.getTitle(),
- autoPlay,
- queue);
+ public static void playOnMainPlayer(final Context context,
+ @NonNull final PlayQueue playQueue) {
+ final PlayQueueItem item = playQueue.getItem();
+ assert item != null;
+ openVideoDetail(context, item.getServiceId(), item.getUrl(), item.getTitle(), playQueue);
}
- public static void playOnMainPlayer(@NonNull final Context context,
- @Nullable final PlayQueue queue,
- @NonNull final StreamingService.LinkType linkType,
- @NonNull final String url,
- @NonNull final String title,
- final boolean autoPlay,
- final boolean resumePlayback) {
-
- final Intent intent = getPlayerIntent(context, MainActivity.class, queue, resumePlayback);
- intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
- intent.putExtra(Constants.KEY_LINK_TYPE, linkType);
- intent.putExtra(Constants.KEY_URL, url);
- intent.putExtra(Constants.KEY_TITLE, title);
- intent.putExtra(VideoDetailFragment.AUTO_PLAY, autoPlay);
- context.startActivity(intent);
- }
-
- public static void playOnPopupPlayer(final Context context, final PlayQueue queue,
+ public static void playOnPopupPlayer(final Context context,
+ final PlayQueue queue,
final boolean resumePlayback) {
if (!PermissionHelper.isPopupEnabled(context)) {
PermissionHelper.showPopupEnablementToast(context);
@@ -300,9 +280,6 @@ public final class NavigationHelper {
.setNegativeButton(R.string.cancel, (dialog, which)
-> Log.i("NavigationHelper", "You unlocked a secret unicorn."))
.show();
-// Log.e("NavigationHelper",
-// "Either no Streaming player for audio was installed, "
-// + "or something important crashed:");
} else {
Toast.makeText(context, R.string.no_player_found_toast, Toast.LENGTH_LONG).show();
}
@@ -358,41 +335,6 @@ public final class NavigationHelper {
.commit();
}
- public static void openVideoDetailFragment(final FragmentManager fragmentManager,
- final int serviceId, final String url,
- final String title) {
- openVideoDetailFragment(fragmentManager, serviceId, url, title, true, null);
- }
-
- public static void openVideoDetailFragment(
- final FragmentManager fragmentManager,
- final int serviceId,
- final String url,
- final String title,
- final boolean autoPlay,
- final PlayQueue playQueue) {
- final Fragment fragment = fragmentManager.findFragmentById(R.id.fragment_player_holder);
-
- if (fragment instanceof VideoDetailFragment && fragment.isVisible()) {
- expandMainPlayer(fragment.requireActivity());
- final VideoDetailFragment detailFragment = (VideoDetailFragment) fragment;
- detailFragment.setAutoplay(autoPlay);
- detailFragment
- .selectAndLoadVideo(serviceId, url, title == null ? "" : title, playQueue);
- detailFragment.scrollToTop();
- return;
- }
-
- final VideoDetailFragment instance = VideoDetailFragment
- .getInstance(serviceId, url, title == null ? "" : title, playQueue);
- instance.setAutoplay(autoPlay);
-
- defaultTransaction(fragmentManager)
- .replace(R.id.fragment_player_holder, instance)
- .runOnCommit(() -> expandMainPlayer(instance.requireActivity()))
- .commit();
- }
-
public static void expandMainPlayer(final Context context) {
context.sendBroadcast(new Intent(VideoDetailFragment.ACTION_SHOW_MAIN_PLAYER));
}
@@ -409,33 +351,86 @@ public final class NavigationHelper {
.commitAllowingStateLoss();
}
+ private interface RunnableWithVideoDetailFragment {
+ void run(VideoDetailFragment detailFragment);
+ }
+
+ public static void openVideoDetailFragment(@NonNull final Context context,
+ @NonNull final FragmentManager fragmentManager,
+ final int serviceId,
+ @Nullable final String url,
+ @NonNull final String title,
+ @Nullable final PlayQueue playQueue,
+ final boolean switchingPlayers) {
+
+ final boolean autoPlay;
+ @Nullable final MainPlayer.PlayerType playerType = PlayerHolder.getType();
+ if (playerType == null) {
+ // no player open
+ autoPlay = PlayerHelper.isAutoplayAllowedByUser(context);
+ } else if (switchingPlayers) {
+ // switching player to main player
+ autoPlay = true;
+ } else if (playerType == MainPlayer.PlayerType.VIDEO) {
+ // opening new stream while already playing in main player
+ autoPlay = PlayerHelper.isAutoplayAllowedByUser(context);
+ } else {
+ // opening new stream while already playing in another player
+ autoPlay = false;
+ }
+
+ final RunnableWithVideoDetailFragment onVideoDetailFragmentReady = (detailFragment) -> {
+ expandMainPlayer(detailFragment.requireActivity());
+ detailFragment.setAutoPlay(autoPlay);
+ if (switchingPlayers) {
+ // Situation when user switches from players to main player. All needed data is
+ // here, we can start watching (assuming newQueue equals playQueue).
+ detailFragment.openVideoPlayer();
+ } else {
+ detailFragment.selectAndLoadVideo(serviceId, url, title, playQueue);
+ }
+ detailFragment.scrollToTop();
+ };
+
+ final Fragment fragment = fragmentManager.findFragmentById(R.id.fragment_player_holder);
+ if (fragment instanceof VideoDetailFragment && fragment.isVisible()) {
+ onVideoDetailFragmentReady.run((VideoDetailFragment) fragment);
+ } else {
+ final VideoDetailFragment instance = VideoDetailFragment
+ .getInstance(serviceId, url, title, playQueue);
+ instance.setAutoPlay(autoPlay);
+
+ defaultTransaction(fragmentManager)
+ .replace(R.id.fragment_player_holder, instance)
+ .runOnCommit(() -> onVideoDetailFragmentReady.run(instance))
+ .commit();
+ }
+ }
+
public static void openChannelFragment(final FragmentManager fragmentManager,
final int serviceId, final String url,
- final String name) {
+ @NonNull final String name) {
defaultTransaction(fragmentManager)
- .replace(R.id.fragment_holder, ChannelFragment.getInstance(serviceId, url,
- name == null ? "" : name))
+ .replace(R.id.fragment_holder, ChannelFragment.getInstance(serviceId, url, name))
.addToBackStack(null)
.commit();
}
public static void openCommentsFragment(final FragmentManager fragmentManager,
final int serviceId, final String url,
- final String name) {
+ @NonNull final String name) {
fragmentManager.beginTransaction()
.setCustomAnimations(R.anim.switch_service_in, R.anim.switch_service_out)
- .replace(R.id.fragment_holder, CommentsFragment.getInstance(serviceId, url,
- name == null ? "" : name))
+ .replace(R.id.fragment_holder, CommentsFragment.getInstance(serviceId, url, name))
.addToBackStack(null)
.commit();
}
public static void openPlaylistFragment(final FragmentManager fragmentManager,
final int serviceId, final String url,
- final String name) {
+ @NonNull final String name) {
defaultTransaction(fragmentManager)
- .replace(R.id.fragment_holder, PlaylistFragment.getInstance(serviceId, url,
- name == null ? "" : name))
+ .replace(R.id.fragment_holder, PlaylistFragment.getInstance(serviceId, url, name))
.addToBackStack(null)
.commit();
}
@@ -511,33 +506,31 @@ public final class NavigationHelper {
context.startActivity(mIntent);
}
- public static void openChannel(final Context context, final int serviceId, final String url) {
- openChannel(context, serviceId, url, null);
- }
-
public static void openChannel(final Context context, final int serviceId,
- final String url, final String name) {
+ final String url, @NonNull final String name) {
final Intent openIntent = getOpenIntent(context, url, serviceId,
StreamingService.LinkType.CHANNEL);
- if (name != null && !name.isEmpty()) {
- openIntent.putExtra(Constants.KEY_TITLE, name);
- }
+ openIntent.putExtra(Constants.KEY_TITLE, name);
context.startActivity(openIntent);
}
- public static void openVideoDetail(final Context context, final int serviceId,
- final String url) {
- openVideoDetail(context, serviceId, url, null);
- }
+ public static void openVideoDetail(final Context context,
+ final int serviceId,
+ final String url,
+ @NonNull final String title,
+ @Nullable final PlayQueue playQueue) {
- public static void openVideoDetail(final Context context, final int serviceId,
- final String url, final String title) {
- final Intent openIntent = getOpenIntent(context, url, serviceId,
+ final Intent intent = getOpenIntent(context, url, serviceId,
StreamingService.LinkType.STREAM);
- if (title != null && !title.isEmpty()) {
- openIntent.putExtra(Constants.KEY_TITLE, title);
+ intent.putExtra(Constants.KEY_TITLE, title);
+
+ if (playQueue != null) {
+ final String cacheKey = SerializedCache.getInstance().put(playQueue, PlayQueue.class);
+ if (cacheKey != null) {
+ intent.putExtra(VideoPlayer.PLAY_QUEUE_KEY, cacheKey);
+ }
}
- context.startActivity(openIntent);
+ context.startActivity(intent);
}
public static void openMainActivity(final Context context) {
@@ -550,7 +543,6 @@ public final class NavigationHelper {
public static void openRouterActivity(final Context context, final String url) {
final Intent mIntent = new Intent(context, RouterActivity.class);
mIntent.setData(Uri.parse(url));
- mIntent.putExtra(RouterActivity.INTERNAL_ROUTE_KEY, true);
context.startActivity(mIntent);
}
@@ -564,14 +556,12 @@ public final class NavigationHelper {
context.startActivity(intent);
}
- public static boolean openDownloads(final Activity activity) {
- if (!PermissionHelper.checkStoragePermissions(
+ public static void openDownloads(final Activity activity) {
+ if (PermissionHelper.checkStoragePermissions(
activity, PermissionHelper.DOWNLOADS_REQUEST_CODE)) {
- return false;
+ final Intent intent = new Intent(activity, DownloadActivity.class);
+ activity.startActivity(intent);
}
- final Intent intent = new Intent(activity, DownloadActivity.class);
- activity.startActivity(intent);
- return true;
}
public static Intent getPlayQueueActivityIntent(final Context context) {
@@ -600,7 +590,8 @@ public final class NavigationHelper {
return getIntentByLink(context, NewPipe.getServiceByUrl(url), url);
}
- public static Intent getIntentByLink(final Context context, final StreamingService service,
+ public static Intent getIntentByLink(final Context context,
+ final StreamingService service,
final String url) throws ExtractionException {
final StreamingService.LinkType linkType = service.getLinkTypeByUrl(url);
@@ -609,15 +600,7 @@ public final class NavigationHelper {
+ " url=" + url);
}
- final Intent rIntent = getOpenIntent(context, url, service.getServiceId(), linkType);
-
- if (linkType == StreamingService.LinkType.STREAM) {
- rIntent.putExtra(VideoDetailFragment.AUTO_PLAY,
- PreferenceManager.getDefaultSharedPreferences(context).getBoolean(
- context.getString(R.string.autoplay_through_intent_key), false));
- }
-
- return rIntent;
+ return getOpenIntent(context, url, service.getServiceId(), linkType);
}
private static Uri openMarketUrl(final String packageName) {
diff --git a/app/src/main/res/values/settings_keys.xml b/app/src/main/res/values/settings_keys.xml
index 1aa781fe2..9c9fa4853 100644
--- a/app/src/main/res/values/settings_keys.xml
+++ b/app/src/main/res/values/settings_keys.xml
@@ -21,7 +21,6 @@
use_external_video_player
use_external_audio_player
- autoplay_through_intent
use_oldplayer
volume_gesture_control
From bb882ada2c4460c9c3705a6fdf461be205f6a2fc Mon Sep 17 00:00:00 2001
From: Stypox
Date: Sun, 18 Oct 2020 20:33:08 +0200
Subject: [PATCH 2/7] Show "Show info" instead of "Video player" if a stream is
playing not on the main player when sharing something to NewPipe
---
.../org/schabi/newpipe/RouterActivity.java | 72 +++++++++----------
1 file changed, 35 insertions(+), 37 deletions(-)
diff --git a/app/src/main/java/org/schabi/newpipe/RouterActivity.java b/app/src/main/java/org/schabi/newpipe/RouterActivity.java
index ca145bb9a..4f563a1d1 100644
--- a/app/src/main/java/org/schabi/newpipe/RouterActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/RouterActivity.java
@@ -40,7 +40,9 @@ import org.schabi.newpipe.extractor.exceptions.ExtractionException;
import org.schabi.newpipe.extractor.playlist.PlaylistInfo;
import org.schabi.newpipe.extractor.stream.StreamInfo;
import org.schabi.newpipe.extractor.stream.VideoStream;
+import org.schabi.newpipe.player.MainPlayer;
import org.schabi.newpipe.player.helper.PlayerHelper;
+import org.schabi.newpipe.player.helper.PlayerHolder;
import org.schabi.newpipe.player.playqueue.ChannelPlayQueue;
import org.schabi.newpipe.player.playqueue.PlayQueue;
import org.schabi.newpipe.player.playqueue.PlaylistPlayQueue;
@@ -394,14 +396,22 @@ public class RouterActivity extends AppCompatActivity {
// show both "show info" and "video player", they are two different activities
returnList.add(showInfo);
returnList.add(videoPlayer);
- } else if (capabilities.contains(VIDEO)
- && PlayerHelper.isAutoplayAllowedByUser(context)) {
- // show only "video player" since the details activity will be opened and the video
- // will be autoplayed there and "show info" would do the exact same thing
- returnList.add(videoPlayer);
} else {
- // show only "show info" if video player is not applicable or autoplay is disabled
- returnList.add(showInfo);
+ final MainPlayer.PlayerType playerType = PlayerHolder.getType();
+ if (capabilities.contains(VIDEO)
+ && PlayerHelper.isAutoplayAllowedByUser(context)
+ && playerType == null || playerType == MainPlayer.PlayerType.VIDEO) {
+ // show only "video player" since the details activity will be opened and the
+ // video will be auto played there. Since "show info" would do the exact same
+ // thing, use that as a key to let VideoDetailFragment load the stream instead
+ // of using FetcherService (see comment in handleChoice())
+ returnList.add(new AdapterChoiceItem(
+ showInfo.key, videoPlayer.description, videoPlayer.icon));
+ } else {
+ // show only "show info" if video player is not applicable, auto play is
+ // disabled or a video is playing in a player different than the main one
+ returnList.add(showInfo);
+ }
}
if (capabilities.contains(VIDEO)) {
@@ -489,7 +499,6 @@ public class RouterActivity extends AppCompatActivity {
.observeOn(AndroidSchedulers.mainThread())
.subscribe(intent -> {
startActivity(intent);
-
finish();
}, throwable -> handleError(throwable, currentUrl))
);
@@ -657,41 +666,30 @@ public class RouterActivity extends AppCompatActivity {
final boolean isExtAudioEnabled = preferences.getBoolean(
getString(R.string.use_external_audio_player_key), false);
- PlayQueue playQueue;
- final String playerChoice = choice.playerChoice;
-
+ final PlayQueue playQueue;
if (info instanceof StreamInfo) {
- if (playerChoice.equals(backgroundPlayerKey) && isExtAudioEnabled) {
+ if (choice.playerChoice.equals(backgroundPlayerKey) && isExtAudioEnabled) {
NavigationHelper.playOnExternalAudioPlayer(this, (StreamInfo) info);
-
- } else if (playerChoice.equals(videoPlayerKey) && isExtVideoEnabled) {
+ return;
+ } else if (choice.playerChoice.equals(videoPlayerKey) && isExtVideoEnabled) {
NavigationHelper.playOnExternalVideoPlayer(this, (StreamInfo) info);
-
- } else {
- playQueue = new SinglePlayQueue((StreamInfo) info);
-
- if (playerChoice.equals(videoPlayerKey)) {
- NavigationHelper.playOnMainPlayer(this, playQueue);
- } else if (playerChoice.equals(backgroundPlayerKey)) {
- NavigationHelper.playOnBackgroundPlayer(this, playQueue, true);
- } else if (playerChoice.equals(popupPlayerKey)) {
- NavigationHelper.playOnPopupPlayer(this, playQueue, true);
- }
+ return;
}
+ playQueue = new SinglePlayQueue((StreamInfo) info);
+ } else if (info instanceof ChannelInfo) {
+ playQueue = new ChannelPlayQueue((ChannelInfo) info);
+ } else if (info instanceof PlaylistInfo) {
+ playQueue = new PlaylistPlayQueue((PlaylistInfo) info);
+ } else {
+ return;
}
- if (info instanceof ChannelInfo || info instanceof PlaylistInfo) {
- playQueue = info instanceof ChannelInfo
- ? new ChannelPlayQueue((ChannelInfo) info)
- : new PlaylistPlayQueue((PlaylistInfo) info);
-
- if (playerChoice.equals(videoPlayerKey)) {
- NavigationHelper.playOnMainPlayer(this, playQueue);
- } else if (playerChoice.equals(backgroundPlayerKey)) {
- NavigationHelper.playOnBackgroundPlayer(this, playQueue, true);
- } else if (playerChoice.equals(popupPlayerKey)) {
- NavigationHelper.playOnPopupPlayer(this, playQueue, true);
- }
+ if (choice.playerChoice.equals(videoPlayerKey)) {
+ NavigationHelper.playOnMainPlayer(this, playQueue);
+ } else if (choice.playerChoice.equals(backgroundPlayerKey)) {
+ NavigationHelper.playOnBackgroundPlayer(this, playQueue, true);
+ } else if (choice.playerChoice.equals(popupPlayerKey)) {
+ NavigationHelper.playOnPopupPlayer(this, playQueue, true);
}
};
}
From 2a2c82e73bb2380c07ab848b185952ab183a5502 Mon Sep 17 00:00:00 2001
From: Stypox
Date: Sat, 31 Oct 2020 20:26:09 +0100
Subject: [PATCH 3/7] More fixes with opening VideoDetailFragment
---
.../org/schabi/newpipe/RouterActivity.java | 2 +-
.../fragments/detail/VideoDetailFragment.java | 4 +-
.../player/BackgroundPlayerActivity.java | 28 ---------
.../org/schabi/newpipe/player/BasePlayer.java | 33 ++++++-----
.../org/schabi/newpipe/player/MainPlayer.java | 2 +-
.../newpipe/player/ServicePlayerActivity.java | 47 ++++++---------
.../newpipe/player/VideoPlayerImpl.java | 48 +++------------
.../player/event/BasePlayerGestureListener.kt | 5 +-
.../newpipe/player/helper/AudioReactor.java | 2 +-
.../newpipe/player/helper/PlayerHelper.java | 6 +-
.../newpipe/player/helper/PlayerHolder.java | 7 +++
.../player/playqueue/PlayQueueItem.java | 14 +++++
.../schabi/newpipe/util/NavigationHelper.java | 59 ++++---------------
13 files changed, 87 insertions(+), 170 deletions(-)
diff --git a/app/src/main/java/org/schabi/newpipe/RouterActivity.java b/app/src/main/java/org/schabi/newpipe/RouterActivity.java
index 4f563a1d1..537d71901 100644
--- a/app/src/main/java/org/schabi/newpipe/RouterActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/RouterActivity.java
@@ -685,7 +685,7 @@ public class RouterActivity extends AppCompatActivity {
}
if (choice.playerChoice.equals(videoPlayerKey)) {
- NavigationHelper.playOnMainPlayer(this, playQueue);
+ NavigationHelper.playOnMainPlayer(this, playQueue, false);
} else if (choice.playerChoice.equals(backgroundPlayerKey)) {
NavigationHelper.playOnBackgroundPlayer(this, playQueue, true);
} else if (choice.playerChoice.equals(popupPlayerKey)) {
diff --git a/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java b/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java
index ffba7f521..1324d6832 100644
--- a/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java
+++ b/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java
@@ -1097,7 +1097,7 @@ public final class VideoDetailFragment
private void openMainPlayer() {
if (playerService == null) {
- PlayerHolder.startService(App.getApp(), true, this);
+ PlayerHolder.startService(App.getApp(), autoPlayEnabled, this);
return;
}
if (currentInfo == null) {
@@ -1112,7 +1112,7 @@ public final class VideoDetailFragment
addVideoPlayerView();
final Intent playerIntent = NavigationHelper
- .getPlayerIntent(requireContext(), MainPlayer.class, queue, null, true);
+ .getPlayerIntent(requireContext(), MainPlayer.class, queue, true, autoPlayEnabled);
activity.startService(playerIntent);
}
diff --git a/app/src/main/java/org/schabi/newpipe/player/BackgroundPlayerActivity.java b/app/src/main/java/org/schabi/newpipe/player/BackgroundPlayerActivity.java
index 0e5222f5e..2fc710fb0 100644
--- a/app/src/main/java/org/schabi/newpipe/player/BackgroundPlayerActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/player/BackgroundPlayerActivity.java
@@ -2,11 +2,8 @@ package org.schabi.newpipe.player;
import android.content.Intent;
import android.view.Menu;
-import android.view.MenuItem;
import org.schabi.newpipe.R;
-import org.schabi.newpipe.util.NavigationHelper;
-import org.schabi.newpipe.util.PermissionHelper;
public final class BackgroundPlayerActivity extends ServicePlayerActivity {
@@ -46,31 +43,6 @@ public final class BackgroundPlayerActivity extends ServicePlayerActivity {
return R.menu.menu_play_queue_bg;
}
- @Override
- public boolean onPlayerOptionSelected(final MenuItem item) {
- if (item.getItemId() == R.id.action_switch_popup) {
-
- if (!PermissionHelper.isPopupEnabled(this)) {
- PermissionHelper.showPopupEnablementToast(this);
- return true;
- }
-
- this.player.setRecovery();
- NavigationHelper.playOnPopupPlayer(
- getApplicationContext(), player.playQueue, this.player.isPlaying());
- return true;
- }
-
- if (item.getItemId() == R.id.action_switch_background) {
- this.player.setRecovery();
- NavigationHelper.playOnBackgroundPlayer(
- getApplicationContext(), player.playQueue, this.player.isPlaying());
- return true;
- }
-
- return false;
- }
-
@Override
public void setupMenu(final Menu menu) {
if (player == null) {
diff --git a/app/src/main/java/org/schabi/newpipe/player/BasePlayer.java b/app/src/main/java/org/schabi/newpipe/player/BasePlayer.java
index 70f2e158b..1355f4285 100644
--- a/app/src/main/java/org/schabi/newpipe/player/BasePlayer.java
+++ b/app/src/main/java/org/schabi/newpipe/player/BasePlayer.java
@@ -125,7 +125,7 @@ public abstract class BasePlayer implements
@NonNull
public static final String RESUME_PLAYBACK = "resume_playback";
@NonNull
- public static final String START_PAUSED = "start_paused";
+ public static final String PLAY_WHEN_READY = "play_when_ready";
@NonNull
public static final String SELECT_ON_APPEND = "select_on_append";
@NonNull
@@ -224,7 +224,7 @@ public abstract class BasePlayer implements
this.dataSource = new PlayerDataSource(context, userAgent, bandwidthMeter);
final TrackSelection.Factory trackSelectionFactory = PlayerHelper
- .getQualitySelector(context);
+ .getQualitySelector();
this.trackSelector = new CustomTrackSelector(context, trackSelectionFactory);
this.loadControl = new LoadController();
@@ -302,6 +302,7 @@ public abstract class BasePlayer implements
final boolean samePlayQueue = playQueue != null && playQueue.equals(queue);
final int repeatMode = intent.getIntExtra(REPEAT_MODE, getRepeatMode());
+ final boolean playWhenReady = intent.getBooleanExtra(PLAY_WHEN_READY, true);
final boolean isMuted = intent
.getBooleanExtra(IS_MUTED, simpleExoPlayer != null && isMuted());
@@ -327,16 +328,20 @@ public abstract class BasePlayer implements
simpleExoPlayer.retry();
}
simpleExoPlayer.seekTo(playQueue.getIndex(), queue.getItem().getRecoveryPosition());
- return;
+ simpleExoPlayer.setPlayWhenReady(playWhenReady);
- } else if (samePlayQueue && !playQueue.isDisposed() && simpleExoPlayer != null) {
+ } else if (simpleExoPlayer != null
+ && samePlayQueue
+ && playQueue != null
+ && !playQueue.isDisposed()) {
// Do not re-init the same PlayQueue. Save time
// Player can have state = IDLE when playback is stopped or failed
// and we should retry() in this case
if (simpleExoPlayer.getPlaybackState() == Player.STATE_IDLE) {
simpleExoPlayer.retry();
}
- return;
+ simpleExoPlayer.setPlayWhenReady(playWhenReady);
+
} else if (intent.getBooleanExtra(RESUME_PLAYBACK, false)
&& isPlaybackResumeEnabled()
&& !samePlayQueue) {
@@ -351,7 +356,7 @@ public abstract class BasePlayer implements
state -> {
queue.setRecovery(queue.getIndex(), state.getProgressTime());
initPlayback(queue, repeatMode, playbackSpeed, playbackPitch,
- playbackSkipSilence, true, isMuted);
+ playbackSkipSilence, playWhenReady, isMuted);
},
error -> {
if (DEBUG) {
@@ -359,24 +364,22 @@ public abstract class BasePlayer implements
}
// In case any error we can start playback without history
initPlayback(queue, repeatMode, playbackSpeed, playbackPitch,
- playbackSkipSilence, true, isMuted);
+ playbackSkipSilence, playWhenReady, isMuted);
},
() -> {
// Completed but not found in history
initPlayback(queue, repeatMode, playbackSpeed, playbackPitch,
- playbackSkipSilence, true, isMuted);
+ playbackSkipSilence, playWhenReady, isMuted);
}
);
databaseUpdateReactor.add(stateLoader);
- return;
}
+ } else {
+ // Good to go...
+ // In a case of equal PlayQueues we can re-init old one but only when it is disposed
+ initPlayback(samePlayQueue ? playQueue : queue, repeatMode, playbackSpeed,
+ playbackPitch, playbackSkipSilence, playWhenReady, isMuted);
}
- // Good to go...
- // In a case of equal PlayQueues we can re-init old one but only when it is disposed
- initPlayback(samePlayQueue ? playQueue : queue, repeatMode,
- playbackSpeed, playbackPitch, playbackSkipSilence,
- !intent.getBooleanExtra(START_PAUSED, false),
- isMuted);
}
private PlaybackParameters retrievePlaybackParametersFromPreferences() {
diff --git a/app/src/main/java/org/schabi/newpipe/player/MainPlayer.java b/app/src/main/java/org/schabi/newpipe/player/MainPlayer.java
index ea205bbdf..07ca7b339 100644
--- a/app/src/main/java/org/schabi/newpipe/player/MainPlayer.java
+++ b/app/src/main/java/org/schabi/newpipe/player/MainPlayer.java
@@ -240,7 +240,7 @@ public final class MainPlayer extends Service {
}
public void removeViewFromParent() {
- if (getView().getParent() != null) {
+ if (getView() != null && getView().getParent() != null) {
if (playerImpl.getParentActivity() != null) {
// This means view was added to fragment
final ViewGroup parent = (ViewGroup) getView().getParent();
diff --git a/app/src/main/java/org/schabi/newpipe/player/ServicePlayerActivity.java b/app/src/main/java/org/schabi/newpipe/player/ServicePlayerActivity.java
index fee189295..ad4c603cd 100644
--- a/app/src/main/java/org/schabi/newpipe/player/ServicePlayerActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/player/ServicePlayerActivity.java
@@ -27,9 +27,7 @@ import androidx.recyclerview.widget.RecyclerView;
import com.google.android.exoplayer2.PlaybackParameters;
import com.google.android.exoplayer2.Player;
-import org.schabi.newpipe.MainActivity;
import org.schabi.newpipe.R;
-import org.schabi.newpipe.extractor.StreamingService;
import org.schabi.newpipe.extractor.stream.StreamInfo;
import org.schabi.newpipe.fragments.OnScrollBelowItemsListener;
import org.schabi.newpipe.local.dialog.PlaylistAppendDialog;
@@ -42,9 +40,9 @@ import org.schabi.newpipe.player.playqueue.PlayQueueItem;
import org.schabi.newpipe.player.playqueue.PlayQueueItemBuilder;
import org.schabi.newpipe.player.playqueue.PlayQueueItemHolder;
import org.schabi.newpipe.player.playqueue.PlayQueueItemTouchCallback;
-import org.schabi.newpipe.util.Constants;
import org.schabi.newpipe.util.Localization;
import org.schabi.newpipe.util.NavigationHelper;
+import org.schabi.newpipe.util.PermissionHelper;
import org.schabi.newpipe.util.ThemeHelper;
import java.util.Collections;
@@ -113,9 +111,8 @@ public abstract class ServicePlayerActivity extends AppCompatActivity
public abstract int getPlayerOptionMenuResource();
- public abstract boolean onPlayerOptionSelected(MenuItem item);
-
public abstract void setupMenu(Menu m);
+
////////////////////////////////////////////////////////////////////////////
// Activity Lifecycle
////////////////////////////////////////////////////////////////////////////
@@ -187,12 +184,22 @@ public abstract class ServicePlayerActivity extends AppCompatActivity
return true;
case R.id.action_switch_main:
this.player.setRecovery();
- getApplicationContext().startActivity(
- getSwitchIntent(MainActivity.class, MainPlayer.PlayerType.VIDEO)
- .putExtra(BasePlayer.START_PAUSED, !this.player.isPlaying()));
+ NavigationHelper.playOnMainPlayer(this, player.getPlayQueue(), true);
+ return true;
+ case R.id.action_switch_popup:
+ if (PermissionHelper.isPopupEnabled(this)) {
+ this.player.setRecovery();
+ NavigationHelper.playOnPopupPlayer(this, player.playQueue, true);
+ } else {
+ PermissionHelper.showPopupEnablementToast(this);
+ }
+ return true;
+ case R.id.action_switch_background:
+ this.player.setRecovery();
+ NavigationHelper.playOnBackgroundPlayer(this, player.playQueue, true);
return true;
}
- return onPlayerOptionSelected(item) || super.onOptionsItemSelected(item);
+ return super.onOptionsItemSelected(item);
}
@Override
@@ -201,24 +208,6 @@ public abstract class ServicePlayerActivity extends AppCompatActivity
unbind();
}
- protected Intent getSwitchIntent(final Class clazz, final MainPlayer.PlayerType playerType) {
- return NavigationHelper.getPlayerIntent(getApplicationContext(), clazz,
- this.player.getPlayQueue(), this.player.getRepeatMode(),
- this.player.getPlaybackSpeed(), this.player.getPlaybackPitch(),
- this.player.getPlaybackSkipSilence(),
- null,
- true,
- !this.player.isPlaying(),
- this.player.isMuted())
- .addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)
- .putExtra(Constants.KEY_LINK_TYPE, StreamingService.LinkType.STREAM)
- .putExtra(Constants.KEY_URL, this.player.getVideoUrl())
- .putExtra(Constants.KEY_TITLE, this.player.getVideoTitle())
- .putExtra(Constants.KEY_SERVICE_ID,
- this.player.getCurrentMetadata().getMetadata().getServiceId())
- .putExtra(VideoPlayer.PLAYER_TYPE, playerType);
- }
-
////////////////////////////////////////////////////////////////////////////
// Service Connection
////////////////////////////////////////////////////////////////////////////
@@ -368,8 +357,8 @@ public abstract class ServicePlayerActivity extends AppCompatActivity
Menu.NONE, R.string.play_queue_stream_detail);
detail.setOnMenuItemClickListener(menuItem -> {
// playQueue is null since we don't want any queue change
- NavigationHelper.openVideoDetail(
- this, item.getServiceId(), item.getUrl(), item.getTitle(), null);
+ NavigationHelper.openVideoDetail(this, item.getServiceId(), item.getUrl(),
+ item.getTitle(), null, false);
return true;
});
diff --git a/app/src/main/java/org/schabi/newpipe/player/VideoPlayerImpl.java b/app/src/main/java/org/schabi/newpipe/player/VideoPlayerImpl.java
index 765eb148b..fa016e158 100644
--- a/app/src/main/java/org/schabi/newpipe/player/VideoPlayerImpl.java
+++ b/app/src/main/java/org/schabi/newpipe/player/VideoPlayerImpl.java
@@ -76,9 +76,7 @@ import com.google.android.exoplayer2.ui.SubtitleView;
import com.google.android.material.floatingactionbutton.FloatingActionButton;
import com.nostra13.universalimageloader.core.assist.FailReason;
-import org.schabi.newpipe.MainActivity;
import org.schabi.newpipe.R;
-import org.schabi.newpipe.extractor.StreamingService;
import org.schabi.newpipe.extractor.stream.StreamInfo;
import org.schabi.newpipe.extractor.stream.VideoStream;
import org.schabi.newpipe.fragments.OnScrollBelowItemsListener;
@@ -97,7 +95,6 @@ import org.schabi.newpipe.player.resolver.AudioPlaybackResolver;
import org.schabi.newpipe.player.resolver.MediaSourceTag;
import org.schabi.newpipe.player.resolver.VideoPlaybackResolver;
import org.schabi.newpipe.util.AnimationUtils;
-import org.schabi.newpipe.util.Constants;
import org.schabi.newpipe.util.DeviceUtils;
import org.schabi.newpipe.util.KoreUtil;
import org.schabi.newpipe.util.ListHelper;
@@ -260,7 +257,12 @@ public class VideoPlayerImpl extends VideoPlayer
onQueueClosed();
// Android TV: without it focus will frame the whole player
playPauseButton.requestFocus();
- onPlay();
+
+ if (simpleExoPlayer.getPlayWhenReady()) {
+ onPlay();
+ } else {
+ onPause();
+ }
}
NavigationHelper.sendPlayerStartedEvent(service);
}
@@ -756,40 +758,6 @@ public class VideoPlayerImpl extends VideoPlayer
setupScreenRotationButton();
}
- public void switchFromPopupToMain() {
- if (DEBUG) {
- Log.d(TAG, "switchFromPopupToMain() called");
- }
- if (!popupPlayerSelected() || simpleExoPlayer == null || getCurrentMetadata() == null) {
- return;
- }
-
- setRecovery();
- service.removeViewFromParent();
- final Intent intent = NavigationHelper.getPlayerIntent(
- service,
- MainActivity.class,
- this.getPlayQueue(),
- this.getRepeatMode(),
- this.getPlaybackSpeed(),
- this.getPlaybackPitch(),
- this.getPlaybackSkipSilence(),
- null,
- true,
- !isPlaying(),
- isMuted()
- );
- intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
- intent.putExtra(Constants.KEY_SERVICE_ID,
- getCurrentMetadata().getMetadata().getServiceId());
- intent.putExtra(Constants.KEY_LINK_TYPE, StreamingService.LinkType.STREAM);
- intent.putExtra(Constants.KEY_URL, getVideoUrl());
- intent.putExtra(Constants.KEY_TITLE, getVideoTitle());
- intent.putExtra(VideoDetailFragment.KEY_SWITCHING_PLAYERS, true);
- service.onDestroy();
- context.startActivity(intent);
- }
-
@Override
public void onClick(final View v) {
super.onClick(v);
@@ -817,7 +785,9 @@ public class VideoPlayerImpl extends VideoPlayer
} else if (v.getId() == openInBrowser.getId()) {
onOpenInBrowserClicked();
} else if (v.getId() == fullscreenButton.getId()) {
- switchFromPopupToMain();
+ setRecovery();
+ NavigationHelper.playOnMainPlayer(context, getPlayQueue(), true);
+ return;
} else if (v.getId() == screenRotationButton.getId()) {
// Only if it's not a vertical video or vertical video but in landscape with locked
// orientation a screen orientation can be changed automatically
diff --git a/app/src/main/java/org/schabi/newpipe/player/event/BasePlayerGestureListener.kt b/app/src/main/java/org/schabi/newpipe/player/event/BasePlayerGestureListener.kt
index dcc1bb128..681c1b9af 100644
--- a/app/src/main/java/org/schabi/newpipe/player/event/BasePlayerGestureListener.kt
+++ b/app/src/main/java/org/schabi/newpipe/player/event/BasePlayerGestureListener.kt
@@ -63,7 +63,7 @@ abstract class BasePlayerGestureListener(
private var isMovingInPopup = false
private var isResizing = false
- private val tossFlingVelocity = PlayerHelper.getTossFlingVelocity(service)
+ private val tossFlingVelocity = PlayerHelper.getTossFlingVelocity()
// [popup] initial coordinates and distance between fingers
private var initPointerDistance = -1.0
@@ -104,9 +104,6 @@ abstract class BasePlayerGestureListener(
}
private fun onTouchInPopup(v: View, event: MotionEvent): Boolean {
- if (playerImpl == null) {
- return false
- }
playerImpl.gestureDetector.onTouchEvent(event)
if (event.pointerCount == 2 && !isMovingInPopup && !isResizing) {
if (DEBUG) {
diff --git a/app/src/main/java/org/schabi/newpipe/player/helper/AudioReactor.java b/app/src/main/java/org/schabi/newpipe/player/helper/AudioReactor.java
index a931c46bd..ffe19599d 100644
--- a/app/src/main/java/org/schabi/newpipe/player/helper/AudioReactor.java
+++ b/app/src/main/java/org/schabi/newpipe/player/helper/AudioReactor.java
@@ -164,7 +164,7 @@ public class AudioReactor implements AudioManager.OnAudioFocusChangeListener, An
@Override
public void onAudioSessionId(final EventTime eventTime, final int audioSessionId) {
- if (!PlayerHelper.isUsingDSP(context)) {
+ if (!PlayerHelper.isUsingDSP()) {
return;
}
diff --git a/app/src/main/java/org/schabi/newpipe/player/helper/PlayerHelper.java b/app/src/main/java/org/schabi/newpipe/player/helper/PlayerHelper.java
index 4b52aa27d..cdd07ba1c 100644
--- a/app/src/main/java/org/schabi/newpipe/player/helper/PlayerHelper.java
+++ b/app/src/main/java/org/schabi/newpipe/player/helper/PlayerHelper.java
@@ -295,7 +295,7 @@ public final class PlayerHelper {
return 60000;
}
- public static TrackSelection.Factory getQualitySelector(@NonNull final Context context) {
+ public static TrackSelection.Factory getQualitySelector() {
return new AdaptiveTrackSelection.Factory(
1000,
AdaptiveTrackSelection.DEFAULT_MAX_DURATION_FOR_QUALITY_DECREASE_MS,
@@ -303,11 +303,11 @@ public final class PlayerHelper {
AdaptiveTrackSelection.DEFAULT_BANDWIDTH_FRACTION);
}
- public static boolean isUsingDSP(@NonNull final Context context) {
+ public static boolean isUsingDSP() {
return true;
}
- public static int getTossFlingVelocity(@NonNull final Context context) {
+ public static int getTossFlingVelocity() {
return 2500;
}
diff --git a/app/src/main/java/org/schabi/newpipe/player/helper/PlayerHolder.java b/app/src/main/java/org/schabi/newpipe/player/helper/PlayerHolder.java
index 6d0f5fff7..5764b2b94 100644
--- a/app/src/main/java/org/schabi/newpipe/player/helper/PlayerHolder.java
+++ b/app/src/main/java/org/schabi/newpipe/player/helper/PlayerHolder.java
@@ -49,6 +49,13 @@ public final class PlayerHolder {
return player.getPlayerType();
}
+ public static boolean isPlaying() {
+ if (player == null) {
+ return false;
+ }
+ return player.isPlaying();
+ }
+
public static void setListener(final PlayerServiceExtendedEventListener newListener) {
listener = newListener;
// Force reload data from service
diff --git a/app/src/main/java/org/schabi/newpipe/player/playqueue/PlayQueueItem.java b/app/src/main/java/org/schabi/newpipe/player/playqueue/PlayQueueItem.java
index 74aef07fa..79efc03ae 100644
--- a/app/src/main/java/org/schabi/newpipe/player/playqueue/PlayQueueItem.java
+++ b/app/src/main/java/org/schabi/newpipe/player/playqueue/PlayQueueItem.java
@@ -64,6 +64,20 @@ public class PlayQueueItem implements Serializable {
this.recoveryPosition = RECOVERY_UNSET;
}
+ @Override
+ public boolean equals(final Object o) {
+ if (o instanceof PlayQueueItem) {
+ return url.equals(((PlayQueueItem) o).url);
+ } else {
+ return false;
+ }
+ }
+
+ @Override
+ public int hashCode() {
+ return url.hashCode();
+ }
+
@NonNull
public String getTitle() {
return title;
diff --git a/app/src/main/java/org/schabi/newpipe/util/NavigationHelper.java b/app/src/main/java/org/schabi/newpipe/util/NavigationHelper.java
index a96730552..3c791d44d 100644
--- a/app/src/main/java/org/schabi/newpipe/util/NavigationHelper.java
+++ b/app/src/main/java/org/schabi/newpipe/util/NavigationHelper.java
@@ -37,7 +37,6 @@ import org.schabi.newpipe.extractor.stream.VideoStream;
import org.schabi.newpipe.fragments.MainFragment;
import org.schabi.newpipe.fragments.detail.VideoDetailFragment;
import org.schabi.newpipe.fragments.list.channel.ChannelFragment;
-import org.schabi.newpipe.fragments.list.comments.CommentsFragment;
import org.schabi.newpipe.fragments.list.kiosk.KioskFragment;
import org.schabi.newpipe.fragments.list.playlist.PlaylistFragment;
import org.schabi.newpipe.fragments.list.search.SearchFragment;
@@ -73,7 +72,6 @@ public final class NavigationHelper {
public static Intent getPlayerIntent(@NonNull final Context context,
@NonNull final Class targetClazz,
@Nullable final PlayQueue playQueue,
- @Nullable final String quality,
final boolean resumePlayback) {
final Intent intent = new Intent(context, targetClazz);
@@ -83,9 +81,6 @@ public final class NavigationHelper {
intent.putExtra(VideoPlayer.PLAY_QUEUE_KEY, cacheKey);
}
}
- if (quality != null) {
- intent.putExtra(VideoPlayer.PLAYBACK_QUALITY, quality);
- }
intent.putExtra(VideoPlayer.RESUME_PLAYBACK, resumePlayback);
intent.putExtra(VideoPlayer.PLAYER_TYPE, VideoPlayer.PLAYER_TYPE_VIDEO);
@@ -96,8 +91,10 @@ public final class NavigationHelper {
public static Intent getPlayerIntent(@NonNull final Context context,
@NonNull final Class targetClazz,
@Nullable final PlayQueue playQueue,
- final boolean resumePlayback) {
- return getPlayerIntent(context, targetClazz, playQueue, null, resumePlayback);
+ final boolean resumePlayback,
+ final boolean playWhenReady) {
+ return getPlayerIntent(context, targetClazz, playQueue, resumePlayback)
+ .putExtra(BasePlayer.PLAY_WHEN_READY, playWhenReady);
}
@NonNull
@@ -111,24 +108,6 @@ public final class NavigationHelper {
.putExtra(BasePlayer.SELECT_ON_APPEND, selectOnAppend);
}
- @NonNull
- public static Intent getPlayerIntent(@NonNull final Context context,
- @NonNull final Class targetClazz,
- @Nullable final PlayQueue playQueue,
- final int repeatMode,
- final float playbackSpeed,
- final float playbackPitch,
- final boolean playbackSkipSilence,
- @Nullable final String playbackQuality,
- final boolean resumePlayback,
- final boolean startPaused,
- final boolean isMuted) {
- return getPlayerIntent(context, targetClazz, playQueue, playbackQuality, resumePlayback)
- .putExtra(BasePlayer.REPEAT_MODE, repeatMode)
- .putExtra(BasePlayer.START_PAUSED, startPaused)
- .putExtra(BasePlayer.IS_MUTED, isMuted);
- }
-
public static void playOnMainPlayer(final AppCompatActivity activity,
@NonNull final PlayQueue playQueue) {
final PlayQueueItem item = playQueue.getItem();
@@ -138,10 +117,12 @@ public final class NavigationHelper {
}
public static void playOnMainPlayer(final Context context,
- @NonNull final PlayQueue playQueue) {
+ @NonNull final PlayQueue playQueue,
+ final boolean switchingPlayers) {
final PlayQueueItem item = playQueue.getItem();
assert item != null;
- openVideoDetail(context, item.getServiceId(), item.getUrl(), item.getTitle(), playQueue);
+ openVideoDetail(context,
+ item.getServiceId(), item.getUrl(), item.getTitle(), playQueue, switchingPlayers);
}
public static void playOnPopupPlayer(final Context context,
@@ -370,7 +351,7 @@ public final class NavigationHelper {
autoPlay = PlayerHelper.isAutoplayAllowedByUser(context);
} else if (switchingPlayers) {
// switching player to main player
- autoPlay = true;
+ autoPlay = PlayerHolder.isPlaying(); // keep play/pause state
} else if (playerType == MainPlayer.PlayerType.VIDEO) {
// opening new stream while already playing in main player
autoPlay = PlayerHelper.isAutoplayAllowedByUser(context);
@@ -416,16 +397,6 @@ public final class NavigationHelper {
.commit();
}
- public static void openCommentsFragment(final FragmentManager fragmentManager,
- final int serviceId, final String url,
- @NonNull final String name) {
- fragmentManager.beginTransaction()
- .setCustomAnimations(R.anim.switch_service_in, R.anim.switch_service_out)
- .replace(R.id.fragment_holder, CommentsFragment.getInstance(serviceId, url, name))
- .addToBackStack(null)
- .commit();
- }
-
public static void openPlaylistFragment(final FragmentManager fragmentManager,
final int serviceId, final String url,
@NonNull final String name) {
@@ -506,23 +477,17 @@ public final class NavigationHelper {
context.startActivity(mIntent);
}
- public static void openChannel(final Context context, final int serviceId,
- final String url, @NonNull final String name) {
- final Intent openIntent = getOpenIntent(context, url, serviceId,
- StreamingService.LinkType.CHANNEL);
- openIntent.putExtra(Constants.KEY_TITLE, name);
- context.startActivity(openIntent);
- }
-
public static void openVideoDetail(final Context context,
final int serviceId,
final String url,
@NonNull final String title,
- @Nullable final PlayQueue playQueue) {
+ @Nullable final PlayQueue playQueue,
+ final boolean switchingPlayers) {
final Intent intent = getOpenIntent(context, url, serviceId,
StreamingService.LinkType.STREAM);
intent.putExtra(Constants.KEY_TITLE, title);
+ intent.putExtra(VideoDetailFragment.KEY_SWITCHING_PLAYERS, switchingPlayers);
if (playQueue != null) {
final String cacheKey = SerializedCache.getInstance().put(playQueue, PlayQueue.class);
From 00a178f7d3b34d57e23dc4047c150c22d2e84fa3 Mon Sep 17 00:00:00 2001
From: Stypox
Date: Sun, 1 Nov 2020 21:25:31 +0100
Subject: [PATCH 4/7] Fix tapping on video thumbnail does nothing
---
.../schabi/newpipe/fragments/detail/VideoDetailFragment.java | 3 +++
1 file changed, 3 insertions(+)
diff --git a/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java b/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java
index 1324d6832..92032986d 100644
--- a/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java
+++ b/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java
@@ -289,6 +289,7 @@ public final class VideoDetailFragment
|| (currentInfo != null
&& isAutoplayEnabled()
&& player.getParentActivity() == null)) {
+ autoPlayEnabled = true; // forcefully start playing
openVideoPlayer();
}
}
@@ -521,6 +522,7 @@ public final class VideoDetailFragment
}
break;
case R.id.detail_thumbnail_root_layout:
+ autoPlayEnabled = true; // forcefully start playing
openVideoPlayer();
break;
case R.id.detail_title_root_layout:
@@ -537,6 +539,7 @@ public final class VideoDetailFragment
player.hideControls(0, 0);
showSystemUi();
} else {
+ autoPlayEnabled = true; // forcefully start playing
openVideoPlayer();
}
From 5a87cfc25df880a579d943299a20d00e6fbdc7e3 Mon Sep 17 00:00:00 2001
From: Stypox
Date: Sun, 1 Nov 2020 21:45:39 +0100
Subject: [PATCH 5/7] Open mini player if player running on app open
---
.../java/org/schabi/newpipe/MainActivity.java | 60 ++++++++++---------
.../newpipe/player/helper/PlayerHolder.java | 4 ++
2 files changed, 37 insertions(+), 27 deletions(-)
diff --git a/app/src/main/java/org/schabi/newpipe/MainActivity.java b/app/src/main/java/org/schabi/newpipe/MainActivity.java
index 1d911c944..84235d4fb 100644
--- a/app/src/main/java/org/schabi/newpipe/MainActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/MainActivity.java
@@ -69,6 +69,7 @@ import org.schabi.newpipe.fragments.detail.VideoDetailFragment;
import org.schabi.newpipe.fragments.list.search.SearchFragment;
import org.schabi.newpipe.player.VideoPlayer;
import org.schabi.newpipe.player.event.OnKeyDownListener;
+import org.schabi.newpipe.player.helper.PlayerHolder;
import org.schabi.newpipe.player.playqueue.PlayQueue;
import org.schabi.newpipe.report.ErrorActivity;
import org.schabi.newpipe.util.Constants;
@@ -152,7 +153,7 @@ public class MainActivity extends AppCompatActivity {
if (DeviceUtils.isTv(this)) {
FocusOverlayView.setupFocusObserver(this);
}
- setupBroadcastReceiver();
+ openMiniPlayerUponPlayerStarted();
}
private void setupDrawer() throws Exception {
@@ -809,34 +810,39 @@ public class MainActivity extends AppCompatActivity {
}
}
- private void setupBroadcastReceiver() {
- broadcastReceiver = new BroadcastReceiver() {
- @Override
- public void onReceive(final Context context, final Intent intent) {
- if (intent.getAction().equals(VideoDetailFragment.ACTION_PLAYER_STARTED)) {
- final Fragment fragmentPlayer = getSupportFragmentManager()
- .findFragmentById(R.id.fragment_player_holder);
- if (fragmentPlayer == null) {
- /*
- * We still don't have a fragment attached to the activity.
- * It can happen when a user started popup or background players
- * without opening a stream inside the fragment.
- * Adding it in a collapsed state (only mini player will be visible)
- * */
- NavigationHelper.showMiniPlayer(getSupportFragmentManager());
+ private void openMiniPlayerIfMissing() {
+ final Fragment fragmentPlayer = getSupportFragmentManager()
+ .findFragmentById(R.id.fragment_player_holder);
+ if (fragmentPlayer == null) {
+ // We still don't have a fragment attached to the activity. It can happen when a user
+ // started popup or background players without opening a stream inside the fragment.
+ // Adding it in a collapsed state (only mini player will be visible).
+ NavigationHelper.showMiniPlayer(getSupportFragmentManager());
+ }
+ }
+
+ private void openMiniPlayerUponPlayerStarted() {
+ if (PlayerHolder.isPlayerOpen()) {
+ // no need for a broadcast receiver if the player is already open
+ openMiniPlayerIfMissing();
+ } else {
+ // listen for player intents being sent around
+ broadcastReceiver = new BroadcastReceiver() {
+ @Override
+ public void onReceive(final Context context, final Intent intent) {
+ if (intent.getAction().equals(VideoDetailFragment.ACTION_PLAYER_STARTED)) {
+ openMiniPlayerIfMissing();
+ // At this point the player is added 100%, we can unregister. Other actions
+ // are useless since the fragment will not be removed after that.
+ unregisterReceiver(broadcastReceiver);
+ broadcastReceiver = null;
}
- /*
- * At this point the player is added 100%, we can unregister.
- * Other actions are useless since the fragment will not be removed after that
- * */
- unregisterReceiver(broadcastReceiver);
- broadcastReceiver = null;
}
- }
- };
- final IntentFilter intentFilter = new IntentFilter();
- intentFilter.addAction(VideoDetailFragment.ACTION_PLAYER_STARTED);
- registerReceiver(broadcastReceiver, intentFilter);
+ };
+ final IntentFilter intentFilter = new IntentFilter();
+ intentFilter.addAction(VideoDetailFragment.ACTION_PLAYER_STARTED);
+ registerReceiver(broadcastReceiver, intentFilter);
+ }
}
private boolean bottomSheetHiddenOrCollapsed() {
diff --git a/app/src/main/java/org/schabi/newpipe/player/helper/PlayerHolder.java b/app/src/main/java/org/schabi/newpipe/player/helper/PlayerHolder.java
index 5764b2b94..854e3eb2b 100644
--- a/app/src/main/java/org/schabi/newpipe/player/helper/PlayerHolder.java
+++ b/app/src/main/java/org/schabi/newpipe/player/helper/PlayerHolder.java
@@ -56,6 +56,10 @@ public final class PlayerHolder {
return player.isPlaying();
}
+ public static boolean isPlayerOpen() {
+ return player != null;
+ }
+
public static void setListener(final PlayerServiceExtendedEventListener newListener) {
listener = newListener;
// Force reload data from service
From 1b47a1a994e009a298f12ad6570d2565cb49b7dd Mon Sep 17 00:00:00 2001
From: Stypox
Date: Mon, 2 Nov 2020 18:06:14 +0100
Subject: [PATCH 6/7] Fix switching to main player when MainActivity is closed
---
.../java/org/schabi/newpipe/MainActivity.java | 15 ++++++++++++---
.../fragments/detail/VideoDetailFragment.java | 4 +++-
.../org/schabi/newpipe/player/MainPlayer.java | 2 ++
.../org/schabi/newpipe/util/NavigationHelper.java | 1 +
4 files changed, 18 insertions(+), 4 deletions(-)
diff --git a/app/src/main/java/org/schabi/newpipe/MainActivity.java b/app/src/main/java/org/schabi/newpipe/MainActivity.java
index 84235d4fb..9bcbe4ff1 100644
--- a/app/src/main/java/org/schabi/newpipe/MainActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/MainActivity.java
@@ -88,6 +88,7 @@ import org.schabi.newpipe.views.FocusOverlayView;
import java.util.ArrayList;
import java.util.List;
+import java.util.Objects;
import static org.schabi.newpipe.util.Localization.assureCorrectAppLanguage;
@@ -822,15 +823,23 @@ public class MainActivity extends AppCompatActivity {
}
private void openMiniPlayerUponPlayerStarted() {
+ if (getIntent().getSerializableExtra(Constants.KEY_LINK_TYPE)
+ == StreamingService.LinkType.STREAM) {
+ // handleIntent() already takes care of opening video detail fragment
+ // due to an intent containing a STREAM link
+ return;
+ }
+
if (PlayerHolder.isPlayerOpen()) {
- // no need for a broadcast receiver if the player is already open
+ // if the player is already open, no need for a broadcast receiver
openMiniPlayerIfMissing();
} else {
- // listen for player intents being sent around
+ // listen for player start intent being sent around
broadcastReceiver = new BroadcastReceiver() {
@Override
public void onReceive(final Context context, final Intent intent) {
- if (intent.getAction().equals(VideoDetailFragment.ACTION_PLAYER_STARTED)) {
+ if (Objects.equals(intent.getAction(),
+ VideoDetailFragment.ACTION_PLAYER_STARTED)) {
openMiniPlayerIfMissing();
// At this point the player is added 100%, we can unregister. Other actions
// are useless since the fragment will not be removed after that.
diff --git a/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java b/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java
index 92032986d..3296f5bf8 100644
--- a/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java
+++ b/app/src/main/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java
@@ -1111,7 +1111,9 @@ public final class VideoDetailFragment
// Video view can have elements visible from popup,
// We hide it here but once it ready the view will be shown in handleIntent()
- playerService.getView().setVisibility(View.GONE);
+ if (playerService.getView() != null) {
+ playerService.getView().setVisibility(View.GONE);
+ }
addVideoPlayerView();
final Intent playerIntent = NavigationHelper
diff --git a/app/src/main/java/org/schabi/newpipe/player/MainPlayer.java b/app/src/main/java/org/schabi/newpipe/player/MainPlayer.java
index 07ca7b339..63f6a400e 100644
--- a/app/src/main/java/org/schabi/newpipe/player/MainPlayer.java
+++ b/app/src/main/java/org/schabi/newpipe/player/MainPlayer.java
@@ -30,6 +30,7 @@ import android.view.View;
import android.view.ViewGroup;
import android.view.WindowManager;
+import androidx.annotation.Nullable;
import androidx.core.content.ContextCompat;
import org.schabi.newpipe.R;
@@ -231,6 +232,7 @@ public final class MainPlayer extends Service {
return metrics.heightPixels < metrics.widthPixels;
}
+ @Nullable
public View getView() {
if (playerImpl == null) {
return null;
diff --git a/app/src/main/java/org/schabi/newpipe/util/NavigationHelper.java b/app/src/main/java/org/schabi/newpipe/util/NavigationHelper.java
index 3c791d44d..b45a1e7b9 100644
--- a/app/src/main/java/org/schabi/newpipe/util/NavigationHelper.java
+++ b/app/src/main/java/org/schabi/newpipe/util/NavigationHelper.java
@@ -486,6 +486,7 @@ public final class NavigationHelper {
final Intent intent = getOpenIntent(context, url, serviceId,
StreamingService.LinkType.STREAM);
+ intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intent.putExtra(Constants.KEY_TITLE, title);
intent.putExtra(VideoDetailFragment.KEY_SWITCHING_PLAYERS, switchingPlayers);
From 617ee0afc0093bc0f075bd4a11b5762c7df19b79 Mon Sep 17 00:00:00 2001
From: Stypox
Date: Wed, 4 Nov 2020 16:10:25 +0100
Subject: [PATCH 7/7] Fix brightness and volume scroll swapped
---
.../schabi/newpipe/player/event/PlayerGestureListener.java | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/app/src/main/java/org/schabi/newpipe/player/event/PlayerGestureListener.java b/app/src/main/java/org/schabi/newpipe/player/event/PlayerGestureListener.java
index a23d5d3ff..fdea20775 100644
--- a/app/src/main/java/org/schabi/newpipe/player/event/PlayerGestureListener.java
+++ b/app/src/main/java/org/schabi/newpipe/player/event/PlayerGestureListener.java
@@ -111,10 +111,10 @@ public class PlayerGestureListener
}
if (playerType == MainPlayer.PlayerType.VIDEO) {
if (portion == DisplayPortion.LEFT_HALF) {
- onScrollMainVolume(distanceX, distanceY);
+ onScrollMainBrightness(distanceX, distanceY);
} else /* DisplayPortion.RIGHT_HALF */ {
- onScrollMainBrightness(distanceX, distanceY);
+ onScrollMainVolume(distanceX, distanceY);
}
} else /* MainPlayer.PlayerType.POPUP */ {