2017-09-03 08:04:18 +02:00
|
|
|
/*
|
|
|
|
* Copyright 2017 Mauricio Colli <mauriciocolli@outlook.com>
|
|
|
|
* MainVideoPlayer.java is part of NewPipe
|
|
|
|
*
|
|
|
|
* License: GPL-3.0+
|
|
|
|
* This program is free software: you can redistribute it and/or modify
|
|
|
|
* it under the terms of the GNU General Public License as published by
|
|
|
|
* the Free Software Foundation, either version 3 of the License, or
|
|
|
|
* (at your option) any later version.
|
|
|
|
*
|
|
|
|
* This program is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
* GNU General Public License for more details.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU General Public License
|
|
|
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
|
|
*/
|
|
|
|
|
2016-02-22 20:28:37 +01:00
|
|
|
package org.schabi.newpipe.player;
|
|
|
|
|
2017-10-26 22:42:50 +02:00
|
|
|
import android.content.Context;
|
2016-02-22 20:28:37 +01:00
|
|
|
import android.content.Intent;
|
2017-12-05 12:51:23 +01:00
|
|
|
import android.content.SharedPreferences;
|
2017-03-27 15:12:22 +02:00
|
|
|
import android.content.pm.ActivityInfo;
|
2017-11-09 11:29:02 +01:00
|
|
|
import android.content.res.Configuration;
|
2017-03-27 06:08:16 +02:00
|
|
|
import android.graphics.Color;
|
2018-05-05 10:26:35 +02:00
|
|
|
import android.graphics.drawable.ColorDrawable;
|
2017-03-27 06:08:16 +02:00
|
|
|
import android.media.AudioManager;
|
|
|
|
import android.os.Build;
|
2016-02-22 20:28:37 +01:00
|
|
|
import android.os.Bundle;
|
2017-12-05 12:51:23 +01:00
|
|
|
import android.preference.PreferenceManager;
|
|
|
|
import android.provider.Settings;
|
2018-04-08 01:40:38 +02:00
|
|
|
import android.support.annotation.ColorInt;
|
2017-10-10 02:25:45 +02:00
|
|
|
import android.support.annotation.NonNull;
|
2017-03-27 06:08:16 +02:00
|
|
|
import android.support.annotation.Nullable;
|
2018-04-08 01:40:38 +02:00
|
|
|
import android.support.v4.app.ActivityCompat;
|
2018-03-21 08:11:54 +01:00
|
|
|
import android.support.v7.app.AppCompatActivity;
|
2018-08-15 11:02:37 +02:00
|
|
|
import android.support.v7.content.res.AppCompatResources;
|
2017-10-13 05:47:12 +02:00
|
|
|
import android.support.v7.widget.RecyclerView;
|
|
|
|
import android.support.v7.widget.helper.ItemTouchHelper;
|
2018-02-07 22:11:19 +01:00
|
|
|
import android.util.DisplayMetrics;
|
2016-02-22 20:28:37 +01:00
|
|
|
import android.util.Log;
|
2018-02-07 22:11:19 +01:00
|
|
|
import android.util.TypedValue;
|
2017-03-27 06:08:16 +02:00
|
|
|
import android.view.GestureDetector;
|
|
|
|
import android.view.MotionEvent;
|
2016-02-22 20:28:37 +01:00
|
|
|
import android.view.View;
|
2017-03-09 05:44:00 +01:00
|
|
|
import android.view.WindowManager;
|
|
|
|
import android.widget.ImageButton;
|
2018-08-15 11:02:37 +02:00
|
|
|
import android.widget.ImageView;
|
2017-03-27 06:08:16 +02:00
|
|
|
import android.widget.PopupMenu;
|
2018-08-15 11:02:37 +02:00
|
|
|
import android.widget.ProgressBar;
|
2017-10-13 05:47:12 +02:00
|
|
|
import android.widget.RelativeLayout;
|
2017-03-09 05:44:00 +01:00
|
|
|
import android.widget.SeekBar;
|
2017-03-27 06:08:16 +02:00
|
|
|
import android.widget.TextView;
|
|
|
|
import android.widget.Toast;
|
2016-02-22 20:28:37 +01:00
|
|
|
|
2017-09-05 00:38:58 +02:00
|
|
|
import com.google.android.exoplayer2.Player;
|
2018-04-08 22:58:18 +02:00
|
|
|
import com.google.android.exoplayer2.text.CaptionStyleCompat;
|
2018-02-07 22:11:19 +01:00
|
|
|
import com.google.android.exoplayer2.ui.AspectRatioFrameLayout;
|
2018-02-09 22:26:03 +01:00
|
|
|
import com.google.android.exoplayer2.ui.SubtitleView;
|
2017-09-05 00:38:58 +02:00
|
|
|
|
2017-03-09 05:44:00 +01:00
|
|
|
import org.schabi.newpipe.R;
|
2017-10-23 04:21:19 +02:00
|
|
|
import org.schabi.newpipe.extractor.stream.VideoStream;
|
2017-11-04 04:32:10 +01:00
|
|
|
import org.schabi.newpipe.fragments.OnScrollBelowItemsListener;
|
2018-03-21 08:11:54 +01:00
|
|
|
import org.schabi.newpipe.player.helper.PlaybackParameterDialog;
|
2017-10-28 19:08:01 +02:00
|
|
|
import org.schabi.newpipe.player.helper.PlayerHelper;
|
2018-04-21 23:10:01 +02:00
|
|
|
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;
|
2018-05-10 22:28:31 +02:00
|
|
|
import org.schabi.newpipe.player.resolver.MediaSourceTag;
|
|
|
|
import org.schabi.newpipe.player.resolver.VideoPlaybackResolver;
|
2017-05-08 15:33:26 +02:00
|
|
|
import org.schabi.newpipe.util.AnimationUtils;
|
2017-10-23 04:21:19 +02:00
|
|
|
import org.schabi.newpipe.util.ListHelper;
|
2017-04-12 08:07:15 +02:00
|
|
|
import org.schabi.newpipe.util.NavigationHelper;
|
2017-03-27 06:08:16 +02:00
|
|
|
import org.schabi.newpipe.util.PermissionHelper;
|
2018-03-06 04:03:49 +01:00
|
|
|
import org.schabi.newpipe.util.StateSaver;
|
2017-03-27 06:08:16 +02:00
|
|
|
import org.schabi.newpipe.util.ThemeHelper;
|
|
|
|
|
2017-10-23 04:21:19 +02:00
|
|
|
import java.util.List;
|
2018-03-06 04:03:49 +01:00
|
|
|
import java.util.Queue;
|
|
|
|
import java.util.UUID;
|
2017-10-23 04:21:19 +02:00
|
|
|
|
2018-03-04 05:58:53 +01:00
|
|
|
import static org.schabi.newpipe.player.BasePlayer.STATE_PLAYING;
|
|
|
|
import static org.schabi.newpipe.player.VideoPlayer.DEFAULT_CONTROLS_DURATION;
|
|
|
|
import static org.schabi.newpipe.player.VideoPlayer.DEFAULT_CONTROLS_HIDE_TIME;
|
2018-08-15 11:02:37 +02:00
|
|
|
import static org.schabi.newpipe.util.AnimationUtils.Type.SCALE_AND_ALPHA;
|
2018-03-14 04:25:22 +01:00
|
|
|
import static org.schabi.newpipe.util.AnimationUtils.Type.SLIDE_AND_ALPHA;
|
|
|
|
import static org.schabi.newpipe.util.AnimationUtils.animateRotation;
|
2017-05-08 15:33:26 +02:00
|
|
|
import static org.schabi.newpipe.util.AnimationUtils.animateView;
|
2018-03-06 04:03:49 +01:00
|
|
|
import static org.schabi.newpipe.util.StateSaver.KEY_SAVED_STATE;
|
2017-05-08 15:33:26 +02:00
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
/**
|
2017-04-17 06:19:53 +02:00
|
|
|
* Activity Player implementing VideoPlayer
|
2017-03-27 06:08:16 +02:00
|
|
|
*
|
|
|
|
* @author mauriciocolli
|
|
|
|
*/
|
2018-03-21 08:11:54 +01:00
|
|
|
public final class MainVideoPlayer extends AppCompatActivity
|
|
|
|
implements StateSaver.WriteRead, PlaybackParameterDialog.Callback {
|
2017-04-17 06:19:53 +02:00
|
|
|
private static final String TAG = ".MainVideoPlayer";
|
|
|
|
private static final boolean DEBUG = BasePlayer.DEBUG;
|
2017-03-27 06:08:16 +02:00
|
|
|
|
|
|
|
private GestureDetector gestureDetector;
|
|
|
|
|
2017-04-17 06:19:53 +02:00
|
|
|
private VideoPlayerImpl playerImpl;
|
2016-02-22 20:28:37 +01:00
|
|
|
|
2017-12-05 12:51:23 +01:00
|
|
|
private SharedPreferences defaultPreferences;
|
|
|
|
|
2018-04-12 05:22:54 +02:00
|
|
|
@Nullable private PlayerState playerState;
|
|
|
|
private boolean isInMultiWindow;
|
2018-06-06 08:37:20 +02:00
|
|
|
private boolean isBackPressed;
|
2018-03-06 04:03:49 +01:00
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
/*//////////////////////////////////////////////////////////////////////////
|
|
|
|
// Activity LifeCycle
|
|
|
|
//////////////////////////////////////////////////////////////////////////*/
|
2016-02-22 20:28:37 +01:00
|
|
|
|
2017-03-09 05:44:00 +01:00
|
|
|
@Override
|
2017-03-27 06:08:16 +02:00
|
|
|
protected void onCreate(@Nullable Bundle savedInstanceState) {
|
2017-03-09 05:44:00 +01:00
|
|
|
super.onCreate(savedInstanceState);
|
2017-03-27 06:08:16 +02:00
|
|
|
if (DEBUG) Log.d(TAG, "onCreate() called with: savedInstanceState = [" + savedInstanceState + "]");
|
2017-12-05 12:51:23 +01:00
|
|
|
defaultPreferences = PreferenceManager.getDefaultSharedPreferences(this);
|
2017-04-26 21:32:20 +02:00
|
|
|
ThemeHelper.setTheme(this);
|
2018-05-05 10:26:35 +02:00
|
|
|
getWindow().setBackgroundDrawable(new ColorDrawable(Color.BLACK));
|
2017-03-27 06:08:16 +02:00
|
|
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) getWindow().setStatusBarColor(Color.BLACK);
|
|
|
|
setVolumeControlStream(AudioManager.STREAM_MUSIC);
|
|
|
|
|
2018-06-01 22:36:09 +02:00
|
|
|
WindowManager.LayoutParams lp = getWindow().getAttributes();
|
|
|
|
lp.screenBrightness = PlayerHelper.getScreenBrightness(getApplicationContext());
|
|
|
|
getWindow().setAttributes(lp);
|
|
|
|
|
2018-03-14 04:25:22 +01:00
|
|
|
hideSystemUi();
|
2018-03-06 04:03:49 +01:00
|
|
|
setContentView(R.layout.activity_main_player);
|
2018-05-17 03:18:32 +02:00
|
|
|
playerImpl = new VideoPlayerImpl(this);
|
2018-03-06 04:03:49 +01:00
|
|
|
playerImpl.setup(findViewById(android.R.id.content));
|
|
|
|
|
|
|
|
if (savedInstanceState != null && savedInstanceState.get(KEY_SAVED_STATE) != null) {
|
|
|
|
return; // We have saved states, stop here to restore it
|
2018-01-04 07:53:31 +01:00
|
|
|
}
|
|
|
|
|
2018-03-06 04:03:49 +01:00
|
|
|
final Intent intent = getIntent();
|
|
|
|
if (intent != null) {
|
|
|
|
playerImpl.handleIntent(intent);
|
|
|
|
} else {
|
2017-03-27 06:08:16 +02:00
|
|
|
Toast.makeText(this, R.string.general_error, Toast.LENGTH_SHORT).show();
|
|
|
|
finish();
|
|
|
|
}
|
2018-01-04 07:53:31 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
2018-03-06 04:03:49 +01:00
|
|
|
protected void onRestoreInstanceState(@NonNull Bundle bundle) {
|
2018-04-12 05:22:54 +02:00
|
|
|
if (DEBUG) Log.d(TAG, "onRestoreInstanceState() called");
|
2018-03-06 04:03:49 +01:00
|
|
|
super.onRestoreInstanceState(bundle);
|
2018-04-12 05:22:54 +02:00
|
|
|
StateSaver.tryToRestore(bundle, this);
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
2017-03-27 06:08:16 +02:00
|
|
|
protected void onNewIntent(Intent intent) {
|
|
|
|
if (DEBUG) Log.d(TAG, "onNewIntent() called with: intent = [" + intent + "]");
|
|
|
|
super.onNewIntent(intent);
|
2018-06-26 19:21:43 +02:00
|
|
|
if (intent != null) {
|
|
|
|
playerState = null;
|
|
|
|
playerImpl.handleIntent(intent);
|
|
|
|
}
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
|
|
|
|
2018-03-06 04:03:49 +01:00
|
|
|
@Override
|
|
|
|
protected void onResume() {
|
|
|
|
if (DEBUG) Log.d(TAG, "onResume() called");
|
2018-04-12 05:22:54 +02:00
|
|
|
super.onResume();
|
2018-03-06 04:03:49 +01:00
|
|
|
|
2018-04-12 05:22:54 +02:00
|
|
|
if (globalScreenOrientationLocked()) {
|
|
|
|
boolean lastOrientationWasLandscape = defaultPreferences.getBoolean(
|
|
|
|
getString(R.string.last_orientation_landscape_key), false);
|
2018-03-06 04:03:49 +01:00
|
|
|
setLandscape(lastOrientationWasLandscape);
|
|
|
|
}
|
|
|
|
|
2018-09-22 11:32:13 +02:00
|
|
|
final int lastResizeMode = defaultPreferences.getInt(
|
|
|
|
getString(R.string.last_resize_mode), AspectRatioFrameLayout.RESIZE_MODE_FIT);
|
|
|
|
playerImpl.setResizeMode(lastResizeMode);
|
|
|
|
|
2018-04-12 05:22:54 +02:00
|
|
|
// Upon going in or out of multiwindow mode, isInMultiWindow will always be false,
|
|
|
|
// since the first onResume needs to restore the player.
|
|
|
|
// Subsequent onResume calls while multiwindow mode remains the same and the player is
|
|
|
|
// prepared should be ignored.
|
|
|
|
if (isInMultiWindow) return;
|
|
|
|
isInMultiWindow = isInMultiWindow();
|
|
|
|
|
|
|
|
if (playerState != null) {
|
|
|
|
playerImpl.setPlaybackQuality(playerState.getPlaybackQuality());
|
|
|
|
playerImpl.initPlayback(playerState.getPlayQueue(), playerState.getRepeatMode(),
|
|
|
|
playerState.getPlaybackSpeed(), playerState.getPlaybackPitch(),
|
2018-05-08 20:24:42 +02:00
|
|
|
playerState.isPlaybackSkipSilence(), playerState.wasPlaying());
|
2018-04-12 05:22:54 +02:00
|
|
|
}
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
|
|
|
|
2018-03-06 04:03:49 +01:00
|
|
|
@Override
|
|
|
|
public void onConfigurationChanged(Configuration newConfig) {
|
|
|
|
super.onConfigurationChanged(newConfig);
|
|
|
|
|
|
|
|
if (playerImpl.isSomePopupMenuVisible()) {
|
|
|
|
playerImpl.getQualityPopupMenu().dismiss();
|
|
|
|
playerImpl.getPlaybackSpeedPopupMenu().dismiss();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2018-06-06 08:37:20 +02:00
|
|
|
@Override
|
|
|
|
public void onBackPressed() {
|
|
|
|
super.onBackPressed();
|
|
|
|
isBackPressed = true;
|
|
|
|
}
|
|
|
|
|
2016-02-22 20:28:37 +01:00
|
|
|
@Override
|
2018-03-06 04:03:49 +01:00
|
|
|
protected void onSaveInstanceState(Bundle outState) {
|
2018-04-12 05:22:54 +02:00
|
|
|
if (DEBUG) Log.d(TAG, "onSaveInstanceState() called");
|
2018-03-06 04:03:49 +01:00
|
|
|
super.onSaveInstanceState(outState);
|
|
|
|
if (playerImpl == null) return;
|
2018-03-05 05:16:38 +01:00
|
|
|
|
2018-03-06 04:03:49 +01:00
|
|
|
playerImpl.setRecovery();
|
2018-10-27 09:57:11 +02:00
|
|
|
if(!playerImpl.gotDestroyed()) {
|
|
|
|
playerState = createPlayerState();
|
|
|
|
}
|
2018-04-12 05:22:54 +02:00
|
|
|
StateSaver.tryToSave(isChangingConfigurations(), null, outState, this);
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
2018-04-12 05:22:54 +02:00
|
|
|
protected void onStop() {
|
|
|
|
if (DEBUG) Log.d(TAG, "onStop() called");
|
|
|
|
super.onStop();
|
2018-06-01 22:36:09 +02:00
|
|
|
PlayerHelper.setScreenBrightness(getApplicationContext(),
|
|
|
|
getWindow().getAttributes().screenBrightness);
|
2018-06-03 22:20:20 +02:00
|
|
|
|
2018-06-06 08:37:20 +02:00
|
|
|
if (playerImpl == null) return;
|
2018-06-26 19:19:16 +02:00
|
|
|
if (!isBackPressed) {
|
2018-06-06 08:37:20 +02:00
|
|
|
playerImpl.minimize();
|
|
|
|
}
|
2018-10-27 09:57:11 +02:00
|
|
|
playerState = createPlayerState();
|
2018-06-26 19:19:16 +02:00
|
|
|
playerImpl.destroy();
|
2018-06-03 22:20:20 +02:00
|
|
|
|
2018-06-06 08:37:20 +02:00
|
|
|
isInMultiWindow = false;
|
|
|
|
isBackPressed = false;
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
|
|
|
|
2018-03-06 04:03:49 +01:00
|
|
|
/*//////////////////////////////////////////////////////////////////////////
|
|
|
|
// State Saving
|
|
|
|
//////////////////////////////////////////////////////////////////////////*/
|
|
|
|
|
2018-10-27 09:57:11 +02:00
|
|
|
private PlayerState createPlayerState() {
|
|
|
|
return new PlayerState(playerImpl.getPlayQueue(), playerImpl.getRepeatMode(),
|
|
|
|
playerImpl.getPlaybackSpeed(), playerImpl.getPlaybackPitch(),
|
|
|
|
playerImpl.getPlaybackQuality(), playerImpl.getPlaybackSkipSilence(),
|
|
|
|
playerImpl.isPlaying());
|
|
|
|
}
|
|
|
|
|
2017-11-09 11:29:02 +01:00
|
|
|
@Override
|
2018-03-06 04:03:49 +01:00
|
|
|
public String generateSuffix() {
|
|
|
|
return "." + UUID.randomUUID().toString() + ".player";
|
|
|
|
}
|
2017-11-09 11:29:02 +01:00
|
|
|
|
2018-03-06 04:03:49 +01:00
|
|
|
@Override
|
|
|
|
public void writeTo(Queue<Object> objectsToSave) {
|
|
|
|
if (objectsToSave == null) return;
|
2018-04-12 05:22:54 +02:00
|
|
|
objectsToSave.add(playerState);
|
2018-03-06 04:03:49 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
@SuppressWarnings("unchecked")
|
2018-04-12 05:22:54 +02:00
|
|
|
public void readFrom(@NonNull Queue<Object> savedObjects) {
|
|
|
|
playerState = (PlayerState) savedObjects.poll();
|
2017-11-09 11:29:02 +01:00
|
|
|
}
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
/*//////////////////////////////////////////////////////////////////////////
|
2018-03-06 04:03:49 +01:00
|
|
|
// View
|
2017-03-27 06:08:16 +02:00
|
|
|
//////////////////////////////////////////////////////////////////////////*/
|
|
|
|
|
2017-03-09 05:44:00 +01:00
|
|
|
private void showSystemUi() {
|
2017-03-09 08:42:40 +01:00
|
|
|
if (DEBUG) Log.d(TAG, "showSystemUi() called");
|
2017-10-13 05:47:12 +02:00
|
|
|
if (playerImpl != null && playerImpl.queueVisible) return;
|
2018-03-04 05:58:53 +01:00
|
|
|
|
|
|
|
final int visibility;
|
2017-03-27 06:08:16 +02:00
|
|
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
|
2018-03-04 05:58:53 +01:00
|
|
|
visibility = View.SYSTEM_UI_FLAG_LAYOUT_STABLE
|
|
|
|
| View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
|
|
|
|
| View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION;
|
|
|
|
} else {
|
|
|
|
visibility = View.STATUS_BAR_VISIBLE;
|
|
|
|
}
|
2018-04-08 01:40:38 +02:00
|
|
|
|
|
|
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
|
|
|
|
@ColorInt final int systenUiColor =
|
|
|
|
ActivityCompat.getColor(getApplicationContext(), R.color.video_overlay_color);
|
|
|
|
getWindow().setStatusBarColor(systenUiColor);
|
|
|
|
getWindow().setNavigationBarColor(systenUiColor);
|
|
|
|
}
|
|
|
|
|
2018-03-04 05:58:53 +01:00
|
|
|
getWindow().getDecorView().setSystemUiVisibility(visibility);
|
2017-03-09 05:44:00 +01:00
|
|
|
getWindow().clearFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
|
|
|
|
2017-03-09 05:44:00 +01:00
|
|
|
private void hideSystemUi() {
|
2017-03-09 08:42:40 +01:00
|
|
|
if (DEBUG) Log.d(TAG, "hideSystemUi() called");
|
2018-03-04 05:58:53 +01:00
|
|
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
|
2017-03-27 06:08:16 +02:00
|
|
|
int visibility = View.SYSTEM_UI_FLAG_LAYOUT_STABLE
|
2018-03-04 05:58:53 +01:00
|
|
|
| View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
|
2017-03-27 06:08:16 +02:00
|
|
|
| View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
|
2018-03-04 05:58:53 +01:00
|
|
|
| View.SYSTEM_UI_FLAG_FULLSCREEN
|
|
|
|
| View.SYSTEM_UI_FLAG_HIDE_NAVIGATION;
|
|
|
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
|
|
|
|
visibility |= View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY;
|
|
|
|
}
|
2017-03-27 06:08:16 +02:00
|
|
|
getWindow().getDecorView().setSystemUiVisibility(visibility);
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
2018-03-04 05:58:53 +01:00
|
|
|
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
|
|
|
|
WindowManager.LayoutParams.FLAG_FULLSCREEN);
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
|
|
|
|
2017-03-27 15:12:22 +02:00
|
|
|
private void toggleOrientation() {
|
2018-03-06 04:03:49 +01:00
|
|
|
setLandscape(!isLandscape());
|
2017-12-05 12:51:23 +01:00
|
|
|
defaultPreferences.edit()
|
2018-03-06 04:03:49 +01:00
|
|
|
.putBoolean(getString(R.string.last_orientation_landscape_key), !isLandscape())
|
2017-12-05 12:51:23 +01:00
|
|
|
.apply();
|
|
|
|
}
|
|
|
|
|
2018-03-06 04:03:49 +01:00
|
|
|
private boolean isLandscape() {
|
2017-12-05 12:51:23 +01:00
|
|
|
return getResources().getDisplayMetrics().heightPixels < getResources().getDisplayMetrics().widthPixels;
|
|
|
|
}
|
|
|
|
|
2018-03-06 04:03:49 +01:00
|
|
|
private void setLandscape(boolean v) {
|
2017-12-05 12:51:23 +01:00
|
|
|
setRequestedOrientation(v
|
2017-03-27 15:12:22 +02:00
|
|
|
? ActivityInfo.SCREEN_ORIENTATION_SENSOR_LANDSCAPE
|
|
|
|
: ActivityInfo.SCREEN_ORIENTATION_SENSOR_PORTRAIT);
|
|
|
|
}
|
|
|
|
|
2017-12-05 12:51:23 +01:00
|
|
|
private boolean globalScreenOrientationLocked() {
|
|
|
|
// 1: Screen orientation changes using acelerometer
|
|
|
|
// 0: Screen orientatino is locked
|
|
|
|
return !(android.provider.Settings.System.getInt(getContentResolver(), Settings.System.ACCELEROMETER_ROTATION, 0) == 1);
|
|
|
|
}
|
|
|
|
|
2017-10-13 02:02:07 +02:00
|
|
|
protected void setRepeatModeButton(final ImageButton imageButton, final int repeatMode) {
|
|
|
|
switch (repeatMode) {
|
|
|
|
case Player.REPEAT_MODE_OFF:
|
|
|
|
imageButton.setImageResource(R.drawable.exo_controls_repeat_off);
|
|
|
|
break;
|
|
|
|
case Player.REPEAT_MODE_ONE:
|
|
|
|
imageButton.setImageResource(R.drawable.exo_controls_repeat_one);
|
|
|
|
break;
|
|
|
|
case Player.REPEAT_MODE_ALL:
|
|
|
|
imageButton.setImageResource(R.drawable.exo_controls_repeat_all);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2017-10-23 03:58:01 +02:00
|
|
|
protected void setShuffleButton(final ImageButton shuffleButton, final boolean shuffled) {
|
|
|
|
final int shuffleAlpha = shuffled ? 255 : 77;
|
|
|
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
|
|
|
|
shuffleButton.setImageAlpha(shuffleAlpha);
|
|
|
|
} else {
|
|
|
|
shuffleButton.setAlpha(shuffleAlpha);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2018-03-25 20:33:31 +02:00
|
|
|
private boolean isInMultiWindow() {
|
|
|
|
return Build.VERSION.SDK_INT >= Build.VERSION_CODES.N && isInMultiWindowMode();
|
|
|
|
}
|
|
|
|
|
2018-03-21 08:11:54 +01:00
|
|
|
////////////////////////////////////////////////////////////////////////////
|
|
|
|
// Playback Parameters Listener
|
|
|
|
////////////////////////////////////////////////////////////////////////////
|
|
|
|
|
|
|
|
@Override
|
2018-05-08 20:24:42 +02:00
|
|
|
public void onPlaybackParameterChanged(float playbackTempo, float playbackPitch,
|
|
|
|
boolean playbackSkipSilence) {
|
|
|
|
if (playerImpl != null) {
|
|
|
|
playerImpl.setPlaybackParameters(playbackTempo, playbackPitch, playbackSkipSilence);
|
|
|
|
}
|
2018-03-21 08:11:54 +01:00
|
|
|
}
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
///////////////////////////////////////////////////////////////////////////
|
2017-03-09 05:44:00 +01:00
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
@SuppressWarnings({"unused", "WeakerAccess"})
|
2017-04-17 06:19:53 +02:00
|
|
|
private class VideoPlayerImpl extends VideoPlayer {
|
2018-08-15 11:02:37 +02:00
|
|
|
private final float MAX_GESTURE_LENGTH = 0.75f;
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
private TextView titleTextView;
|
|
|
|
private TextView channelTextView;
|
2018-08-15 11:02:37 +02:00
|
|
|
private RelativeLayout volumeRelativeLayout;
|
|
|
|
private ProgressBar volumeProgressBar;
|
|
|
|
private ImageView volumeImageView;
|
|
|
|
private RelativeLayout brightnessRelativeLayout;
|
|
|
|
private ProgressBar brightnessProgressBar;
|
|
|
|
private ImageView brightnessImageView;
|
2017-10-13 05:47:12 +02:00
|
|
|
private ImageButton queueButton;
|
2017-10-23 03:58:01 +02:00
|
|
|
private ImageButton repeatButton;
|
|
|
|
private ImageButton shuffleButton;
|
2016-02-22 20:28:37 +01:00
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
private ImageButton playPauseButton;
|
2017-10-22 21:43:49 +02:00
|
|
|
private ImageButton playPreviousButton;
|
|
|
|
private ImageButton playNextButton;
|
2017-03-27 06:08:16 +02:00
|
|
|
|
2017-10-13 05:47:12 +02:00
|
|
|
private RelativeLayout queueLayout;
|
|
|
|
private ImageButton itemsListCloseButton;
|
|
|
|
private RecyclerView itemsList;
|
|
|
|
private ItemTouchHelper itemTouchHelper;
|
|
|
|
|
|
|
|
private boolean queueVisible;
|
|
|
|
|
2017-11-09 11:29:02 +01:00
|
|
|
private ImageButton moreOptionsButton;
|
2018-02-07 00:07:49 +01:00
|
|
|
private ImageButton toggleOrientationButton;
|
|
|
|
private ImageButton switchPopupButton;
|
|
|
|
private ImageButton switchBackgroundButton;
|
|
|
|
|
2018-03-04 05:58:53 +01:00
|
|
|
private RelativeLayout windowRootLayout;
|
2018-02-07 00:07:49 +01:00
|
|
|
private View secondaryControls;
|
2017-11-09 11:29:02 +01:00
|
|
|
|
2018-08-15 11:02:37 +02:00
|
|
|
private int maxGestureLength;
|
|
|
|
|
2017-10-26 22:42:50 +02:00
|
|
|
VideoPlayerImpl(final Context context) {
|
|
|
|
super("VideoPlayerImpl" + MainVideoPlayer.TAG, context);
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
|
|
|
|
2017-03-09 05:44:00 +01:00
|
|
|
@Override
|
2017-03-27 06:08:16 +02:00
|
|
|
public void initViews(View rootView) {
|
|
|
|
super.initViews(rootView);
|
2017-09-03 08:04:18 +02:00
|
|
|
this.titleTextView = rootView.findViewById(R.id.titleTextView);
|
|
|
|
this.channelTextView = rootView.findViewById(R.id.channelTextView);
|
2018-08-15 11:02:37 +02:00
|
|
|
this.volumeRelativeLayout = rootView.findViewById(R.id.volumeRelativeLayout);
|
|
|
|
this.volumeProgressBar = rootView.findViewById(R.id.volumeProgressBar);
|
|
|
|
this.volumeImageView = rootView.findViewById(R.id.volumeImageView);
|
|
|
|
this.brightnessRelativeLayout = rootView.findViewById(R.id.brightnessRelativeLayout);
|
|
|
|
this.brightnessProgressBar = rootView.findViewById(R.id.brightnessProgressBar);
|
|
|
|
this.brightnessImageView = rootView.findViewById(R.id.brightnessImageView);
|
2017-10-13 05:47:12 +02:00
|
|
|
this.queueButton = rootView.findViewById(R.id.queueButton);
|
2017-10-23 03:58:01 +02:00
|
|
|
this.repeatButton = rootView.findViewById(R.id.repeatButton);
|
|
|
|
this.shuffleButton = rootView.findViewById(R.id.shuffleButton);
|
2017-03-27 06:08:16 +02:00
|
|
|
|
2017-09-03 08:04:18 +02:00
|
|
|
this.playPauseButton = rootView.findViewById(R.id.playPauseButton);
|
2017-10-22 21:43:49 +02:00
|
|
|
this.playPreviousButton = rootView.findViewById(R.id.playPreviousButton);
|
|
|
|
this.playNextButton = rootView.findViewById(R.id.playNextButton);
|
2018-02-07 00:07:49 +01:00
|
|
|
|
2017-11-09 11:29:02 +01:00
|
|
|
this.moreOptionsButton = rootView.findViewById(R.id.moreOptionsButton);
|
2018-02-07 00:07:49 +01:00
|
|
|
this.secondaryControls = rootView.findViewById(R.id.secondaryControls);
|
|
|
|
this.toggleOrientationButton = rootView.findViewById(R.id.toggleOrientation);
|
|
|
|
this.switchBackgroundButton = rootView.findViewById(R.id.switchBackground);
|
|
|
|
this.switchPopupButton = rootView.findViewById(R.id.switchPopup);
|
2017-03-27 06:08:16 +02:00
|
|
|
|
2018-03-04 05:58:53 +01:00
|
|
|
this.queueLayout = findViewById(R.id.playQueuePanel);
|
|
|
|
this.itemsListCloseButton = findViewById(R.id.playQueueClose);
|
|
|
|
this.itemsList = findViewById(R.id.playQueue);
|
|
|
|
|
2017-10-28 21:57:09 +02:00
|
|
|
titleTextView.setSelected(true);
|
|
|
|
channelTextView.setSelected(true);
|
|
|
|
|
2017-05-14 05:32:28 +02:00
|
|
|
getRootView().setKeepScreenOn(true);
|
2018-02-09 22:26:03 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
protected void setupSubtitleView(@NonNull SubtitleView view,
|
2018-04-08 22:58:18 +02:00
|
|
|
final float captionScale,
|
|
|
|
@NonNull final CaptionStyleCompat captionStyle) {
|
2018-02-09 22:26:03 +01:00
|
|
|
final DisplayMetrics metrics = context.getResources().getDisplayMetrics();
|
|
|
|
final int minimumLength = Math.min(metrics.heightPixels, metrics.widthPixels);
|
2018-04-08 22:58:18 +02:00
|
|
|
final float captionRatioInverse = 20f + 4f * (1f - captionScale);
|
2018-02-09 22:26:03 +01:00
|
|
|
view.setFixedTextSize(TypedValue.COMPLEX_UNIT_PX,
|
2018-02-11 04:33:48 +01:00
|
|
|
(float) minimumLength / captionRatioInverse);
|
2018-04-08 22:58:18 +02:00
|
|
|
view.setApplyEmbeddedStyles(captionStyle.equals(CaptionStyleCompat.DEFAULT));
|
|
|
|
view.setStyle(captionStyle);
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
|
|
|
|
2017-03-09 05:44:00 +01:00
|
|
|
@Override
|
2017-03-27 06:08:16 +02:00
|
|
|
public void initListeners() {
|
|
|
|
super.initListeners();
|
|
|
|
|
2018-09-05 04:54:17 +02:00
|
|
|
PlayerGestureListener listener = new PlayerGestureListener();
|
2017-03-27 06:08:16 +02:00
|
|
|
gestureDetector = new GestureDetector(context, listener);
|
|
|
|
gestureDetector.setIsLongpressEnabled(false);
|
2017-09-07 22:01:02 +02:00
|
|
|
getRootView().setOnTouchListener(listener);
|
2017-03-27 06:08:16 +02:00
|
|
|
|
2017-10-13 05:47:12 +02:00
|
|
|
queueButton.setOnClickListener(this);
|
2017-03-27 06:08:16 +02:00
|
|
|
repeatButton.setOnClickListener(this);
|
2017-10-23 03:58:01 +02:00
|
|
|
shuffleButton.setOnClickListener(this);
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
playPauseButton.setOnClickListener(this);
|
2017-10-22 21:43:49 +02:00
|
|
|
playPreviousButton.setOnClickListener(this);
|
|
|
|
playNextButton.setOnClickListener(this);
|
2018-02-07 00:07:49 +01:00
|
|
|
|
2017-11-09 11:29:02 +01:00
|
|
|
moreOptionsButton.setOnClickListener(this);
|
2018-02-07 00:07:49 +01:00
|
|
|
toggleOrientationButton.setOnClickListener(this);
|
|
|
|
switchBackgroundButton.setOnClickListener(this);
|
|
|
|
switchPopupButton.setOnClickListener(this);
|
2018-08-15 11:02:37 +02:00
|
|
|
|
|
|
|
getRootView().addOnLayoutChangeListener((view, l, t, r, b, ol, ot, or, ob) -> {
|
|
|
|
if (l != ol || t != ot || r != or || b != ob) {
|
|
|
|
// Use smaller value to be consistent between screen orientations
|
|
|
|
// (and to make usage easier)
|
|
|
|
int width = r - l, height = b - t;
|
|
|
|
maxGestureLength = (int) (Math.min(width, height) * MAX_GESTURE_LENGTH);
|
|
|
|
|
|
|
|
if (DEBUG) Log.d(TAG, "maxGestureLength = " + maxGestureLength);
|
|
|
|
|
|
|
|
volumeProgressBar.setMax(maxGestureLength);
|
|
|
|
brightnessProgressBar.setMax(maxGestureLength);
|
2018-09-05 04:54:17 +02:00
|
|
|
|
|
|
|
setInitialGestureValues();
|
2018-08-15 11:02:37 +02:00
|
|
|
}
|
|
|
|
});
|
2017-03-09 05:44:00 +01:00
|
|
|
}
|
2016-02-22 20:28:37 +01:00
|
|
|
|
2018-06-06 08:37:20 +02:00
|
|
|
public void minimize() {
|
2018-06-03 23:09:16 +02:00
|
|
|
switch (PlayerHelper.getMinimizeOnExitAction(context)) {
|
|
|
|
case PlayerHelper.MinimizeMode.MINIMIZE_ON_EXIT_MODE_BACKGROUND:
|
|
|
|
onPlayBackgroundButtonClicked();
|
|
|
|
break;
|
|
|
|
case PlayerHelper.MinimizeMode.MINIMIZE_ON_EXIT_MODE_POPUP:
|
|
|
|
onFullScreenButtonClicked();
|
|
|
|
break;
|
|
|
|
case PlayerHelper.MinimizeMode.MINIMIZE_ON_EXIT_MODE_NONE:
|
2018-06-26 19:19:16 +02:00
|
|
|
default:
|
|
|
|
// No action
|
2018-06-03 23:09:16 +02:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2017-10-13 02:02:07 +02:00
|
|
|
/*//////////////////////////////////////////////////////////////////////////
|
|
|
|
// ExoPlayer Video Listener
|
|
|
|
//////////////////////////////////////////////////////////////////////////*/
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void onRepeatModeChanged(int i) {
|
|
|
|
super.onRepeatModeChanged(i);
|
2017-10-23 03:58:01 +02:00
|
|
|
updatePlaybackButtons();
|
2017-10-13 02:02:07 +02:00
|
|
|
}
|
|
|
|
|
2018-03-03 23:24:21 +01:00
|
|
|
@Override
|
|
|
|
public void onShuffleClicked() {
|
|
|
|
super.onShuffleClicked();
|
|
|
|
updatePlaybackButtons();
|
|
|
|
}
|
|
|
|
|
2017-09-05 21:27:12 +02:00
|
|
|
/*//////////////////////////////////////////////////////////////////////////
|
|
|
|
// Playback Listener
|
|
|
|
//////////////////////////////////////////////////////////////////////////*/
|
|
|
|
|
2018-05-17 03:18:32 +02:00
|
|
|
protected void onMetadataChanged(@NonNull final MediaSourceTag tag) {
|
2018-05-10 22:28:31 +02:00
|
|
|
super.onMetadataChanged(tag);
|
2017-09-05 21:27:12 +02:00
|
|
|
|
2018-05-17 03:18:32 +02:00
|
|
|
titleTextView.setText(tag.getMetadata().getName());
|
|
|
|
channelTextView.setText(tag.getMetadata().getUploaderName());
|
2017-09-02 20:06:36 +02:00
|
|
|
}
|
|
|
|
|
2017-10-23 03:58:01 +02:00
|
|
|
@Override
|
2018-03-03 23:24:21 +01:00
|
|
|
public void onPlaybackShutdown() {
|
|
|
|
super.onPlaybackShutdown();
|
|
|
|
finish();
|
2017-10-23 03:58:01 +02:00
|
|
|
}
|
|
|
|
|
2017-10-23 04:21:19 +02:00
|
|
|
/*//////////////////////////////////////////////////////////////////////////
|
|
|
|
// Player Overrides
|
|
|
|
//////////////////////////////////////////////////////////////////////////*/
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
@Override
|
|
|
|
public void onFullScreenButtonClicked() {
|
2017-09-07 22:01:02 +02:00
|
|
|
super.onFullScreenButtonClicked();
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
if (DEBUG) Log.d(TAG, "onFullScreenButtonClicked() called");
|
2017-09-07 22:01:02 +02:00
|
|
|
if (simpleExoPlayer == null) return;
|
2017-03-27 06:08:16 +02:00
|
|
|
|
2018-01-27 03:55:28 +01:00
|
|
|
if (!PermissionHelper.isPopupEnabled(context)) {
|
|
|
|
PermissionHelper.showPopupEnablementToast(context);
|
2017-03-27 06:08:16 +02:00
|
|
|
return;
|
|
|
|
}
|
2016-02-22 20:28:37 +01:00
|
|
|
|
2017-10-22 21:43:49 +02:00
|
|
|
setRecovery();
|
2017-09-25 05:14:58 +02:00
|
|
|
final Intent intent = NavigationHelper.getPlayerIntent(
|
|
|
|
context,
|
|
|
|
PopupVideoPlayer.class,
|
|
|
|
this.getPlayQueue(),
|
2017-10-25 07:18:44 +02:00
|
|
|
this.getRepeatMode(),
|
2017-10-23 03:58:01 +02:00
|
|
|
this.getPlaybackSpeed(),
|
2017-10-25 06:47:14 +02:00
|
|
|
this.getPlaybackPitch(),
|
2018-05-08 20:24:42 +02:00
|
|
|
this.getPlaybackSkipSilence(),
|
2017-10-25 06:47:14 +02:00
|
|
|
this.getPlaybackQuality()
|
2017-09-25 05:14:58 +02:00
|
|
|
);
|
2017-09-11 02:43:21 +02:00
|
|
|
context.startService(intent);
|
2017-04-12 08:07:15 +02:00
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
((View) getControlAnimationView().getParent()).setVisibility(View.GONE);
|
2017-10-28 21:57:09 +02:00
|
|
|
destroy();
|
2017-09-07 22:01:02 +02:00
|
|
|
finish();
|
2017-03-09 05:44:00 +01:00
|
|
|
}
|
2016-02-22 20:28:37 +01:00
|
|
|
|
2017-11-09 11:29:02 +01:00
|
|
|
public void onPlayBackgroundButtonClicked() {
|
|
|
|
if (DEBUG) Log.d(TAG, "onPlayBackgroundButtonClicked() called");
|
|
|
|
if (playerImpl.getPlayer() == null) return;
|
|
|
|
|
|
|
|
setRecovery();
|
|
|
|
final Intent intent = NavigationHelper.getPlayerIntent(
|
|
|
|
context,
|
|
|
|
BackgroundPlayer.class,
|
|
|
|
this.getPlayQueue(),
|
|
|
|
this.getRepeatMode(),
|
|
|
|
this.getPlaybackSpeed(),
|
|
|
|
this.getPlaybackPitch(),
|
2018-05-08 20:24:42 +02:00
|
|
|
this.getPlaybackSkipSilence(),
|
2017-11-09 11:29:02 +01:00
|
|
|
this.getPlaybackQuality()
|
|
|
|
);
|
|
|
|
context.startService(intent);
|
|
|
|
|
|
|
|
((View) getControlAnimationView().getParent()).setVisibility(View.GONE);
|
|
|
|
destroy();
|
|
|
|
finish();
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
@Override
|
|
|
|
public void onClick(View v) {
|
|
|
|
super.onClick(v);
|
2017-10-23 03:58:01 +02:00
|
|
|
if (v.getId() == playPauseButton.getId()) {
|
2018-03-23 02:12:11 +01:00
|
|
|
onPlayPause();
|
2017-10-13 05:47:12 +02:00
|
|
|
|
2017-10-22 21:43:49 +02:00
|
|
|
} else if (v.getId() == playPreviousButton.getId()) {
|
|
|
|
onPlayPrevious();
|
|
|
|
|
|
|
|
} else if (v.getId() == playNextButton.getId()) {
|
|
|
|
onPlayNext();
|
|
|
|
|
2017-10-13 05:47:12 +02:00
|
|
|
} else if (v.getId() == queueButton.getId()) {
|
|
|
|
onQueueClicked();
|
|
|
|
return;
|
2017-10-23 03:58:01 +02:00
|
|
|
} else if (v.getId() == repeatButton.getId()) {
|
|
|
|
onRepeatClicked();
|
|
|
|
return;
|
|
|
|
} else if (v.getId() == shuffleButton.getId()) {
|
|
|
|
onShuffleClicked();
|
|
|
|
return;
|
2017-11-09 11:29:02 +01:00
|
|
|
} else if (v.getId() == moreOptionsButton.getId()) {
|
|
|
|
onMoreOptionsClicked();
|
2018-02-07 00:07:49 +01:00
|
|
|
|
|
|
|
} else if (v.getId() == toggleOrientationButton.getId()) {
|
|
|
|
onScreenRotationClicked();
|
|
|
|
|
|
|
|
} else if (v.getId() == switchPopupButton.getId()) {
|
|
|
|
onFullScreenButtonClicked();
|
|
|
|
|
|
|
|
} else if (v.getId() == switchBackgroundButton.getId()) {
|
|
|
|
onPlayBackgroundButtonClicked();
|
|
|
|
|
2017-10-13 05:47:12 +02:00
|
|
|
}
|
2017-03-27 06:08:16 +02:00
|
|
|
|
|
|
|
if (getCurrentState() != STATE_COMPLETED) {
|
2017-05-08 15:33:26 +02:00
|
|
|
getControlsVisibilityHandler().removeCallbacksAndMessages(null);
|
2018-03-04 05:58:53 +01:00
|
|
|
animateView(getControlsRoot(), true, DEFAULT_CONTROLS_DURATION, 0, () -> {
|
2018-01-04 07:53:31 +01:00
|
|
|
if (getCurrentState() == STATE_PLAYING && !isSomePopupMenuVisible()) {
|
2018-03-04 05:58:53 +01:00
|
|
|
hideControls(DEFAULT_CONTROLS_DURATION, DEFAULT_CONTROLS_HIDE_TIME);
|
2017-03-27 06:08:16 +02:00
|
|
|
}
|
2017-05-08 15:33:26 +02:00
|
|
|
});
|
2017-03-27 06:08:16 +02:00
|
|
|
}
|
|
|
|
}
|
2016-02-22 20:28:37 +01:00
|
|
|
|
2017-10-13 05:47:12 +02:00
|
|
|
private void onQueueClicked() {
|
|
|
|
queueVisible = true;
|
|
|
|
hideSystemUi();
|
2017-10-23 03:58:01 +02:00
|
|
|
|
|
|
|
buildQueue();
|
|
|
|
updatePlaybackButtons();
|
|
|
|
|
2017-10-13 05:47:12 +02:00
|
|
|
getControlsRoot().setVisibility(View.INVISIBLE);
|
2018-03-14 04:25:22 +01:00
|
|
|
animateView(queueLayout, SLIDE_AND_ALPHA, /*visible=*/true,
|
|
|
|
DEFAULT_CONTROLS_DURATION);
|
2017-10-23 03:58:01 +02:00
|
|
|
|
2017-11-04 04:32:10 +01:00
|
|
|
itemsList.scrollToPosition(playQueue.getIndex());
|
2017-10-13 05:47:12 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
private void onQueueClosed() {
|
2018-03-14 04:25:22 +01:00
|
|
|
animateView(queueLayout, SLIDE_AND_ALPHA, /*visible=*/false,
|
|
|
|
DEFAULT_CONTROLS_DURATION);
|
2017-10-13 05:47:12 +02:00
|
|
|
queueVisible = false;
|
|
|
|
}
|
|
|
|
|
2017-11-09 11:29:02 +01:00
|
|
|
private void onMoreOptionsClicked() {
|
|
|
|
if (DEBUG) Log.d(TAG, "onMoreOptionsClicked() called");
|
|
|
|
|
2018-03-14 04:25:22 +01:00
|
|
|
final boolean isMoreControlsVisible = secondaryControls.getVisibility() == View.VISIBLE;
|
|
|
|
|
|
|
|
animateRotation(moreOptionsButton, DEFAULT_CONTROLS_DURATION,
|
|
|
|
isMoreControlsVisible ? 0 : 180);
|
|
|
|
animateView(secondaryControls, SLIDE_AND_ALPHA, !isMoreControlsVisible,
|
|
|
|
DEFAULT_CONTROLS_DURATION);
|
2018-03-04 05:58:53 +01:00
|
|
|
showControls(DEFAULT_CONTROLS_DURATION);
|
2017-11-09 11:29:02 +01:00
|
|
|
}
|
|
|
|
|
2017-03-27 15:12:22 +02:00
|
|
|
private void onScreenRotationClicked() {
|
|
|
|
if (DEBUG) Log.d(TAG, "onScreenRotationClicked() called");
|
|
|
|
toggleOrientation();
|
2018-01-04 07:53:31 +01:00
|
|
|
showControlsThenHide();
|
2017-03-27 15:12:22 +02:00
|
|
|
}
|
|
|
|
|
2018-03-21 08:11:54 +01:00
|
|
|
@Override
|
|
|
|
public void onPlaybackSpeedClicked() {
|
2018-05-08 20:24:42 +02:00
|
|
|
PlaybackParameterDialog
|
|
|
|
.newInstance(getPlaybackSpeed(), getPlaybackPitch(), getPlaybackSkipSilence())
|
2018-03-21 08:11:54 +01:00
|
|
|
.show(getSupportFragmentManager(), TAG);
|
|
|
|
}
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
@Override
|
|
|
|
public void onStopTrackingTouch(SeekBar seekBar) {
|
|
|
|
super.onStopTrackingTouch(seekBar);
|
2018-03-04 05:58:53 +01:00
|
|
|
if (wasPlaying()) showControlsThenHide();
|
2017-03-27 06:08:16 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void onDismiss(PopupMenu menu) {
|
|
|
|
super.onDismiss(menu);
|
2018-03-04 05:58:53 +01:00
|
|
|
if (isPlaying()) hideControls(DEFAULT_CONTROLS_DURATION, 0);
|
2018-03-16 04:07:38 +01:00
|
|
|
hideSystemUi();
|
2017-03-27 06:08:16 +02:00
|
|
|
}
|
|
|
|
|
2018-02-07 22:11:19 +01:00
|
|
|
@Override
|
2018-02-11 04:33:48 +01:00
|
|
|
protected int nextResizeMode(int currentResizeMode) {
|
2018-09-22 11:32:13 +02:00
|
|
|
final int newResizeMode;
|
2018-02-11 04:33:48 +01:00
|
|
|
switch (currentResizeMode) {
|
|
|
|
case AspectRatioFrameLayout.RESIZE_MODE_FIT:
|
2018-09-22 11:32:13 +02:00
|
|
|
newResizeMode = AspectRatioFrameLayout.RESIZE_MODE_FILL;
|
|
|
|
break;
|
2018-02-11 04:33:48 +01:00
|
|
|
case AspectRatioFrameLayout.RESIZE_MODE_FILL:
|
2018-09-22 11:32:13 +02:00
|
|
|
newResizeMode = AspectRatioFrameLayout.RESIZE_MODE_ZOOM;
|
|
|
|
break;
|
2018-02-11 04:33:48 +01:00
|
|
|
default:
|
2018-09-22 11:32:13 +02:00
|
|
|
newResizeMode = AspectRatioFrameLayout.RESIZE_MODE_FIT;
|
|
|
|
break;
|
2018-02-07 22:11:19 +01:00
|
|
|
}
|
2018-09-22 11:32:13 +02:00
|
|
|
|
|
|
|
storeResizeMode(newResizeMode);
|
|
|
|
return newResizeMode;
|
|
|
|
}
|
|
|
|
|
|
|
|
private void storeResizeMode(@AspectRatioFrameLayout.ResizeMode int resizeMode) {
|
|
|
|
defaultPreferences.edit()
|
|
|
|
.putInt(getString(R.string.last_resize_mode), resizeMode)
|
|
|
|
.apply();
|
2018-02-07 22:11:19 +01:00
|
|
|
}
|
|
|
|
|
2017-10-23 04:21:19 +02:00
|
|
|
@Override
|
2018-05-10 22:28:31 +02:00
|
|
|
protected VideoPlaybackResolver.QualityResolver getQualityResolver() {
|
|
|
|
return new VideoPlaybackResolver.QualityResolver() {
|
|
|
|
@Override
|
|
|
|
public int getDefaultResolutionIndex(List<VideoStream> sortedVideos) {
|
|
|
|
return ListHelper.getDefaultResolutionIndex(context, sortedVideos);
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public int getOverrideResolutionIndex(List<VideoStream> sortedVideos,
|
|
|
|
String playbackQuality) {
|
|
|
|
return ListHelper.getResolutionIndex(context, sortedVideos, playbackQuality);
|
|
|
|
}
|
|
|
|
};
|
2017-10-25 06:47:14 +02:00
|
|
|
}
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
/*//////////////////////////////////////////////////////////////////////////
|
|
|
|
// States
|
|
|
|
//////////////////////////////////////////////////////////////////////////*/
|
|
|
|
|
2017-10-22 21:43:49 +02:00
|
|
|
private void animatePlayButtons(final boolean show, final int duration) {
|
|
|
|
animateView(playPauseButton, AnimationUtils.Type.SCALE_AND_ALPHA, show, duration);
|
|
|
|
animateView(playPreviousButton, AnimationUtils.Type.SCALE_AND_ALPHA, show, duration);
|
|
|
|
animateView(playNextButton, AnimationUtils.Type.SCALE_AND_ALPHA, show, duration);
|
|
|
|
}
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
@Override
|
2017-09-14 17:44:09 +02:00
|
|
|
public void onBlocked() {
|
|
|
|
super.onBlocked();
|
2017-03-27 06:08:16 +02:00
|
|
|
playPauseButton.setImageResource(R.drawable.ic_pause_white);
|
2017-10-22 21:43:49 +02:00
|
|
|
animatePlayButtons(false, 100);
|
2017-05-14 05:32:28 +02:00
|
|
|
getRootView().setKeepScreenOn(true);
|
2017-04-09 19:34:00 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void onBuffering() {
|
|
|
|
super.onBuffering();
|
2017-05-14 05:32:28 +02:00
|
|
|
getRootView().setKeepScreenOn(true);
|
2017-03-27 06:08:16 +02:00
|
|
|
}
|
|
|
|
|
2017-04-17 06:19:53 +02:00
|
|
|
@Override
|
|
|
|
public void onPlaying() {
|
|
|
|
super.onPlaying();
|
2018-01-04 07:53:31 +01:00
|
|
|
animateView(playPauseButton, AnimationUtils.Type.SCALE_AND_ALPHA, false, 80, 0, () -> {
|
|
|
|
playPauseButton.setImageResource(R.drawable.ic_pause_white);
|
|
|
|
animatePlayButtons(true, 200);
|
2017-04-17 06:19:53 +02:00
|
|
|
});
|
2018-03-04 05:58:53 +01:00
|
|
|
|
2017-05-14 05:32:28 +02:00
|
|
|
getRootView().setKeepScreenOn(true);
|
2017-04-17 06:19:53 +02:00
|
|
|
}
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
@Override
|
|
|
|
public void onPaused() {
|
|
|
|
super.onPaused();
|
2018-01-04 07:53:31 +01:00
|
|
|
animateView(playPauseButton, AnimationUtils.Type.SCALE_AND_ALPHA, false, 80, 0, () -> {
|
|
|
|
playPauseButton.setImageResource(R.drawable.ic_play_arrow_white);
|
|
|
|
animatePlayButtons(true, 200);
|
2017-04-17 06:19:53 +02:00
|
|
|
});
|
|
|
|
|
2018-04-08 01:40:38 +02:00
|
|
|
showSystemUi();
|
2017-05-14 05:32:28 +02:00
|
|
|
getRootView().setKeepScreenOn(false);
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
2017-03-27 06:08:16 +02:00
|
|
|
public void onPausedSeek() {
|
|
|
|
super.onPausedSeek();
|
2017-10-22 21:43:49 +02:00
|
|
|
animatePlayButtons(false, 100);
|
2017-05-14 05:32:28 +02:00
|
|
|
getRootView().setKeepScreenOn(true);
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
|
|
|
|
2017-03-09 05:44:00 +01:00
|
|
|
|
|
|
|
@Override
|
2017-03-27 06:08:16 +02:00
|
|
|
public void onCompleted() {
|
2018-01-04 07:53:31 +01:00
|
|
|
animateView(playPauseButton, AnimationUtils.Type.SCALE_AND_ALPHA, false, 0, 0, () -> {
|
|
|
|
playPauseButton.setImageResource(R.drawable.ic_replay_white);
|
2018-03-04 05:58:53 +01:00
|
|
|
animatePlayButtons(true, DEFAULT_CONTROLS_DURATION);
|
2017-09-05 00:38:58 +02:00
|
|
|
});
|
|
|
|
|
2017-05-14 05:32:28 +02:00
|
|
|
getRootView().setKeepScreenOn(false);
|
2017-03-27 06:08:16 +02:00
|
|
|
super.onCompleted();
|
|
|
|
}
|
|
|
|
|
|
|
|
/*//////////////////////////////////////////////////////////////////////////
|
|
|
|
// Utils
|
|
|
|
//////////////////////////////////////////////////////////////////////////*/
|
|
|
|
|
2018-09-05 04:54:17 +02:00
|
|
|
private void setInitialGestureValues() {
|
|
|
|
if (getAudioReactor() != null) {
|
|
|
|
final float currentVolumeNormalized = (float) getAudioReactor().getVolume() / getAudioReactor().getMaxVolume();
|
|
|
|
volumeProgressBar.setProgress((int) (volumeProgressBar.getMax() * currentVolumeNormalized));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2017-10-13 05:47:12 +02:00
|
|
|
@Override
|
|
|
|
public void showControlsThenHide() {
|
|
|
|
if (queueVisible) return;
|
|
|
|
|
|
|
|
super.showControlsThenHide();
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void showControls(long duration) {
|
|
|
|
if (queueVisible) return;
|
|
|
|
|
|
|
|
super.showControls(duration);
|
|
|
|
}
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
@Override
|
2017-05-08 15:33:26 +02:00
|
|
|
public void hideControls(final long duration, long delay) {
|
|
|
|
if (DEBUG) Log.d(TAG, "hideControls() called with: delay = [" + delay + "]");
|
|
|
|
getControlsVisibilityHandler().removeCallbacksAndMessages(null);
|
2018-01-04 07:53:31 +01:00
|
|
|
getControlsVisibilityHandler().postDelayed(() ->
|
2018-03-04 05:58:53 +01:00
|
|
|
animateView(getControlsRoot(), false, duration, 0,
|
|
|
|
MainVideoPlayer.this::hideSystemUi),
|
|
|
|
/*delayMillis=*/delay
|
2018-01-04 07:53:31 +01:00
|
|
|
);
|
2017-03-27 06:08:16 +02:00
|
|
|
}
|
|
|
|
|
2017-10-23 03:58:01 +02:00
|
|
|
private void updatePlaybackButtons() {
|
|
|
|
if (repeatButton == null || shuffleButton == null ||
|
|
|
|
simpleExoPlayer == null || playQueue == null) return;
|
|
|
|
|
2017-10-25 07:18:44 +02:00
|
|
|
setRepeatModeButton(repeatButton, getRepeatMode());
|
2017-10-23 03:58:01 +02:00
|
|
|
setShuffleButton(shuffleButton, playQueue.isShuffled());
|
|
|
|
}
|
|
|
|
|
2017-10-13 05:47:12 +02:00
|
|
|
private void buildQueue() {
|
|
|
|
itemsList.setAdapter(playQueueAdapter);
|
|
|
|
itemsList.setClickable(true);
|
|
|
|
itemsList.setLongClickable(true);
|
|
|
|
|
2017-11-04 04:32:10 +01:00
|
|
|
itemsList.clearOnScrollListeners();
|
|
|
|
itemsList.addOnScrollListener(getQueueScrollListener());
|
|
|
|
|
2017-10-13 05:47:12 +02:00
|
|
|
itemTouchHelper = new ItemTouchHelper(getItemTouchCallback());
|
|
|
|
itemTouchHelper.attachToRecyclerView(itemsList);
|
|
|
|
|
|
|
|
playQueueAdapter.setSelectedListener(getOnSelectedListener());
|
|
|
|
|
2018-01-04 07:53:31 +01:00
|
|
|
itemsListCloseButton.setOnClickListener(view -> onQueueClosed());
|
2017-10-13 05:47:12 +02:00
|
|
|
}
|
|
|
|
|
2017-11-04 04:32:10 +01:00
|
|
|
private OnScrollBelowItemsListener getQueueScrollListener() {
|
|
|
|
return new OnScrollBelowItemsListener() {
|
|
|
|
@Override
|
|
|
|
public void onScrolledDown(RecyclerView recyclerView) {
|
|
|
|
if (playQueue != null && !playQueue.isComplete()) {
|
|
|
|
playQueue.fetch();
|
|
|
|
} else if (itemsList != null) {
|
|
|
|
itemsList.clearOnScrollListeners();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
};
|
|
|
|
}
|
|
|
|
|
2017-10-13 05:47:12 +02:00
|
|
|
private ItemTouchHelper.SimpleCallback getItemTouchCallback() {
|
2018-03-14 04:25:22 +01:00
|
|
|
return new PlayQueueItemTouchCallback() {
|
2017-10-13 05:47:12 +02:00
|
|
|
@Override
|
2018-03-14 04:25:22 +01:00
|
|
|
public void onMove(int sourceIndex, int targetIndex) {
|
|
|
|
if (playQueue != null) playQueue.move(sourceIndex, targetIndex);
|
2017-10-13 05:47:12 +02:00
|
|
|
}
|
2018-11-30 20:05:27 +01:00
|
|
|
|
|
|
|
@Override
|
|
|
|
public void onSwiped(int index) {
|
|
|
|
if(index != -1) playQueue.remove(index);
|
|
|
|
}
|
2017-10-13 05:47:12 +02:00
|
|
|
};
|
|
|
|
}
|
|
|
|
|
|
|
|
private PlayQueueItemBuilder.OnSelectedListener getOnSelectedListener() {
|
|
|
|
return new PlayQueueItemBuilder.OnSelectedListener() {
|
|
|
|
@Override
|
|
|
|
public void selected(PlayQueueItem item, View view) {
|
2017-10-14 06:07:19 +02:00
|
|
|
onSelected(item);
|
2017-10-13 05:47:12 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void held(PlayQueueItem item, View view) {
|
|
|
|
final int index = playQueue.indexOf(item);
|
|
|
|
if (index != -1) playQueue.remove(index);
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void onStartDrag(PlayQueueItemHolder viewHolder) {
|
|
|
|
if (itemTouchHelper != null) itemTouchHelper.startDrag(viewHolder);
|
|
|
|
}
|
|
|
|
};
|
|
|
|
}
|
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
///////////////////////////////////////////////////////////////////////////
|
|
|
|
// Getters
|
|
|
|
///////////////////////////////////////////////////////////////////////////
|
|
|
|
|
|
|
|
public TextView getTitleTextView() {
|
|
|
|
return titleTextView;
|
|
|
|
}
|
|
|
|
|
|
|
|
public TextView getChannelTextView() {
|
|
|
|
return channelTextView;
|
2016-02-22 20:28:37 +01:00
|
|
|
}
|
|
|
|
|
2018-08-15 11:02:37 +02:00
|
|
|
public RelativeLayout getVolumeRelativeLayout() {
|
|
|
|
return volumeRelativeLayout;
|
|
|
|
}
|
|
|
|
|
|
|
|
public ProgressBar getVolumeProgressBar() {
|
|
|
|
return volumeProgressBar;
|
|
|
|
}
|
|
|
|
|
|
|
|
public ImageView getVolumeImageView() {
|
|
|
|
return volumeImageView;
|
|
|
|
}
|
|
|
|
|
|
|
|
public RelativeLayout getBrightnessRelativeLayout() {
|
|
|
|
return brightnessRelativeLayout;
|
|
|
|
}
|
|
|
|
|
|
|
|
public ProgressBar getBrightnessProgressBar() {
|
|
|
|
return brightnessProgressBar;
|
2017-03-09 05:44:00 +01:00
|
|
|
}
|
|
|
|
|
2018-08-15 11:02:37 +02:00
|
|
|
public ImageView getBrightnessImageView() {
|
|
|
|
return brightnessImageView;
|
2017-03-09 05:44:00 +01:00
|
|
|
}
|
2017-03-27 06:08:16 +02:00
|
|
|
|
|
|
|
public ImageButton getRepeatButton() {
|
|
|
|
return repeatButton;
|
|
|
|
}
|
|
|
|
|
|
|
|
public ImageButton getPlayPauseButton() {
|
|
|
|
return playPauseButton;
|
|
|
|
}
|
2018-08-15 11:02:37 +02:00
|
|
|
|
|
|
|
public int getMaxGestureLength() {
|
|
|
|
return maxGestureLength;
|
|
|
|
}
|
2017-03-27 06:08:16 +02:00
|
|
|
}
|
|
|
|
|
2018-09-05 04:54:17 +02:00
|
|
|
private class PlayerGestureListener extends GestureDetector.SimpleOnGestureListener implements View.OnTouchListener {
|
2017-03-27 06:08:16 +02:00
|
|
|
private boolean isMoving;
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public boolean onDoubleTap(MotionEvent e) {
|
|
|
|
if (DEBUG) Log.d(TAG, "onDoubleTap() called with: e = [" + e + "]" + "rawXy = " + e.getRawX() + ", " + e.getRawY() + ", xy = " + e.getX() + ", " + e.getY());
|
2017-09-01 21:10:36 +02:00
|
|
|
|
2018-04-29 11:23:21 +02:00
|
|
|
if (e.getX() > playerImpl.getRootView().getWidth() * 2 / 3) {
|
2017-10-22 21:43:49 +02:00
|
|
|
playerImpl.onFastForward();
|
2018-04-29 11:23:21 +02:00
|
|
|
} else if (e.getX() < playerImpl.getRootView().getWidth() / 3) {
|
2017-10-22 21:43:49 +02:00
|
|
|
playerImpl.onFastRewind();
|
2018-04-29 11:23:21 +02:00
|
|
|
} else {
|
|
|
|
playerImpl.getPlayPauseButton().performClick();
|
2017-10-29 02:18:40 +01:00
|
|
|
}
|
2017-09-01 21:10:36 +02:00
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public boolean onSingleTapConfirmed(MotionEvent e) {
|
|
|
|
if (DEBUG) Log.d(TAG, "onSingleTapConfirmed() called with: e = [" + e + "]");
|
2017-10-13 02:02:07 +02:00
|
|
|
if (playerImpl.getCurrentState() == BasePlayer.STATE_BLOCKED) return true;
|
2017-03-27 06:08:16 +02:00
|
|
|
|
2018-03-04 05:58:53 +01:00
|
|
|
if (playerImpl.isControlsVisible()) {
|
|
|
|
playerImpl.hideControls(150, 0);
|
|
|
|
} else {
|
2017-05-08 15:33:26 +02:00
|
|
|
playerImpl.showControlsThenHide();
|
2018-04-08 01:40:38 +02:00
|
|
|
showSystemUi();
|
2017-03-27 06:08:16 +02:00
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2018-03-05 05:16:38 +01:00
|
|
|
@Override
|
|
|
|
public boolean onDown(MotionEvent e) {
|
|
|
|
if (DEBUG) Log.d(TAG, "onDown() called with: e = [" + e + "]");
|
|
|
|
|
|
|
|
return super.onDown(e);
|
|
|
|
}
|
|
|
|
|
2018-09-05 04:54:17 +02:00
|
|
|
private static final int MOVEMENT_THRESHOLD = 40;
|
2017-05-17 02:45:38 +02:00
|
|
|
|
2018-08-31 16:00:40 +02:00
|
|
|
private final boolean isVolumeGestureEnabled = PlayerHelper.isVolumeGestureEnabled(getApplicationContext());
|
|
|
|
private final boolean isBrightnessGestureEnabled = PlayerHelper.isBrightnessGestureEnabled(getApplicationContext());
|
2017-05-17 02:45:38 +02:00
|
|
|
|
2018-08-15 11:02:37 +02:00
|
|
|
private final int maxVolume = playerImpl.getAudioReactor().getMaxVolume();
|
2017-03-27 06:08:16 +02:00
|
|
|
|
|
|
|
@Override
|
2018-09-05 04:54:17 +02:00
|
|
|
public boolean onScroll(MotionEvent initialEvent, MotionEvent movingEvent, float distanceX, float distanceY) {
|
2018-08-31 16:00:40 +02:00
|
|
|
if (!isVolumeGestureEnabled && !isBrightnessGestureEnabled) return false;
|
2017-05-17 02:45:38 +02:00
|
|
|
|
2017-03-27 06:08:16 +02:00
|
|
|
//noinspection PointlessBooleanExpression
|
2017-04-26 21:32:20 +02:00
|
|
|
if (DEBUG && false) Log.d(TAG, "MainVideoPlayer.onScroll = " +
|
2018-09-05 04:54:17 +02:00
|
|
|
", e1.getRaw = [" + initialEvent.getRawX() + ", " + initialEvent.getRawY() + "]" +
|
|
|
|
", e2.getRaw = [" + movingEvent.getRawX() + ", " + movingEvent.getRawY() + "]" +
|
2017-03-27 06:08:16 +02:00
|
|
|
", distanceXy = [" + distanceX + ", " + distanceY + "]");
|
2018-08-15 11:02:37 +02:00
|
|
|
|
2018-09-05 04:54:17 +02:00
|
|
|
final boolean insideThreshold = Math.abs(movingEvent.getY() - initialEvent.getY()) <= MOVEMENT_THRESHOLD;
|
|
|
|
if (!isMoving && (insideThreshold || Math.abs(distanceX) > Math.abs(distanceY))
|
|
|
|
|| playerImpl.getCurrentState() == BasePlayer.STATE_COMPLETED) {
|
2017-03-27 06:08:16 +02:00
|
|
|
return false;
|
2018-09-05 04:54:17 +02:00
|
|
|
}
|
2017-03-27 06:08:16 +02:00
|
|
|
|
|
|
|
isMoving = true;
|
|
|
|
|
2018-08-31 16:00:40 +02:00
|
|
|
boolean acceptAnyArea = isVolumeGestureEnabled != isBrightnessGestureEnabled;
|
2018-09-08 19:05:51 +02:00
|
|
|
boolean acceptVolumeArea = acceptAnyArea || initialEvent.getX() > playerImpl.getRootView().getWidth() / 2;
|
2018-08-31 16:00:40 +02:00
|
|
|
boolean acceptBrightnessArea = acceptAnyArea || !acceptVolumeArea;
|
|
|
|
|
|
|
|
if (isVolumeGestureEnabled && acceptVolumeArea) {
|
2018-08-15 11:02:37 +02:00
|
|
|
playerImpl.getVolumeProgressBar().incrementProgressBy((int) distanceY);
|
|
|
|
float currentProgressPercent =
|
|
|
|
(float) playerImpl.getVolumeProgressBar().getProgress() / playerImpl.getMaxGestureLength();
|
|
|
|
int currentVolume = (int) (maxVolume * currentProgressPercent);
|
2017-10-28 19:08:01 +02:00
|
|
|
playerImpl.getAudioReactor().setVolume(currentVolume);
|
2017-03-27 06:08:16 +02:00
|
|
|
|
|
|
|
if (DEBUG) Log.d(TAG, "onScroll().volumeControl, currentVolume = " + currentVolume);
|
|
|
|
|
2018-08-15 11:02:37 +02:00
|
|
|
final int resId =
|
|
|
|
currentProgressPercent <= 0 ? R.drawable.ic_volume_off_white_72dp
|
|
|
|
: currentProgressPercent < 0.25 ? R.drawable.ic_volume_mute_white_72dp
|
|
|
|
: currentProgressPercent < 0.75 ? R.drawable.ic_volume_down_white_72dp
|
|
|
|
: R.drawable.ic_volume_up_white_72dp;
|
2017-03-27 06:08:16 +02:00
|
|
|
|
2018-08-15 11:02:37 +02:00
|
|
|
playerImpl.getVolumeImageView().setImageDrawable(
|
|
|
|
AppCompatResources.getDrawable(getApplicationContext(), resId)
|
|
|
|
);
|
2017-03-27 06:08:16 +02:00
|
|
|
|
2018-08-15 11:02:37 +02:00
|
|
|
if (playerImpl.getVolumeRelativeLayout().getVisibility() != View.VISIBLE) {
|
|
|
|
animateView(playerImpl.getVolumeRelativeLayout(), SCALE_AND_ALPHA, true, 200);
|
|
|
|
}
|
|
|
|
if (playerImpl.getBrightnessRelativeLayout().getVisibility() == View.VISIBLE) {
|
|
|
|
playerImpl.getBrightnessRelativeLayout().setVisibility(View.GONE);
|
|
|
|
}
|
2018-08-31 16:00:40 +02:00
|
|
|
} else if (isBrightnessGestureEnabled && acceptBrightnessArea) {
|
2018-08-15 11:02:37 +02:00
|
|
|
playerImpl.getBrightnessProgressBar().incrementProgressBy((int) distanceY);
|
|
|
|
float currentProgressPercent =
|
|
|
|
(float) playerImpl.getBrightnessProgressBar().getProgress() / playerImpl.getMaxGestureLength();
|
|
|
|
WindowManager.LayoutParams layoutParams = getWindow().getAttributes();
|
|
|
|
layoutParams.screenBrightness = currentProgressPercent;
|
|
|
|
getWindow().setAttributes(layoutParams);
|
|
|
|
|
|
|
|
if (DEBUG) Log.d(TAG, "onScroll().brightnessControl, currentBrightness = " + currentProgressPercent);
|
|
|
|
|
|
|
|
final int resId =
|
|
|
|
currentProgressPercent < 0.25 ? R.drawable.ic_brightness_low_white_72dp
|
|
|
|
: currentProgressPercent < 0.75 ? R.drawable.ic_brightness_medium_white_72dp
|
|
|
|
: R.drawable.ic_brightness_high_white_72dp;
|
|
|
|
|
|
|
|
playerImpl.getBrightnessImageView().setImageDrawable(
|
|
|
|
AppCompatResources.getDrawable(getApplicationContext(), resId)
|
|
|
|
);
|
|
|
|
|
|
|
|
if (playerImpl.getBrightnessRelativeLayout().getVisibility() != View.VISIBLE) {
|
|
|
|
animateView(playerImpl.getBrightnessRelativeLayout(), SCALE_AND_ALPHA, true, 200);
|
|
|
|
}
|
|
|
|
if (playerImpl.getVolumeRelativeLayout().getVisibility() == View.VISIBLE) {
|
|
|
|
playerImpl.getVolumeRelativeLayout().setVisibility(View.GONE);
|
|
|
|
}
|
2017-03-27 06:08:16 +02:00
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
private void onScrollEnd() {
|
|
|
|
if (DEBUG) Log.d(TAG, "onScrollEnd() called");
|
2018-08-15 11:02:37 +02:00
|
|
|
|
|
|
|
if (playerImpl.getVolumeRelativeLayout().getVisibility() == View.VISIBLE) {
|
|
|
|
animateView(playerImpl.getVolumeRelativeLayout(), SCALE_AND_ALPHA, false, 200, 200);
|
2018-03-04 05:58:53 +01:00
|
|
|
}
|
2018-08-15 11:02:37 +02:00
|
|
|
if (playerImpl.getBrightnessRelativeLayout().getVisibility() == View.VISIBLE) {
|
|
|
|
animateView(playerImpl.getBrightnessRelativeLayout(), SCALE_AND_ALPHA, false, 200, 200);
|
2018-03-04 05:58:53 +01:00
|
|
|
}
|
2017-03-27 06:08:16 +02:00
|
|
|
|
2018-03-04 05:58:53 +01:00
|
|
|
if (playerImpl.isControlsVisible() && playerImpl.getCurrentState() == STATE_PLAYING) {
|
|
|
|
playerImpl.hideControls(DEFAULT_CONTROLS_DURATION, DEFAULT_CONTROLS_HIDE_TIME);
|
2017-03-27 06:08:16 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public boolean onTouch(View v, MotionEvent event) {
|
2017-04-26 21:32:20 +02:00
|
|
|
//noinspection PointlessBooleanExpression
|
|
|
|
if (DEBUG && false) Log.d(TAG, "onTouch() called with: v = [" + v + "], event = [" + event + "]");
|
2017-03-27 06:08:16 +02:00
|
|
|
gestureDetector.onTouchEvent(event);
|
|
|
|
if (event.getAction() == MotionEvent.ACTION_UP && isMoving) {
|
|
|
|
isMoving = false;
|
|
|
|
onScrollEnd();
|
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2017-03-09 05:44:00 +01:00
|
|
|
}
|
2017-11-09 11:29:02 +01:00
|
|
|
}
|