diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/DownloaderImpl.java b/app/src/braveLegacy/java/org/schabi/newpipe/DownloaderImpl.java index 946d0494d..29c5cef4e 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/DownloaderImpl.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/DownloaderImpl.java @@ -153,7 +153,7 @@ public final class DownloaderImpl extends Downloader { RequestBody requestBody = null; if (dataToSend != null) { - requestBody = RequestBody.create(dataToSend); + requestBody = RequestBody.create(null, dataToSend); } final okhttp3.Request.Builder requestBuilder = new okhttp3.Request.Builder() diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/ExitActivity.java b/app/src/braveLegacy/java/org/schabi/newpipe/ExitActivity.java index bd1351f0c..8da22db2d 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/ExitActivity.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/ExitActivity.java @@ -3,6 +3,7 @@ package org.schabi.newpipe; import android.annotation.SuppressLint; import android.app.Activity; import android.content.Intent; +import android.os.Build; import android.os.Bundle; import org.schabi.newpipe.util.NavigationHelper; @@ -43,7 +44,11 @@ public class ExitActivity extends Activity { protected void onCreate(final Bundle savedInstanceState) { super.onCreate(savedInstanceState); - finishAndRemoveTask(); + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + finishAndRemoveTask(); + } else { + finish(); + } NavigationHelper.restartApp(this); } diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/MainActivity.java b/app/src/braveLegacy/java/org/schabi/newpipe/MainActivity.java index ea047ce61..edf1d2bf0 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/MainActivity.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/MainActivity.java @@ -28,6 +28,7 @@ import android.content.Intent; import android.content.IntentFilter; import android.content.SharedPreferences; import android.content.pm.PackageManager; +import android.os.Build; import android.os.Bundle; import android.os.Handler; import android.os.Looper; @@ -85,6 +86,7 @@ import org.schabi.newpipe.util.PermissionHelper; import org.schabi.newpipe.util.SerializedCache; import org.schabi.newpipe.util.ServiceHelper; import org.schabi.newpipe.util.StateSaver; +import org.schabi.newpipe.util.BraveTLSSocketFactory; import org.schabi.newpipe.util.ThemeHelper; import org.schabi.newpipe.views.FocusOverlayView; @@ -129,6 +131,11 @@ public class MainActivity extends AppCompatActivity { + "savedInstanceState = [" + savedInstanceState + "]"); } + // enable TLS1.1/1.2 for kitkat devices, to fix download and play for media.ccc.de sources + if (Build.VERSION.SDK_INT == Build.VERSION_CODES.KITKAT) { + BraveTLSSocketFactory.setAsDefault(); + } + ThemeHelper.setDayNightMode(this); ThemeHelper.setTheme(this, ServiceHelper.getSelectedServiceId(this)); diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/PanicResponderActivity.java b/app/src/braveLegacy/java/org/schabi/newpipe/PanicResponderActivity.java index f0d1af81a..b4fbdfb28 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/PanicResponderActivity.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/PanicResponderActivity.java @@ -3,6 +3,7 @@ package org.schabi.newpipe; import android.annotation.SuppressLint; import android.app.Activity; import android.content.Intent; +import android.os.Build; import android.os.Bundle; /* @@ -39,6 +40,10 @@ public class PanicResponderActivity extends Activity { ExitActivity.exitAndRemoveFromRecentApps(this); } - finishAndRemoveTask(); + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + finishAndRemoveTask(); + } else { + finish(); + } } } diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/error/ReCaptchaActivity.java b/app/src/braveLegacy/java/org/schabi/newpipe/error/ReCaptchaActivity.java index 3c14cfe4c..ac1f34e3d 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/error/ReCaptchaActivity.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/error/ReCaptchaActivity.java @@ -3,6 +3,7 @@ package org.schabi.newpipe.error; import android.annotation.SuppressLint; import android.content.Intent; import android.content.SharedPreferences; +import android.os.Build; import android.os.Bundle; import android.util.Log; import android.view.Menu; @@ -108,7 +109,12 @@ public class ReCaptchaActivity extends AppCompatActivity { // cleaning cache, history and cookies from webView recaptchaBinding.reCaptchaWebView.clearCache(true); recaptchaBinding.reCaptchaWebView.clearHistory(); - CookieManager.getInstance().removeAllCookies(null); + final CookieManager cookieManager = CookieManager.getInstance(); + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + cookieManager.removeAllCookies(value -> { }); + } else { + cookieManager.removeAllCookie(); + } recaptchaBinding.reCaptchaWebView.loadUrl(url); } diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java b/app/src/braveLegacy/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java index a7cb2a516..66fdff13b 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/fragments/detail/VideoDetailFragment.java @@ -1884,7 +1884,13 @@ public final class VideoDetailFragment } scrollToTop(); - tryAddVideoPlayerView(); + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + tryAddVideoPlayerView(); + } else { + // KitKat needs a delay before addVideoPlayerView call or it reports wrong height in + // activity.getWindow().getDecorView().getHeight() + new Handler().post(this::tryAddVideoPlayerView); + } } @Override @@ -1947,8 +1953,10 @@ public final class VideoDetailFragment } activity.getWindow().getDecorView().setSystemUiVisibility(0); activity.getWindow().clearFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN); - activity.getWindow().setStatusBarColor(ThemeHelper.resolveColorFromAttr( - requireContext(), android.R.attr.colorPrimary)); + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + activity.getWindow().setStatusBarColor(ThemeHelper.resolveColorFromAttr( + requireContext(), android.R.attr.colorPrimary)); + } } private void hideSystemUi() { @@ -1979,7 +1987,8 @@ public final class VideoDetailFragment } activity.getWindow().getDecorView().setSystemUiVisibility(visibility); - if (isInMultiWindow || isFullscreen()) { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP + && (isInMultiWindow || isFullscreen())) { activity.getWindow().setStatusBarColor(Color.TRANSPARENT); activity.getWindow().setNavigationBarColor(Color.TRANSPARENT); } diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/fragments/list/search/SearchFragment.java b/app/src/braveLegacy/java/org/schabi/newpipe/fragments/list/search/SearchFragment.java index 09c852763..595e9cc4e 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/fragments/list/search/SearchFragment.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/fragments/list/search/SearchFragment.java @@ -507,6 +507,9 @@ public class SearchFragment extends BaseListFragment content + val contrastColor = AppCompatResources.getColorStateList(requireContext(), R.color.contrastColor) + searchLayoutBinding.toolbarSearchEditText.setTextColor(contrastColor) + searchLayoutBinding.toolbarSearchEditText.setHintTextColor(contrastColor.withAlpha(128)) + ImageViewCompat.setImageTintList(searchLayoutBinding.toolbarSearchClearIcon, contrastColor) + } + viewModel = ViewModelProvider( this, FeedGroupDialogViewModel.getFactory( diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/player/ui/MainPlayerUi.java b/app/src/braveLegacy/java/org/schabi/newpipe/player/ui/MainPlayerUi.java index 73da0f55d..7143dbced 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/player/ui/MainPlayerUi.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/player/ui/MainPlayerUi.java @@ -22,6 +22,7 @@ import android.content.res.Resources; import android.database.ContentObserver; import android.graphics.Bitmap; import android.graphics.Color; +import android.os.Build; import android.os.Handler; import android.os.Looper; import android.provider.Settings; @@ -449,8 +450,10 @@ public final class MainPlayerUi extends VideoPlayerUi implements View.OnLayoutCh public void showSystemUIPartially() { if (isFullscreen) { getParentActivity().map(Activity::getWindow).ifPresent(window -> { - window.setStatusBarColor(Color.TRANSPARENT); - window.setNavigationBarColor(Color.TRANSPARENT); + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + window.setStatusBarColor(Color.TRANSPARENT); + window.setNavigationBarColor(Color.TRANSPARENT); + } final int visibility = View.SYSTEM_UI_FLAG_LAYOUT_STABLE | View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION; diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/settings/DownloadSettingsFragment.java b/app/src/braveLegacy/java/org/schabi/newpipe/settings/DownloadSettingsFragment.java index 472db6afe..fc8783b8c 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/settings/DownloadSettingsFragment.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/settings/DownloadSettingsFragment.java @@ -65,10 +65,16 @@ public class DownloadSettingsFragment extends BasePreferenceFragment { prefStorageAsk = findPreference(downloadStorageAsk); final SwitchPreferenceCompat prefUseSaf = findPreference(storageUseSafPreference); + prefUseSaf.setDefaultValue(Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP); prefUseSaf.setChecked(NewPipeSettings.useStorageAccessFramework(ctx)); - if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q + || Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) { prefUseSaf.setEnabled(false); - prefUseSaf.setSummary(R.string.downloads_storage_use_saf_summary_api_29); + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) { + prefUseSaf.setSummary(R.string.downloads_storage_use_saf_summary_api_29); + } else { + prefUseSaf.setSummary(R.string.downloads_storage_use_saf_summary_api_19); + } prefStorageAsk.setSummary(R.string.downloads_storage_ask_summary_no_saf_notice); } @@ -246,7 +252,8 @@ public class DownloadSettingsFragment extends BasePreferenceFragment { forgetSAFTree(context, defaultPreferences.getString(key, "")); - if (!FilePickerActivityHelper.isOwnFileUri(context, uri)) { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP + && !FilePickerActivityHelper.isOwnFileUri(context, uri)) { // steps to acquire the selected path: // 1. acquire permissions on the new save path // 2. save the new path, if step(2) was successful diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/settings/NewPipeSettings.java b/app/src/braveLegacy/java/org/schabi/newpipe/settings/NewPipeSettings.java index 4d8560a59..bce64474e 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/settings/NewPipeSettings.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/settings/NewPipeSettings.java @@ -109,7 +109,7 @@ public final class NewPipeSettings { public static boolean useStorageAccessFramework(final Context context) { // There's a FireOS bug which prevents SAF open/close dialogs from being confirmed with a // remote (see #6455). - if (DeviceUtils.isFireTv()) { + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP || DeviceUtils.isFireTv()) { return false; } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) { return true; diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/settings/NotificationSettingsFragment.kt b/app/src/braveLegacy/java/org/schabi/newpipe/settings/NotificationSettingsFragment.kt index 11eb4fa33..6bea8b69e 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/settings/NotificationSettingsFragment.kt +++ b/app/src/braveLegacy/java/org/schabi/newpipe/settings/NotificationSettingsFragment.kt @@ -1,9 +1,19 @@ package org.schabi.newpipe.settings +import android.os.Build import android.os.Bundle +import androidx.preference.Preference +import org.schabi.newpipe.R class NotificationSettingsFragment : BasePreferenceFragment() { override fun onCreatePreferences(savedInstanceState: Bundle?, rootKey: String?) { addPreferencesFromResourceRegistry() + + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) { + val colorizePref: Preference? = findPreference(getString(R.string.notification_colorize_key)) + colorizePref?.let { + preferenceScreen.removePreference(it) + } + } } } diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/settings/SettingMigrations.java b/app/src/braveLegacy/java/org/schabi/newpipe/settings/SettingMigrations.java index b7bafde75..4ae700dff 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/settings/SettingMigrations.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/settings/SettingMigrations.java @@ -2,6 +2,7 @@ package org.schabi.newpipe.settings; import android.content.Context; import android.content.SharedPreferences; +import android.os.Build; import android.util.Log; import androidx.annotation.NonNull; @@ -71,12 +72,12 @@ public final class SettingMigrations { // and standard way to access folders and files to be used consistently everywhere. // We reset the setting to its default value, i.e. "use SAF", since now there are no // more issues with SAF and users should use that one instead of the old - // NoNonsenseFilePicker. Also, there's a bug on FireOS in which SAF open/close + // NoNonsenseFilePicker. SAF does not work on KitKat and below, though, so the setting + // is set to false in that case. Also, there's a bug on FireOS in which SAF open/close // dialogs cannot be confirmed with a remote (see #6455). - sp.edit().putBoolean( - context.getString(R.string.storage_use_saf), - !DeviceUtils.isFireTv() - ).apply(); + sp.edit().putBoolean(context.getString(R.string.storage_use_saf), + Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP + && !DeviceUtils.isFireTv()).apply(); } }; diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/settings/preferencesearch/PreferenceSearchResultHighlighter.java b/app/src/braveLegacy/java/org/schabi/newpipe/settings/preferencesearch/PreferenceSearchResultHighlighter.java index 7eae5c128..418a3ea46 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/settings/preferencesearch/PreferenceSearchResultHighlighter.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/settings/preferencesearch/PreferenceSearchResultHighlighter.java @@ -6,6 +6,7 @@ import android.graphics.PorterDuff; import android.graphics.PorterDuffColorFilter; import android.graphics.drawable.Drawable; import android.graphics.drawable.RippleDrawable; +import android.os.Build; import android.os.Handler; import android.os.Looper; import android.util.Log; @@ -64,7 +65,8 @@ public final class PreferenceSearchResultHighlighter { recyclerView.findViewHolderForAdapterPosition(position); if (holder != null) { final Drawable background = holder.itemView.getBackground(); - if (background instanceof RippleDrawable) { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP + && background instanceof RippleDrawable) { showRippleAnimation((RippleDrawable) background); return; } diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/streams/io/StoredDirectoryHelper.java b/app/src/braveLegacy/java/org/schabi/newpipe/streams/io/StoredDirectoryHelper.java index 74fc74c76..80b675ee1 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/streams/io/StoredDirectoryHelper.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/streams/io/StoredDirectoryHelper.java @@ -5,6 +5,7 @@ import android.content.Context; import android.content.Intent; import android.database.Cursor; import android.net.Uri; +import android.os.Build; import android.provider.DocumentsContract; import android.util.Log; @@ -59,6 +60,10 @@ public class StoredDirectoryHelper { throw new IOException(e); } + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) { + throw new IOException("Storage Access Framework with Directory API is not available"); + } + this.docTree = DocumentFile.fromTreeUri(context, path); if (this.docTree == null) { @@ -75,7 +80,7 @@ public class StoredDirectoryHelper { final String[] filename = splitFilename(name); final String lcFileName = filename[0].toLowerCase(); - if (docTree == null) { + if (docTree == null || Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) { try (Stream stream = Files.list(ioTree)) { matches.addAll(stream.map(path -> path.getFileName().toString().toLowerCase()) .filter(fileName -> fileName.startsWith(lcFileName)) @@ -294,7 +299,7 @@ public class StoredDirectoryHelper { */ static DocumentFile findFileSAFHelper(@Nullable final Context context, final DocumentFile tree, final String filename) { - if (context == null) { + if (context == null || Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) { return tree.findFile(filename); // warning: this is very slow } diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/streams/io/StoredFileHelper.java b/app/src/braveLegacy/java/org/schabi/newpipe/streams/io/StoredFileHelper.java index 5404426c4..ad528c765 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/streams/io/StoredFileHelper.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/streams/io/StoredFileHelper.java @@ -1,5 +1,6 @@ package org.schabi.newpipe.streams.io; +import android.annotation.TargetApi; import android.content.ContentResolver; import android.content.Context; import android.content.Intent; @@ -77,6 +78,7 @@ public class StoredFileHelper implements Serializable { this.tag = tag; } + @TargetApi(Build.VERSION_CODES.LOLLIPOP) StoredFileHelper(@Nullable final Context context, final DocumentFile tree, final String filename, final String mime, final boolean safe) throws IOException { @@ -118,6 +120,7 @@ public class StoredFileHelper implements Serializable { srcType = mime; } + @TargetApi(Build.VERSION_CODES.KITKAT) public StoredFileHelper(final Context context, @Nullable final Uri parent, @NonNull final Uri path, final String tag) throws IOException { this.tag = tag; diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/util/DeviceUtils.java b/app/src/braveLegacy/java/org/schabi/newpipe/util/DeviceUtils.java index e9678c2b0..658e43885 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/util/DeviceUtils.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/util/DeviceUtils.java @@ -145,7 +145,7 @@ public final class DeviceUtils { boolean isTv = ContextCompat.getSystemService(context, UiModeManager.class) .getCurrentModeType() == Configuration.UI_MODE_TYPE_TELEVISION || isFireTv() - || pm.hasSystemFeature(PackageManager.FEATURE_LEANBACK); + || pm.hasSystemFeature(PackageManager.FEATURE_TELEVISION); // from https://stackoverflow.com/a/58932366 if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { @@ -157,6 +157,10 @@ public final class DeviceUtils { && pm.hasSystemFeature(PackageManager.FEATURE_ETHERNET)); } + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + isTv = isTv || pm.hasSystemFeature(PackageManager.FEATURE_LEANBACK); + } + DeviceUtils.isTV = isTv; return DeviceUtils.isTV; } @@ -319,11 +323,12 @@ public final class DeviceUtils { * #9023 for more info.

* @Note Update {@link #MEDIA_TUNNELING_DEVICE_BLACKLIST_VERSION} * when adding a new device to the method. - * @return {@code false} if affected device; {@code true} otherwise + * @return {@code false} if Kitkat (does not support tunneling) or affected device */ public static boolean shouldSupportMediaTunneling() { // Maintainers note: update MEDIA_TUNNELING_DEVICES_UPDATE_APP_VERSION_CODE - return !HI3798MV200 + return Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP + && !HI3798MV200 && !CVT_MT5886_EU_1G && !REALTEKATV && !QM16XE_U diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/util/PermissionHelper.java b/app/src/braveLegacy/java/org/schabi/newpipe/util/PermissionHelper.java index 55193599e..08ae6adbb 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/util/PermissionHelper.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/util/PermissionHelper.java @@ -36,6 +36,7 @@ public final class PermissionHelper { return checkWriteStoragePermissions(activity, requestCode); } + @RequiresApi(api = Build.VERSION_CODES.JELLY_BEAN) public static boolean checkReadStoragePermissions(final Activity activity, final int requestCode) { if (ContextCompat.checkSelfPermission(activity, Manifest.permission.READ_EXTERNAL_STORAGE) diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/util/external_communication/ShareUtils.java b/app/src/braveLegacy/java/org/schabi/newpipe/util/external_communication/ShareUtils.java index 7524e5413..6ea5a1074 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/util/external_communication/ShareUtils.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/util/external_communication/ShareUtils.java @@ -191,10 +191,17 @@ public final class ShareUtils { } // Migrate any clip data and flags from the original intent. - final int permFlags = intent.getFlags() & (Intent.FLAG_GRANT_READ_URI_PERMISSION - | Intent.FLAG_GRANT_WRITE_URI_PERMISSION - | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION - | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); + final int permFlags; + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + permFlags = intent.getFlags() & (Intent.FLAG_GRANT_READ_URI_PERMISSION + | Intent.FLAG_GRANT_WRITE_URI_PERMISSION + | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION + | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); + } else { + permFlags = intent.getFlags() & (Intent.FLAG_GRANT_READ_URI_PERMISSION + | Intent.FLAG_GRANT_WRITE_URI_PERMISSION + | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); + } if (permFlags != 0) { ClipData targetClipData = intent.getClipData(); if (targetClipData == null && intent.getData() != null) { diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/views/CollapsibleView.java b/app/src/braveLegacy/java/org/schabi/newpipe/views/CollapsibleView.java index f79e1e3a3..e1ada4f9b 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/views/CollapsibleView.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/views/CollapsibleView.java @@ -21,6 +21,7 @@ package org.schabi.newpipe.views; import android.animation.ValueAnimator; import android.content.Context; +import android.os.Build; import android.os.Parcelable; import android.util.AttributeSet; import android.util.Log; @@ -28,6 +29,7 @@ import android.widget.LinearLayout; import androidx.annotation.IntDef; import androidx.annotation.Nullable; +import androidx.annotation.RequiresApi; import org.schabi.newpipe.ktx.ViewUtils; @@ -74,6 +76,7 @@ public class CollapsibleView extends LinearLayout { super(context, attrs, defStyleAttr); } + @RequiresApi(api = Build.VERSION_CODES.LOLLIPOP) public CollapsibleView(final Context context, final AttributeSet attrs, final int defStyleAttr, final int defStyleRes) { super(context, attrs, defStyleAttr, defStyleRes); diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/views/ExpandableSurfaceView.java b/app/src/braveLegacy/java/org/schabi/newpipe/views/ExpandableSurfaceView.java index 175c81e46..cfa17e20c 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/views/ExpandableSurfaceView.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/views/ExpandableSurfaceView.java @@ -1,6 +1,7 @@ package org.schabi.newpipe.views; import android.content.Context; +import android.os.Build; import android.util.AttributeSet; import android.view.SurfaceView; @@ -44,7 +45,10 @@ public class ExpandableSurfaceView extends SurfaceView { scaleX = 1.0f; scaleY = 1.0f; - if (resizeMode == RESIZE_MODE_FIT) { + if (resizeMode == RESIZE_MODE_FIT + // KitKat doesn't work well when a view has a scale like needed for ZOOM + || (resizeMode == RESIZE_MODE_ZOOM + && Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP)) { if (aspectDeformation > 0) { height = (int) (width / videoAspectRatio); } else { diff --git a/app/src/braveLegacy/java/org/schabi/newpipe/views/FocusAwareCoordinator.java b/app/src/braveLegacy/java/org/schabi/newpipe/views/FocusAwareCoordinator.java index d4fafc31a..e4acb00b7 100644 --- a/app/src/braveLegacy/java/org/schabi/newpipe/views/FocusAwareCoordinator.java +++ b/app/src/braveLegacy/java/org/schabi/newpipe/views/FocusAwareCoordinator.java @@ -17,8 +17,10 @@ */ package org.schabi.newpipe.views; +import android.annotation.TargetApi; import android.content.Context; import android.graphics.Rect; +import android.os.Build; import android.util.AttributeSet; import android.view.View; import android.view.ViewGroup; @@ -73,6 +75,7 @@ public final class FocusAwareCoordinator extends CoordinatorLayout { * Makes possible for multiple fragments to co-exist. Without this code * the first ViewGroup who consumes will be the last who receive the insets */ + @TargetApi(Build.VERSION_CODES.LOLLIPOP) @Override public WindowInsets dispatchApplyWindowInsets(final WindowInsets insets) { boolean consumed = false; diff --git a/app/src/braveLegacy/java/us/shandian/giga/get/DownloadMission.java b/app/src/braveLegacy/java/us/shandian/giga/get/DownloadMission.java index 4661e1ce0..f5b76887a 100644 --- a/app/src/braveLegacy/java/us/shandian/giga/get/DownloadMission.java +++ b/app/src/braveLegacy/java/us/shandian/giga/get/DownloadMission.java @@ -1,5 +1,6 @@ package us.shandian.giga.get; +import android.os.Build; import android.os.Handler; import android.system.ErrnoException; import android.system.OsConstants; @@ -316,14 +317,16 @@ public class DownloadMission extends Mission { public synchronized void notifyError(int code, Exception err) { Log.e(TAG, "notifyError() code = " + code, err); - if (err != null && err.getCause() instanceof ErrnoException) { - int errno = ((ErrnoException) err.getCause()).errno; - if (errno == OsConstants.ENOSPC) { - code = ERROR_INSUFFICIENT_STORAGE; - err = null; - } else if (errno == OsConstants.EACCES) { - code = ERROR_PERMISSION_DENIED; - err = null; + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + if (err != null && err.getCause() instanceof ErrnoException) { + int errno = ((ErrnoException) err.getCause()).errno; + if (errno == OsConstants.ENOSPC) { + code = ERROR_INSUFFICIENT_STORAGE; + err = null; + } else if (errno == OsConstants.EACCES) { + code = ERROR_PERMISSION_DENIED; + err = null; + } } } diff --git a/app/src/braveLegacy/java/us/shandian/giga/service/DownloadManagerService.java b/app/src/braveLegacy/java/us/shandian/giga/service/DownloadManagerService.java index dbef73f70..99d8af1ae 100755 --- a/app/src/braveLegacy/java/us/shandian/giga/service/DownloadManagerService.java +++ b/app/src/braveLegacy/java/us/shandian/giga/service/DownloadManagerService.java @@ -7,8 +7,10 @@ import android.app.Notification; import android.app.NotificationManager; import android.app.PendingIntent; import android.app.Service; +import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; +import android.content.IntentFilter; import android.content.SharedPreferences; import android.content.SharedPreferences.OnSharedPreferenceChangeListener; import android.graphics.Bitmap; @@ -19,6 +21,7 @@ import android.net.NetworkInfo; import android.net.NetworkRequest; import android.net.Uri; import android.os.Binder; +import android.os.Build; import android.os.Handler; import android.os.Handler.Callback; import android.os.IBinder; @@ -103,6 +106,7 @@ public class DownloadManagerService extends Service { private final List mEchoObservers = new ArrayList<>(1); private ConnectivityManager mConnectivityManager; + private BroadcastReceiver mNetworkStateListener = null; private ConnectivityManager.NetworkCallback mNetworkStateListenerL = null; private SharedPreferences mPrefs = null; @@ -169,18 +173,28 @@ public class DownloadManagerService extends Service { mConnectivityManager = ContextCompat.getSystemService(this, ConnectivityManager.class); - mNetworkStateListenerL = new ConnectivityManager.NetworkCallback() { - @Override - public void onAvailable(Network network) { - handleConnectivityState(false); - } + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + mNetworkStateListenerL = new ConnectivityManager.NetworkCallback() { + @Override + public void onAvailable(Network network) { + handleConnectivityState(false); + } - @Override - public void onLost(Network network) { - handleConnectivityState(false); - } - }; - mConnectivityManager.registerNetworkCallback(new NetworkRequest.Builder().build(), mNetworkStateListenerL); + @Override + public void onLost(Network network) { + handleConnectivityState(false); + } + }; + mConnectivityManager.registerNetworkCallback(new NetworkRequest.Builder().build(), mNetworkStateListenerL); + } else { + mNetworkStateListener = new BroadcastReceiver() { + @Override + public void onReceive(Context context, Intent intent) { + handleConnectivityState(false); + } + }; + registerReceiver(mNetworkStateListener, new IntentFilter(ConnectivityManager.CONNECTIVITY_ACTION)); + } mPrefs.registerOnSharedPreferenceChangeListener(mPrefChangeListener); @@ -239,7 +253,10 @@ public class DownloadManagerService extends Service { manageLock(false); - mConnectivityManager.unregisterNetworkCallback(mNetworkStateListenerL); + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) + mConnectivityManager.unregisterNetworkCallback(mNetworkStateListenerL); + else + unregisterReceiver(mNetworkStateListener); mPrefs.unregisterOnSharedPreferenceChangeListener(mPrefChangeListener); @@ -253,6 +270,21 @@ public class DownloadManagerService extends Service { @Override public IBinder onBind(Intent intent) { + /* + int permissionCheck; + if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN) { + permissionCheck = PermissionChecker.checkSelfPermission(this, Manifest.permission.READ_EXTERNAL_STORAGE); + if (permissionCheck == PermissionChecker.PERMISSION_DENIED) { + Toast.makeText(this, "Permission denied (read)", Toast.LENGTH_SHORT).show(); + } + } + + permissionCheck = PermissionChecker.checkSelfPermission(this, Manifest.permission.WRITE_EXTERNAL_STORAGE); + if (permissionCheck == PermissionChecker.PERMISSION_DENIED) { + Toast.makeText(this, "Permission denied (write)", Toast.LENGTH_SHORT).show(); + } + */ + return mBinder; } @@ -470,7 +502,12 @@ public class DownloadManagerService extends Service { if (downloadDoneCount == 1) { downloadDoneList.append(name); - downloadDoneNotification.setContentTitle(null); + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) { + downloadDoneNotification.setContentTitle(getString(R.string.app_name)); + } else { + downloadDoneNotification.setContentTitle(null); + } + downloadDoneNotification.setContentText(Localization.downloadCount(this, downloadDoneCount)); downloadDoneNotification.setStyle(new NotificationCompat.BigTextStyle() .setBigContentTitle(Localization.downloadCount(this, downloadDoneCount)) @@ -503,10 +540,16 @@ public class DownloadManagerService extends Service { .setContentIntent(mOpenDownloadList); } - downloadFailedNotification.setContentTitle(getString(R.string.download_failed)); - downloadFailedNotification.setContentText(mission.storage.getName()); - downloadFailedNotification.setStyle(new NotificationCompat.BigTextStyle() - .bigText(mission.storage.getName())); + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) { + downloadFailedNotification.setContentTitle(getString(R.string.app_name)); + downloadFailedNotification.setStyle(new NotificationCompat.BigTextStyle() + .bigText(getString(R.string.download_failed).concat(": ").concat(mission.storage.getName()))); + } else { + downloadFailedNotification.setContentTitle(getString(R.string.download_failed)); + downloadFailedNotification.setContentText(mission.storage.getName()); + downloadFailedNotification.setStyle(new NotificationCompat.BigTextStyle() + .bigText(mission.storage.getName())); + } mNotificationManager.notify(id, downloadFailedNotification.build()); } @@ -543,7 +586,12 @@ public class DownloadManagerService extends Service { if (path.charAt(0) == File.separatorChar) { Log.i(TAG, "Old save path style present: " + path); - path = ""; + + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) + path = Uri.fromFile(new File(path)).toString(); + else + path = ""; + mPrefs.edit().putString(getString(prefKey), "").apply(); } diff --git a/app/src/braveLegacy/java/us/shandian/giga/ui/adapter/MissionAdapter.java b/app/src/braveLegacy/java/us/shandian/giga/ui/adapter/MissionAdapter.java index 90c29d673..6ce6c96ea 100644 --- a/app/src/braveLegacy/java/us/shandian/giga/ui/adapter/MissionAdapter.java +++ b/app/src/braveLegacy/java/us/shandian/giga/ui/adapter/MissionAdapter.java @@ -370,7 +370,11 @@ public class MissionAdapter extends Adapter implements Handler.Callb Intent intent = new Intent(Intent.ACTION_VIEW); intent.setDataAndType(resolveShareableUri(mission), mimeType); intent.addFlags(FLAG_GRANT_READ_URI_PERMISSION); - intent.addFlags(FLAG_GRANT_PREFIX_URI_PERMISSION); + + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + intent.addFlags(FLAG_GRANT_PREFIX_URI_PERMISSION); + } + ShareUtils.openIntentInApp(mContext, intent); }