From e22d9bba5e9a78eeef958ea4881ccbbb16e870e6 Mon Sep 17 00:00:00 2001
From: InfinityLoop1308 <96324692+InfinityLoop1308@users.noreply.github.com>
Date: Sat, 20 Jun 2026 16:37:40 +0800
Subject: [PATCH 1/5] Revert "fix: navigation bar is not configured to
contrast"
---
app/src/main/res/values-v29/styles.xml | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/app/src/main/res/values-v29/styles.xml b/app/src/main/res/values-v29/styles.xml
index 89d423d5d..24ebf5d2b 100644
--- a/app/src/main/res/values-v29/styles.xml
+++ b/app/src/main/res/values-v29/styles.xml
@@ -3,7 +3,7 @@
From f4a3dc34502fb6df5eda251115797f1fe6061c55 Mon Sep 17 00:00:00 2001
From: InfinityLoop1308 <96324692+InfinityLoop1308@users.noreply.github.com>
Date: Sat, 20 Jun 2026 16:37:40 +0800
Subject: [PATCH 2/5] Revert "fix(ui): keep the mini player above the
navigation bar in edge-to-edge (#53)"
---
.../java/org/schabi/newpipe/MainActivity.java | 3 ---
.../org/schabi/newpipe/about/AboutActivity.kt | 2 --
.../schabi/newpipe/about/LicenseFragment.kt | 3 ---
.../newpipe/download/DownloadActivity.java | 2 --
.../schabi/newpipe/error/ErrorActivity.java | 2 --
.../newpipe/error/ReCaptchaActivity.java | 2 --
.../schabi/newpipe/fragments/MainFragment.java | 16 ++++++++++++++++
.../fragments/detail/VideoDetailFragment.java | 15 +++++++++++++++
.../settings/BaseFilterListActivity.java | 2 --
.../newpipe/settings/SettingsActivity.java | 3 ---
.../newpipe/util/WindowInsetsHelper.java | 18 ------------------
.../views/BaseLoginWebViewActivity.java | 3 ---
app/src/main/res/layout/activity_main.xml | 1 -
13 files changed, 31 insertions(+), 41 deletions(-)
diff --git a/app/src/main/java/org/schabi/newpipe/MainActivity.java b/app/src/main/java/org/schabi/newpipe/MainActivity.java
index 3894c1fab..0586fed66 100644
--- a/app/src/main/java/org/schabi/newpipe/MainActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/MainActivity.java
@@ -154,9 +154,6 @@ protected void onCreate(final Bundle savedInstanceState) {
WindowInsetsHelper.applyStatusBarInsets(this, toolbarLayoutBinding.toolbar,
mainBinding.fragmentHolder);
- // Edge-to-edge (targetSdk 35+): keep the main content (feed/search/channel/playlist lists,
- // and the bottom tab strip) above the system navigation bar.
- WindowInsetsHelper.applyNavigationBarInsets(mainBinding.fragmentHolder);
if (getSupportFragmentManager().getBackStackEntryCount() == 0) {
initFragments();
diff --git a/app/src/main/java/org/schabi/newpipe/about/AboutActivity.kt b/app/src/main/java/org/schabi/newpipe/about/AboutActivity.kt
index 76f18d2ed..4abab8570 100644
--- a/app/src/main/java/org/schabi/newpipe/about/AboutActivity.kt
+++ b/app/src/main/java/org/schabi/newpipe/about/AboutActivity.kt
@@ -79,8 +79,6 @@ class AboutActivity : AppCompatActivity() {
aboutAppVersion.text = BuildConfig.VERSION_NAME
aboutGithubLink.openLink(R.string.github_url)
aboutDonationLink.openLink(R.string.donation_url)
- // Edge-to-edge (targetSdk 35+): keep the bottom of the page above the nav bar.
- WindowInsetsHelper.applyNavigationBarInsets(root)
return root
}
}
diff --git a/app/src/main/java/org/schabi/newpipe/about/LicenseFragment.kt b/app/src/main/java/org/schabi/newpipe/about/LicenseFragment.kt
index e1820c9a6..c816d78be 100644
--- a/app/src/main/java/org/schabi/newpipe/about/LicenseFragment.kt
+++ b/app/src/main/java/org/schabi/newpipe/about/LicenseFragment.kt
@@ -11,7 +11,6 @@ import org.schabi.newpipe.R
import org.schabi.newpipe.about.LicenseFragmentHelper.showLicense
import org.schabi.newpipe.databinding.FragmentLicensesBinding
import org.schabi.newpipe.databinding.ItemSoftwareComponentBinding
-import org.schabi.newpipe.util.WindowInsetsHelper
/**
* Fragment containing the software licenses.
@@ -68,8 +67,6 @@ class LicenseFragment : Fragment() {
registerForContextMenu(root)
}
activeLicense?.let { compositeDisposable.add(showLicense(activity, it)) }
- // Edge-to-edge (targetSdk 35+): keep the bottom of the licenses list above the nav bar.
- WindowInsetsHelper.applyNavigationBarInsets(binding.root)
return binding.root
}
diff --git a/app/src/main/java/org/schabi/newpipe/download/DownloadActivity.java b/app/src/main/java/org/schabi/newpipe/download/DownloadActivity.java
index 75dcc42bc..61bc32061 100644
--- a/app/src/main/java/org/schabi/newpipe/download/DownloadActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/download/DownloadActivity.java
@@ -47,8 +47,6 @@ protected void onCreate(final Bundle savedInstanceState) {
setSupportActionBar(downloaderBinding.toolbarLayout.toolbar);
WindowInsetsHelper.applyStatusBarInsets(this, downloaderBinding.toolbarLayout.toolbar);
- // Edge-to-edge (targetSdk 35+): keep the bottom of the downloads list above the nav bar.
- WindowInsetsHelper.applyNavigationBarInsets(downloaderBinding.frame);
final ActionBar actionBar = getSupportActionBar();
if (actionBar != null) {
diff --git a/app/src/main/java/org/schabi/newpipe/error/ErrorActivity.java b/app/src/main/java/org/schabi/newpipe/error/ErrorActivity.java
index 00eb37391..db1e21769 100644
--- a/app/src/main/java/org/schabi/newpipe/error/ErrorActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/error/ErrorActivity.java
@@ -108,8 +108,6 @@ protected void onCreate(final Bundle savedInstanceState) {
WindowInsetsHelper.applyStatusBarInsets(this,
activityErrorBinding.toolbarLayout.toolbar,
activityErrorBinding.scrollView);
- // Edge-to-edge (targetSdk 35+): keep the bottom of a long error report above the nav bar.
- WindowInsetsHelper.applyNavigationBarInsets(activityErrorBinding.scrollView);
final ActionBar actionBar = getSupportActionBar();
if (actionBar != null) {
diff --git a/app/src/main/java/org/schabi/newpipe/error/ReCaptchaActivity.java b/app/src/main/java/org/schabi/newpipe/error/ReCaptchaActivity.java
index 490d09b89..753bcfdb5 100644
--- a/app/src/main/java/org/schabi/newpipe/error/ReCaptchaActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/error/ReCaptchaActivity.java
@@ -81,8 +81,6 @@ protected void onCreate(final Bundle savedInstanceState) {
WindowInsetsHelper.applyStatusBarInsets(this, recaptchaBinding.toolbar,
recaptchaBinding.reCaptchaWebView);
- // Edge-to-edge (targetSdk 35+): keep the captcha web view content above the nav bar.
- WindowInsetsHelper.applyNavigationBarInsets(recaptchaBinding.reCaptchaWebView);
final String url = sanitizeRecaptchaUrl(getIntent().getStringExtra(RECAPTCHA_URL_EXTRA));
// set return to Cancel by default
diff --git a/app/src/main/java/org/schabi/newpipe/fragments/MainFragment.java b/app/src/main/java/org/schabi/newpipe/fragments/MainFragment.java
index e37086888..5f10b4182 100644
--- a/app/src/main/java/org/schabi/newpipe/fragments/MainFragment.java
+++ b/app/src/main/java/org/schabi/newpipe/fragments/MainFragment.java
@@ -24,6 +24,8 @@
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.appcompat.app.ActionBar;
+import androidx.core.view.ViewCompat;
+import androidx.core.view.WindowInsetsCompat;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentManager;
import androidx.fragment.app.FragmentStatePagerAdapterMenuWorkaround;
@@ -105,6 +107,17 @@ protected void initViews(final View rootView, final Bundle savedInstanceState) {
binding.mainTabLayout.setTabRippleColor(binding.mainTabLayout.getTabRippleColor()
.withAlpha(32));
+ // Edge-to-edge (targetSdk 35+): when the tab strip is moved to the bottom it sits behind the
+ // system navigation bar (tabs unclickable). Pad it by the nav-bar inset; the pager is laid
+ // out relative to the tab strip so it follows automatically. requestApplyInsets() in
+ // updateTabLayoutPosition() re-runs this when the user toggles the position.
+ ViewCompat.setOnApplyWindowInsetsListener(binding.mainTabLayout, (v, insets) -> {
+ final int navBottom = mainTabsPositionBottom
+ ? insets.getInsets(WindowInsetsCompat.Type.navigationBars()).bottom : 0;
+ v.setPadding(v.getPaddingLeft(), v.getPaddingTop(), v.getPaddingRight(), navBottom);
+ return insets;
+ });
+
setupTabs();
updateTabLayoutPosition();
}
@@ -235,6 +248,9 @@ private void updateTabLayoutPosition() {
tabLayout.setTabRippleColor(ColorStateList.valueOf(iconColor).withAlpha(32));
tabLayout.setTabIconTint(ColorStateList.valueOf(iconColor));
tabLayout.setSelectedTabIndicatorColor(iconColor);
+
+ // Re-apply the nav-bar inset padding for the new position (added at bottom, cleared at top).
+ ViewCompat.requestApplyInsets(tabLayout);
}
@Override
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 4c444278f..c9ac6aa33 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
@@ -722,6 +722,21 @@ protected void initViews(final View rootView, final Bundle savedInstanceState) {
pageAdapter = new TabAdapter(getChildFragmentManager());
binding.viewPager.setAdapter(pageAdapter);
binding.tabLayout.setupWithViewPager(binding.viewPager);
+ // Edge-to-edge (targetSdk 35+): the bottom tab strip is laid out gravity=bottom, so without
+ // insets it sits behind the system navigation bar (tabs unclickable) and the pager's last
+ // item runs under it. Pad the tab strip by the nav-bar inset and grow the pager's bottom
+ // padding (its XML 48dp tab clearance) by the same amount so content clears both.
+ final int viewPagerBottomBase = binding.viewPager.getPaddingBottom();
+ ViewCompat.setOnApplyWindowInsetsListener(binding.tabLayout, (v, insets) -> {
+ final int navBottom = insets.getInsets(
+ WindowInsetsCompat.Type.navigationBars()).bottom;
+ v.setPadding(v.getPaddingLeft(), v.getPaddingTop(), v.getPaddingRight(), navBottom);
+ binding.viewPager.setPadding(binding.viewPager.getPaddingLeft(),
+ binding.viewPager.getPaddingTop(), binding.viewPager.getPaddingRight(),
+ viewPagerBottomBase + navBottom);
+ return insets;
+ });
+ ViewCompat.requestApplyInsets(binding.tabLayout);
updateStickyPlayerMode();
binding.detailThumbnailRootLayout.requestFocus();
diff --git a/app/src/main/java/org/schabi/newpipe/settings/BaseFilterListActivity.java b/app/src/main/java/org/schabi/newpipe/settings/BaseFilterListActivity.java
index e77493a39..5b08f6d58 100644
--- a/app/src/main/java/org/schabi/newpipe/settings/BaseFilterListActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/settings/BaseFilterListActivity.java
@@ -63,8 +63,6 @@ protected void onCreate(Bundle savedInstanceState) {
recyclerView = findViewById(R.id.filter_list);
recyclerView.setLayoutManager(new LinearLayoutManager(this));
- // Edge-to-edge (targetSdk 35+): keep the bottom of the filter list above the nav bar.
- WindowInsetsHelper.applyNavigationBarInsets(recyclerView);
sharedPreferences = PreferenceManager.getDefaultSharedPreferences(this);
loadFilterItems();
diff --git a/app/src/main/java/org/schabi/newpipe/settings/SettingsActivity.java b/app/src/main/java/org/schabi/newpipe/settings/SettingsActivity.java
index 09b77f444..65f72b66f 100644
--- a/app/src/main/java/org/schabi/newpipe/settings/SettingsActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/settings/SettingsActivity.java
@@ -106,9 +106,6 @@ protected void onCreate(final Bundle savedInstanceBundle) {
WindowInsetsHelper.applyStatusBarInsets(this,
settingsLayoutBinding.settingsToolbarLayout.toolbar,
settingsLayoutBinding.settingsFragmentHolder);
- // Edge-to-edge (targetSdk 35+): keep the last preference entry on long, scrollable
- // settings pages above the system navigation bar.
- WindowInsetsHelper.applyNavigationBarInsets(settingsLayoutBinding.settingsFragmentHolder);
if (restored) {
// Restore state
diff --git a/app/src/main/java/org/schabi/newpipe/util/WindowInsetsHelper.java b/app/src/main/java/org/schabi/newpipe/util/WindowInsetsHelper.java
index c77446f43..18f656b0b 100644
--- a/app/src/main/java/org/schabi/newpipe/util/WindowInsetsHelper.java
+++ b/app/src/main/java/org/schabi/newpipe/util/WindowInsetsHelper.java
@@ -71,24 +71,6 @@ public static void applyStatusBarInsets(@NonNull final AppCompatActivity activit
});
}
- /**
- * Pads the bottom of a content view by the navigation-bar inset, so its last items stay above
- * the system navigation bar in edge-to-edge (targetSdk 35+). Used on the main fragment holder
- * so feed/search/channel/playlist lists are not drawn behind the nav bar.
- */
- public static void applyNavigationBarInsets(@NonNull final View content) {
- final int initialLeft = content.getPaddingLeft();
- final int initialTop = content.getPaddingTop();
- final int initialRight = content.getPaddingRight();
- final int initialBottom = content.getPaddingBottom();
-
- ViewCompat.setOnApplyWindowInsetsListener(content, (view, insets) -> {
- final Insets navBars = insets.getInsets(WindowInsetsCompat.Type.navigationBars());
- view.setPadding(initialLeft, initialTop, initialRight, initialBottom + navBars.bottom);
- return insets;
- });
- }
-
private static int getActionBarSize(@NonNull final AppCompatActivity activity) {
final TypedValue typedValue = new TypedValue();
if (activity.getTheme().resolveAttribute(android.R.attr.actionBarSize, typedValue, true)) {
diff --git a/app/src/main/java/org/schabi/newpipe/views/BaseLoginWebViewActivity.java b/app/src/main/java/org/schabi/newpipe/views/BaseLoginWebViewActivity.java
index 6ebb3ee24..b08afa4eb 100644
--- a/app/src/main/java/org/schabi/newpipe/views/BaseLoginWebViewActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/views/BaseLoginWebViewActivity.java
@@ -7,7 +7,6 @@
import android.webkit.WebViewClient;
import androidx.appcompat.app.AppCompatActivity;
import org.schabi.newpipe.R;
-import org.schabi.newpipe.util.WindowInsetsHelper;
public abstract class BaseLoginWebViewActivity extends AppCompatActivity {
@@ -19,8 +18,6 @@ protected void onCreate(Bundle savedInstanceState) {
setContentView(R.layout.login_webview);
webView = findViewById(R.id.login_webview);
- // Edge-to-edge (targetSdk 35+): keep the bottom of the login page above the nav bar.
- WindowInsetsHelper.applyNavigationBarInsets(webView);
configureWebView();
webView.setWebViewClient(createWebViewClient());
loadLoginUrl();
diff --git a/app/src/main/res/layout/activity_main.xml b/app/src/main/res/layout/activity_main.xml
index 1d6072700..97ccd199e 100644
--- a/app/src/main/res/layout/activity_main.xml
+++ b/app/src/main/res/layout/activity_main.xml
@@ -25,7 +25,6 @@
android:layout_gravity="center_horizontal"
app:behavior_hideable="true"
app:behavior_peekHeight="0dp"
- app:paddingBottomSystemWindowInsets="true"
app:layout_behavior="org.schabi.newpipe.player.event.CustomBottomSheetBehavior" />
From f098316302048d9c26af79cf8ab3ec99b6cc41ea Mon Sep 17 00:00:00 2001
From: InfinityLoop1308 <96324692+InfinityLoop1308@users.noreply.github.com>
Date: Sat, 20 Jun 2026 16:37:40 +0800
Subject: [PATCH 3/5] Revert "fix(ui): edge-to-edge bottom-tab overlap + back
button closing the app (targetSdk 37) (#52)"
---
app/src/main/AndroidManifest.xml | 1 -
.../schabi/newpipe/fragments/MainFragment.java | 16 ----------------
.../fragments/detail/VideoDetailFragment.java | 15 ---------------
.../main/res/layout/fragment_video_detail.xml | 1 -
4 files changed, 33 deletions(-)
diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml
index 73f63fa81..0759c024c 100644
--- a/app/src/main/AndroidManifest.xml
+++ b/app/src/main/AndroidManifest.xml
@@ -53,7 +53,6 @@
android:logo="@mipmap/ic_launcher"
android:theme="@style/OpeningTheme"
android:resizeableActivity="true"
- android:enableOnBackInvokedCallback="false"
tools:ignore="AllowBackup">
{
- final int navBottom = mainTabsPositionBottom
- ? insets.getInsets(WindowInsetsCompat.Type.navigationBars()).bottom : 0;
- v.setPadding(v.getPaddingLeft(), v.getPaddingTop(), v.getPaddingRight(), navBottom);
- return insets;
- });
-
setupTabs();
updateTabLayoutPosition();
}
@@ -248,9 +235,6 @@ private void updateTabLayoutPosition() {
tabLayout.setTabRippleColor(ColorStateList.valueOf(iconColor).withAlpha(32));
tabLayout.setTabIconTint(ColorStateList.valueOf(iconColor));
tabLayout.setSelectedTabIndicatorColor(iconColor);
-
- // Re-apply the nav-bar inset padding for the new position (added at bottom, cleared at top).
- ViewCompat.requestApplyInsets(tabLayout);
}
@Override
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 c9ac6aa33..4c444278f 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
@@ -722,21 +722,6 @@ protected void initViews(final View rootView, final Bundle savedInstanceState) {
pageAdapter = new TabAdapter(getChildFragmentManager());
binding.viewPager.setAdapter(pageAdapter);
binding.tabLayout.setupWithViewPager(binding.viewPager);
- // Edge-to-edge (targetSdk 35+): the bottom tab strip is laid out gravity=bottom, so without
- // insets it sits behind the system navigation bar (tabs unclickable) and the pager's last
- // item runs under it. Pad the tab strip by the nav-bar inset and grow the pager's bottom
- // padding (its XML 48dp tab clearance) by the same amount so content clears both.
- final int viewPagerBottomBase = binding.viewPager.getPaddingBottom();
- ViewCompat.setOnApplyWindowInsetsListener(binding.tabLayout, (v, insets) -> {
- final int navBottom = insets.getInsets(
- WindowInsetsCompat.Type.navigationBars()).bottom;
- v.setPadding(v.getPaddingLeft(), v.getPaddingTop(), v.getPaddingRight(), navBottom);
- binding.viewPager.setPadding(binding.viewPager.getPaddingLeft(),
- binding.viewPager.getPaddingTop(), binding.viewPager.getPaddingRight(),
- viewPagerBottomBase + navBottom);
- return insets;
- });
- ViewCompat.requestApplyInsets(binding.tabLayout);
updateStickyPlayerMode();
binding.detailThumbnailRootLayout.requestFocus();
diff --git a/app/src/main/res/layout/fragment_video_detail.xml b/app/src/main/res/layout/fragment_video_detail.xml
index 8e62761a2..d426fd071 100644
--- a/app/src/main/res/layout/fragment_video_detail.xml
+++ b/app/src/main/res/layout/fragment_video_detail.xml
@@ -626,7 +626,6 @@
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="bottom|center"
- android:background="?attr/windowBackground"
app:tabIndicatorGravity="top"
app:tabIconTint="?attr/colorAccent"
app:tabBackground="?attr/windowBackground"
From b3da97b23ffaee77fdea37f03192b4116bc3dcc1 Mon Sep 17 00:00:00 2001
From: InfinityLoop1308 <96324692+InfinityLoop1308@users.noreply.github.com>
Date: Sat, 20 Jun 2026 16:43:23 +0800
Subject: [PATCH 4/5] Revert "dev: update targetSdk to 37 with status bar fix
(#49)"
Keep the targetSdk, foreground service, feed service, and build compatibility changes from the pull request.
---
app/src/main/java/org/schabi/newpipe/App.java | 1 -
.../java/org/schabi/newpipe/MainActivity.java | 3 -
.../org/schabi/newpipe/about/AboutActivity.kt | 2 -
.../newpipe/download/DownloadActivity.java | 4 -
.../schabi/newpipe/error/ErrorActivity.java | 6 --
.../newpipe/error/ReCaptchaActivity.java | 5 --
.../fragments/detail/VideoDetailFragment.java | 58 ++-----------
.../newpipe/player/PlayQueueActivity.java | 34 --------
.../org/schabi/newpipe/player/Player.java | 15 ----
.../settings/BaseFilterListActivity.java | 7 +-
.../newpipe/settings/SettingsActivity.java | 6 --
.../schabi/newpipe/util/StatusBarHelper.java | 43 ----------
.../newpipe/util/WindowInsetsHelper.java | 86 -------------------
.../newpipe/views/FocusAwareCoordinator.java | 4 +-
.../activity_player_queue_control.xml | 1 +
app/src/main/res/layout/activity_about.xml | 1 +
.../layout/activity_player_queue_control.xml | 1 +
app/src/main/res/layout/player.xml | 1 +
18 files changed, 14 insertions(+), 264 deletions(-)
delete mode 100644 app/src/main/java/org/schabi/newpipe/util/StatusBarHelper.java
delete mode 100644 app/src/main/java/org/schabi/newpipe/util/WindowInsetsHelper.java
diff --git a/app/src/main/java/org/schabi/newpipe/App.java b/app/src/main/java/org/schabi/newpipe/App.java
index bf966e5ff..d0caeb87d 100644
--- a/app/src/main/java/org/schabi/newpipe/App.java
+++ b/app/src/main/java/org/schabi/newpipe/App.java
@@ -104,7 +104,6 @@ public void onChanged(Integer connectionState) {
// Initialize settings first because others inits can use its values
NewPipeSettings.initSettings(this);
- StatusBarHelper.init(this);
// Initialize Android Auto component state based on preference
DeviceUtils.updateAndroidAutoComponentState(this);
diff --git a/app/src/main/java/org/schabi/newpipe/MainActivity.java b/app/src/main/java/org/schabi/newpipe/MainActivity.java
index 0586fed66..afd020963 100644
--- a/app/src/main/java/org/schabi/newpipe/MainActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/MainActivity.java
@@ -152,9 +152,6 @@ protected void onCreate(final Bundle savedInstanceState) {
toolbarLayoutBinding = mainBinding.toolbarLayout;
setContentView(mainBinding.getRoot());
- WindowInsetsHelper.applyStatusBarInsets(this, toolbarLayoutBinding.toolbar,
- mainBinding.fragmentHolder);
-
if (getSupportFragmentManager().getBackStackEntryCount() == 0) {
initFragments();
}
diff --git a/app/src/main/java/org/schabi/newpipe/about/AboutActivity.kt b/app/src/main/java/org/schabi/newpipe/about/AboutActivity.kt
index 4abab8570..d588cfaec 100644
--- a/app/src/main/java/org/schabi/newpipe/about/AboutActivity.kt
+++ b/app/src/main/java/org/schabi/newpipe/about/AboutActivity.kt
@@ -17,7 +17,6 @@ import org.schabi.newpipe.databinding.ActivityAboutBinding
import org.schabi.newpipe.databinding.FragmentAboutBinding
import org.schabi.newpipe.util.Localization
import org.schabi.newpipe.util.ThemeHelper
-import org.schabi.newpipe.util.WindowInsetsHelper
import org.schabi.newpipe.util.external_communication.ShareUtils
class AboutActivity : AppCompatActivity() {
@@ -32,7 +31,6 @@ class AboutActivity : AppCompatActivity() {
setContentView(aboutBinding.root)
setSupportActionBar(aboutBinding.aboutToolbar)
- WindowInsetsHelper.applyStatusBarInsets(this, aboutBinding.aboutToolbar)
supportActionBar?.setDisplayHomeAsUpEnabled(true)
// Create the adapter that will return a fragment for each of the three
diff --git a/app/src/main/java/org/schabi/newpipe/download/DownloadActivity.java b/app/src/main/java/org/schabi/newpipe/download/DownloadActivity.java
index 61bc32061..37eefed96 100644
--- a/app/src/main/java/org/schabi/newpipe/download/DownloadActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/download/DownloadActivity.java
@@ -5,7 +5,6 @@
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
-import android.view.ViewGroup;
import android.view.ViewTreeObserver;
import androidx.appcompat.app.ActionBar;
@@ -16,7 +15,6 @@
import org.schabi.newpipe.databinding.ActivityDownloaderBinding;
import org.schabi.newpipe.util.DeviceUtils;
import org.schabi.newpipe.util.ThemeHelper;
-import org.schabi.newpipe.util.WindowInsetsHelper;
import org.schabi.newpipe.views.FocusOverlayView;
import us.shandian.giga.service.DownloadManagerService;
@@ -46,8 +44,6 @@ protected void onCreate(final Bundle savedInstanceState) {
setSupportActionBar(downloaderBinding.toolbarLayout.toolbar);
- WindowInsetsHelper.applyStatusBarInsets(this, downloaderBinding.toolbarLayout.toolbar);
-
final ActionBar actionBar = getSupportActionBar();
if (actionBar != null) {
actionBar.setDisplayHomeAsUpEnabled(true);
diff --git a/app/src/main/java/org/schabi/newpipe/error/ErrorActivity.java b/app/src/main/java/org/schabi/newpipe/error/ErrorActivity.java
index db1e21769..8497da9e0 100644
--- a/app/src/main/java/org/schabi/newpipe/error/ErrorActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/error/ErrorActivity.java
@@ -13,7 +13,6 @@
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
-import android.view.ViewGroup;
import androidx.annotation.Nullable;
import androidx.appcompat.app.ActionBar;
import androidx.appcompat.app.AlertDialog;
@@ -28,7 +27,6 @@
import org.schabi.newpipe.util.ErrorMatcher;
import org.schabi.newpipe.util.Localization;
import org.schabi.newpipe.util.ThemeHelper;
-import org.schabi.newpipe.util.WindowInsetsHelper;
import org.schabi.newpipe.util.external_communication.ShareUtils;
import org.schabi.newpipe.util.utils;
@@ -105,10 +103,6 @@ protected void onCreate(final Bundle savedInstanceState) {
setSupportActionBar(activityErrorBinding.toolbarLayout.toolbar);
- WindowInsetsHelper.applyStatusBarInsets(this,
- activityErrorBinding.toolbarLayout.toolbar,
- activityErrorBinding.scrollView);
-
final ActionBar actionBar = getSupportActionBar();
if (actionBar != null) {
actionBar.setDisplayHomeAsUpEnabled(true);
diff --git a/app/src/main/java/org/schabi/newpipe/error/ReCaptchaActivity.java b/app/src/main/java/org/schabi/newpipe/error/ReCaptchaActivity.java
index 753bcfdb5..bee9e6395 100644
--- a/app/src/main/java/org/schabi/newpipe/error/ReCaptchaActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/error/ReCaptchaActivity.java
@@ -8,7 +8,6 @@
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
-import android.view.ViewGroup;
import android.webkit.CookieManager;
import android.webkit.WebSettings;
import android.webkit.WebView;
@@ -26,7 +25,6 @@
import org.schabi.newpipe.MainActivity;
import org.schabi.newpipe.R;
import org.schabi.newpipe.util.ThemeHelper;
-import org.schabi.newpipe.util.WindowInsetsHelper;
import java.io.UnsupportedEncodingException;
import java.net.URLDecoder;
@@ -79,9 +77,6 @@ protected void onCreate(final Bundle savedInstanceState) {
setContentView(recaptchaBinding.getRoot());
setSupportActionBar(recaptchaBinding.toolbar);
- WindowInsetsHelper.applyStatusBarInsets(this, recaptchaBinding.toolbar,
- recaptchaBinding.reCaptchaWebView);
-
final String url = sanitizeRecaptchaUrl(getIntent().getStringExtra(RECAPTCHA_URL_EXTRA));
// set return to Cancel by default
setResult(RESULT_CANCELED);
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 4c444278f..5a3bbaf81 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
@@ -42,9 +42,6 @@
import androidx.appcompat.widget.Toolbar;
import androidx.coordinatorlayout.widget.CoordinatorLayout;
import androidx.core.content.ContextCompat;
-import androidx.core.view.ViewCompat;
-import androidx.core.view.WindowInsetsCompat;
-import androidx.core.view.WindowInsetsControllerCompat;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentManager;
import androidx.preference.PreferenceManager;
@@ -225,7 +222,6 @@ private void onSharedPreferencesChanged(final SharedPreferences sharedPreference
private List sortedVideoStreams;
private int selectedVideoStreamIndex = -1;
- private int statusBarInset;
private BottomSheetBehavior bottomSheetBehavior;
private BroadcastReceiver broadcastReceiver;
@@ -807,20 +803,6 @@ protected void initListeners() {
});
setupBottomPlayer();
- final View bottomSheetLayout = activity.findViewById(R.id.fragment_player_holder);
- ViewCompat.setOnApplyWindowInsetsListener(bottomSheetLayout, (v, insets) -> {
- final int statusBarHeight = insets.getInsets(
- WindowInsetsCompat.Type.statusBars()).top;
- statusBarInset = insets.getInsetsIgnoringVisibility(
- WindowInsetsCompat.Type.statusBars()).top;
- final int topPadding = isPlayerAvailable() && player.isFullscreen()
- ? 0 : statusBarHeight;
- v.setPadding(v.getPaddingLeft(), topPadding,
- v.getPaddingRight(), v.getPaddingBottom());
- updateBottomSheetPeekHeight();
- return insets;
- });
- ViewCompat.requestApplyInsets(bottomSheetLayout);
if (!playerHolder.isBound()) {
setHeightThumbnail();
} else {
@@ -2278,14 +2260,6 @@ public void onFullscreenStateChanged(final boolean fullscreen) {
scrollToTop();
addVideoPlayerView();
- final View bottomSheetLayout = requireActivity().findViewById(R.id.fragment_player_holder);
- if (fullscreen) {
- bottomSheetLayout.setPadding(bottomSheetLayout.getPaddingLeft(), 0,
- bottomSheetLayout.getPaddingRight(), bottomSheetLayout.getPaddingBottom());
- } else {
- bottomSheetLayout.setPadding(bottomSheetLayout.getPaddingLeft(), statusBarInset,
- bottomSheetLayout.getPaddingRight(), bottomSheetLayout.getPaddingBottom());
- }
}
@Override
@@ -2356,11 +2330,6 @@ private void showSystemUi() {
WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT;
}
activity.getWindow().getDecorView().setSystemUiVisibility(0);
- final WindowInsetsControllerCompat controller = ViewCompat.getWindowInsetsController(
- activity.getWindow().getDecorView());
- if (controller != null) {
- controller.show(WindowInsetsCompat.Type.systemBars());
- }
activity.getWindow().clearFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
activity.getWindow().setStatusBarColor(ThemeHelper.resolveColorFromAttr(
requireContext(), android.R.attr.colorPrimary));
@@ -2393,24 +2362,19 @@ private void hideSystemUi() {
visibility |= View.SYSTEM_UI_FLAG_FULLSCREEN;
}
activity.getWindow().getDecorView().setSystemUiVisibility(visibility);
- final WindowInsetsControllerCompat controller = ViewCompat.getWindowInsetsController(
- activity.getWindow().getDecorView());
- if (controller != null) {
- controller.setSystemBarsBehavior(
- WindowInsetsControllerCompat.BEHAVIOR_SHOW_TRANSIENT_BARS_BY_SWIPE);
- controller.hide(WindowInsetsCompat.Type.systemBars());
- }
if (isInMultiWindow || isPlayerAvailable() && player.isFullscreen()) {
activity.getWindow().setStatusBarColor(Color.TRANSPARENT);
activity.getWindow().setNavigationBarColor(Color.TRANSPARENT);
}
- activity.getWindow().addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
+ activity.getWindow().clearFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
}
// Listener implementation
public void hideSystemUiIfNeeded() {
- if (isPlayerAvailable() && player.isFullscreen()) {
+ if (isPlayerAvailable()
+ && player.isFullscreen()
+ && bottomSheetBehavior.getState() == BottomSheetBehavior.STATE_EXPANDED) {
hideSystemUi();
}
}
@@ -2618,13 +2582,6 @@ private void manageSpaceAtTheBottom(final boolean showMore) {
newBottomPadding);
}
- private void updateBottomSheetPeekHeight() {
- final int peekHeight = getResources().getDimensionPixelSize(R.dimen.mini_player_height)
- + statusBarInset;
- bottomSheetBehavior.setPeekHeight(bottomSheetState == BottomSheetBehavior.STATE_HIDDEN
- ? 0 : peekHeight);
- }
-
private void setupBottomPlayer() {
final CoordinatorLayout.LayoutParams params =
(CoordinatorLayout.LayoutParams) binding.appBarLayout.getLayoutParams();
@@ -2633,9 +2590,10 @@ private void setupBottomPlayer() {
final FrameLayout bottomSheetLayout = activity.findViewById(R.id.fragment_player_holder);
bottomSheetBehavior = BottomSheetBehavior.from(bottomSheetLayout);
bottomSheetBehavior.setState(bottomSheetState);
+ final int peekHeight = getResources().getDimensionPixelSize(R.dimen.mini_player_height);
if (bottomSheetState != BottomSheetBehavior.STATE_HIDDEN) {
manageSpaceAtTheBottom(false);
- updateBottomSheetPeekHeight();
+ bottomSheetBehavior.setPeekHeight(peekHeight);
if (bottomSheetState == BottomSheetBehavior.STATE_COLLAPSED) {
binding.overlayLayout.setAlpha(MAX_OVERLAY_ALPHA);
} else if (bottomSheetState == BottomSheetBehavior.STATE_EXPANDED) {
@@ -2663,7 +2621,7 @@ public void onStateChanged(@NonNull final View bottomSheet, final int newState)
moveFocusToMainFragment(false);
manageSpaceAtTheBottom(false);
- updateBottomSheetPeekHeight();
+ bottomSheetBehavior.setPeekHeight(peekHeight);
// Disable click because overlay buttons located on top of buttons
// from the player
setOverlayElementsClickable(false);
@@ -2689,7 +2647,7 @@ && isPlayerAvailable()
moveFocusToMainFragment(true);
manageSpaceAtTheBottom(false);
- updateBottomSheetPeekHeight();
+ bottomSheetBehavior.setPeekHeight(peekHeight);
// Re-enable clicks
setOverlayElementsClickable(true);
diff --git a/app/src/main/java/org/schabi/newpipe/player/PlayQueueActivity.java b/app/src/main/java/org/schabi/newpipe/player/PlayQueueActivity.java
index d2512e0c0..7fa03e806 100644
--- a/app/src/main/java/org/schabi/newpipe/player/PlayQueueActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/player/PlayQueueActivity.java
@@ -9,7 +9,6 @@
import android.os.IBinder;
import android.provider.Settings;
import android.util.Log;
-import android.util.TypedValue;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
@@ -18,11 +17,8 @@
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
-import androidx.core.view.ViewCompat;
-import androidx.core.view.WindowInsetsCompat;
import androidx.recyclerview.widget.ItemTouchHelper;
-import com.google.android.material.appbar.AppBarLayout;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@@ -82,36 +78,6 @@ protected void onCreate(final Bundle savedInstanceState) {
setSupportActionBar(queueControlBinding.toolbar);
- queueControlBinding.appbar.setStatusBarForeground(null);
- getWindow().setStatusBarColor(android.graphics.Color.TRANSPARENT);
-
- WindowInsetsHelper.applyStatusBarInsets(this, queueControlBinding.toolbar);
-
- ViewCompat.setOnApplyWindowInsetsListener(queueControlBinding.getRoot(), (v, insets) -> {
- final int navBarHeight = insets.getInsets(
- WindowInsetsCompat.Type.navigationBars()).bottom;
- final int twelveDp = (int) (12 * getResources()
- .getDisplayMetrics().density + 0.5f);
-
- if (queueControlBinding.playbackControls != null) {
- final ViewGroup.MarginLayoutParams controlsParams =
- (ViewGroup.MarginLayoutParams) queueControlBinding
- .playbackControls.getLayoutParams();
- controlsParams.bottomMargin = twelveDp + navBarHeight;
- queueControlBinding.playbackControls.setLayoutParams(controlsParams);
- }
-
- if (queueControlBinding.playbackControlsBottom != null) {
- queueControlBinding.playbackControlsBottom.setPadding(
- queueControlBinding.playbackControlsBottom.getPaddingLeft(),
- queueControlBinding.playbackControlsBottom.getPaddingTop(),
- queueControlBinding.playbackControlsBottom.getPaddingRight(),
- navBarHeight);
- }
-
- return insets;
- });
-
if (getSupportActionBar() != null) {
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
getSupportActionBar().setTitle(R.string.title_activity_play_queue);
diff --git a/app/src/main/java/org/schabi/newpipe/player/Player.java b/app/src/main/java/org/schabi/newpipe/player/Player.java
index 53b8e54bb..612a3eaed 100644
--- a/app/src/main/java/org/schabi/newpipe/player/Player.java
+++ b/app/src/main/java/org/schabi/newpipe/player/Player.java
@@ -500,7 +500,6 @@ public void setupFromView(@NonNull final PlayerBinding playerBinding) {
private void initViews(@NonNull final PlayerBinding playerBinding) {
binding = playerBinding;
- updatePlaybackControlInsetsMode();
setupSubtitleView();
binding.resizeTextView
@@ -1388,7 +1387,6 @@ private void onBroadcastReceived(final Intent intent) {
// and thus enlarging the whole player.
// This causes the seekbar to be ouf the visible area.
updateEndScreenThumbnail();
- updatePlaybackControlInsetsMode();
break;
case Intent.ACTION_SCREEN_ON:
// Interrupt playback only when screen turns on
@@ -2251,10 +2249,6 @@ private void showOrHideButtons() {
private void showSystemUIPartially() {
final AppCompatActivity activity = getParentActivity();
if (isFullscreen && activity != null) {
- if (!service.isLandscape()) {
- hideSystemUIIfNeeded();
- return;
- }
activity.getWindow().setStatusBarColor(Color.TRANSPARENT);
activity.getWindow().setNavigationBarColor(Color.TRANSPARENT);
final int visibility = View.SYSTEM_UI_FLAG_LAYOUT_STABLE
@@ -4716,7 +4710,6 @@ public void toggleFullscreen() {
}
isFullscreen = !isFullscreen;
- updatePlaybackControlInsetsMode();
if (!isFullscreen) {
// Apply window insets because Android will not do it when orientation changes
// from landscape to portrait (open vertical video to reproduce)
@@ -4744,14 +4737,6 @@ public void toggleFullscreen() {
setupScreenRotationButton();
}
- private void updatePlaybackControlInsetsMode() {
- final boolean fitSystemWindows = isFullscreen && service.isLandscape();
- binding.playbackControlRoot.setFitsSystemWindows(fitSystemWindows);
- if (!fitSystemWindows) {
- binding.playbackControlRoot.setPadding(0, 0, 0, 0);
- }
- }
-
public void checkLandscape() {
final AppCompatActivity parent = getParentActivity();
final boolean videoInLandscapeButNotInFullscreen =
diff --git a/app/src/main/java/org/schabi/newpipe/settings/BaseFilterListActivity.java b/app/src/main/java/org/schabi/newpipe/settings/BaseFilterListActivity.java
index 5b08f6d58..5c1b3749b 100644
--- a/app/src/main/java/org/schabi/newpipe/settings/BaseFilterListActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/settings/BaseFilterListActivity.java
@@ -12,7 +12,6 @@
import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.widget.SearchView;
-import androidx.appcompat.widget.Toolbar;
import androidx.recyclerview.widget.ItemTouchHelper;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@@ -24,7 +23,6 @@
import org.schabi.newpipe.R;
import org.schabi.newpipe.util.ServiceHelper;
import org.schabi.newpipe.util.ThemeHelper;
-import org.schabi.newpipe.util.WindowInsetsHelper;
import java.util.ArrayList;
import java.util.HashSet;
@@ -49,10 +47,7 @@ protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_filter_list);
- final Toolbar toolbar = findViewById(R.id.toolbar);
- setSupportActionBar(toolbar);
-
- WindowInsetsHelper.applyStatusBarInsets(this, toolbar);
+ setSupportActionBar(findViewById(R.id.toolbar));
if (getSupportActionBar() != null) {
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
getSupportActionBar().setTitle(getActivityTitle());
diff --git a/app/src/main/java/org/schabi/newpipe/settings/SettingsActivity.java b/app/src/main/java/org/schabi/newpipe/settings/SettingsActivity.java
index 65f72b66f..3ff93d79c 100644
--- a/app/src/main/java/org/schabi/newpipe/settings/SettingsActivity.java
+++ b/app/src/main/java/org/schabi/newpipe/settings/SettingsActivity.java
@@ -9,7 +9,6 @@
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
-import android.view.ViewGroup;
import android.widget.EditText;
import androidx.annotation.IdRes;
@@ -35,7 +34,6 @@
import org.schabi.newpipe.settings.preferencesearch.PreferenceSearchResultListener;
import org.schabi.newpipe.settings.preferencesearch.PreferenceSearcher;
import org.schabi.newpipe.util.DeviceUtils;
-import org.schabi.newpipe.util.WindowInsetsHelper;
import org.schabi.newpipe.util.KeyboardUtil;
import org.schabi.newpipe.util.ReleaseVersionUtil;
import org.schabi.newpipe.util.ThemeHelper;
@@ -103,10 +101,6 @@ protected void onCreate(final Bundle savedInstanceBundle) {
setSupportActionBar(settingsLayoutBinding.settingsToolbarLayout.toolbar);
- WindowInsetsHelper.applyStatusBarInsets(this,
- settingsLayoutBinding.settingsToolbarLayout.toolbar,
- settingsLayoutBinding.settingsFragmentHolder);
-
if (restored) {
// Restore state
if (this.wasSearchActive) {
diff --git a/app/src/main/java/org/schabi/newpipe/util/StatusBarHelper.java b/app/src/main/java/org/schabi/newpipe/util/StatusBarHelper.java
deleted file mode 100644
index bafdf56e0..000000000
--- a/app/src/main/java/org/schabi/newpipe/util/StatusBarHelper.java
+++ /dev/null
@@ -1,43 +0,0 @@
-package org.schabi.newpipe.util;
-
-import android.content.Context;
-import android.content.res.Configuration;
-import android.content.res.Resources;
-
-import androidx.annotation.NonNull;
-
-public final class StatusBarHelper {
- private static int portraitHeight;
- private static int landscapeHeight;
-
- private StatusBarHelper() {
- }
-
- public static void init(@NonNull final Context context) {
- final Resources resources = context.getResources();
- portraitHeight = getInternalDimensionPixelSize(resources, "status_bar_height_portrait");
- landscapeHeight = getInternalDimensionPixelSize(resources, "status_bar_height_landscape");
-
- final int fallbackHeight = getInternalDimensionPixelSize(resources, "status_bar_height");
- if (portraitHeight == 0) {
- portraitHeight = fallbackHeight;
- }
- if (landscapeHeight == 0) {
- landscapeHeight = fallbackHeight;
- }
- }
-
- public static int get(@NonNull final Context context) {
- return context.getResources().getConfiguration().orientation
- == Configuration.ORIENTATION_LANDSCAPE ? landscapeHeight : portraitHeight;
- }
-
- private static int getInternalDimensionPixelSize(@NonNull final Resources resources,
- @NonNull final String name) {
- final int resourceId = resources.getIdentifier(name, "dimen", "android");
- if (resourceId == 0) {
- return 0;
- }
- return resources.getDimensionPixelSize(resourceId);
- }
-}
diff --git a/app/src/main/java/org/schabi/newpipe/util/WindowInsetsHelper.java b/app/src/main/java/org/schabi/newpipe/util/WindowInsetsHelper.java
deleted file mode 100644
index 18f656b0b..000000000
--- a/app/src/main/java/org/schabi/newpipe/util/WindowInsetsHelper.java
+++ /dev/null
@@ -1,86 +0,0 @@
-package org.schabi.newpipe.util;
-
-import android.util.TypedValue;
-import android.view.View;
-import android.view.ViewGroup;
-
-import androidx.annotation.NonNull;
-import androidx.appcompat.app.AppCompatActivity;
-import androidx.appcompat.widget.Toolbar;
-import androidx.core.graphics.Insets;
-import androidx.core.view.ViewCompat;
-import androidx.core.view.WindowInsetsCompat;
-
-public final class WindowInsetsHelper {
-
- private WindowInsetsHelper() {
- }
-
- public static void applyStatusBarInsets(@NonNull final AppCompatActivity activity,
- @NonNull final Toolbar toolbar) {
- final int initialLeft = toolbar.getPaddingLeft();
- final int initialTop = toolbar.getPaddingTop();
- final int initialRight = toolbar.getPaddingRight();
- final int initialBottom = toolbar.getPaddingBottom();
- final int actionBarSize = getActionBarSize(activity);
-
- ViewCompat.setOnApplyWindowInsetsListener(toolbar, (view, insets) -> {
- final Insets statusBars = insets.getInsets(WindowInsetsCompat.Type.statusBars());
- view.setPadding(initialLeft, initialTop + statusBars.top, initialRight, initialBottom);
-
- final ViewGroup.LayoutParams layoutParams = view.getLayoutParams();
- layoutParams.height = actionBarSize + initialTop + statusBars.top + initialBottom;
- view.setLayoutParams(layoutParams);
-
- return insets;
- });
- }
-
- public static void applyStatusBarInsets(@NonNull final AppCompatActivity activity,
- @NonNull final Toolbar toolbar,
- @NonNull final View content) {
- final ViewGroup.MarginLayoutParams layoutParams =
- (ViewGroup.MarginLayoutParams) content.getLayoutParams();
- final int initialTopMargin = layoutParams.topMargin;
-
- applyStatusBarInsets(activity, toolbar, insets -> {
- layoutParams.topMargin = initialTopMargin + insets.top;
- content.setLayoutParams(layoutParams);
- });
- }
-
- public static void applyStatusBarInsets(@NonNull final AppCompatActivity activity,
- @NonNull final Toolbar toolbar,
- @NonNull final InsetsConsumer insetsConsumer) {
- final int initialLeft = toolbar.getPaddingLeft();
- final int initialTop = toolbar.getPaddingTop();
- final int initialRight = toolbar.getPaddingRight();
- final int initialBottom = toolbar.getPaddingBottom();
- final int actionBarSize = getActionBarSize(activity);
-
- ViewCompat.setOnApplyWindowInsetsListener(toolbar, (view, insets) -> {
- final Insets statusBars = insets.getInsets(WindowInsetsCompat.Type.statusBars());
- view.setPadding(initialLeft, initialTop + statusBars.top, initialRight, initialBottom);
-
- final ViewGroup.LayoutParams layoutParams = view.getLayoutParams();
- layoutParams.height = actionBarSize + initialTop + statusBars.top + initialBottom;
- view.setLayoutParams(layoutParams);
-
- insetsConsumer.accept(statusBars);
- return insets;
- });
- }
-
- private static int getActionBarSize(@NonNull final AppCompatActivity activity) {
- final TypedValue typedValue = new TypedValue();
- if (activity.getTheme().resolveAttribute(android.R.attr.actionBarSize, typedValue, true)) {
- return TypedValue.complexToDimensionPixelSize(
- typedValue.data, activity.getResources().getDisplayMetrics());
- }
- return 0;
- }
-
- public interface InsetsConsumer {
- void accept(@NonNull Insets insets);
- }
-}
diff --git a/app/src/main/java/org/schabi/newpipe/views/FocusAwareCoordinator.java b/app/src/main/java/org/schabi/newpipe/views/FocusAwareCoordinator.java
index fbca13287..798d08c72 100644
--- a/app/src/main/java/org/schabi/newpipe/views/FocusAwareCoordinator.java
+++ b/app/src/main/java/org/schabi/newpipe/views/FocusAwareCoordinator.java
@@ -101,9 +101,7 @@ public WindowInsets dispatchApplyWindowInsets(final WindowInsets insets) {
protected boolean fitSystemWindows(final Rect insets) {
final ViewGroup controls = findViewById(R.id.playbackControlRoot);
if (controls != null) {
- controls.setPadding(insets.left,
- controls.getFitsSystemWindows() ? insets.top : 0,
- insets.right, insets.bottom);
+ controls.setPadding(insets.left, insets.top, insets.right, insets.bottom);
}
return super.fitSystemWindows(insets);
}
diff --git a/app/src/main/res/layout-land/activity_player_queue_control.xml b/app/src/main/res/layout-land/activity_player_queue_control.xml
index e23743475..b77e1b6aa 100644
--- a/app/src/main/res/layout-land/activity_player_queue_control.xml
+++ b/app/src/main/res/layout-land/activity_player_queue_control.xml
@@ -5,6 +5,7 @@
android:id="@+id/main_content"
android:layout_width="match_parent"
android:layout_height="match_parent"
+ android:fitsSystemWindows="true"
tools:context="org.schabi.newpipe.player.PlayQueueActivity">
From d2d8728c10b8ad4065fc351822e728d1c0c60277 Mon Sep 17 00:00:00 2001
From: InfinityLoop1308 <96324692+InfinityLoop1308@users.noreply.github.com>
Date: Sat, 20 Jun 2026 17:18:30 +0800
Subject: [PATCH 5/5] fix: disable edge-to-edge enforcement on Android 15+
---
app/build.gradle | 2 ++
app/src/main/java/org/schabi/newpipe/App.java | 1 +
.../newpipe/util/EdgeToEdgeWorkaround.java | 33 +++++++++++++++++++
3 files changed, 36 insertions(+)
create mode 100644 app/src/main/java/org/schabi/newpipe/util/EdgeToEdgeWorkaround.java
diff --git a/app/build.gradle b/app/build.gradle
index 77f809e07..dd19e4f8b 100644
--- a/app/build.gradle
+++ b/app/build.gradle
@@ -267,6 +267,8 @@ dependencies {
implementation "androidx.car.app:app:1.7.0"
/** Third-party libraries **/
+ implementation 'org.lsposed.hiddenapibypass:hiddenapibypass:6.1'
+
// HTML parser
implementation "org.jsoup:jsoup:1.14.3"
diff --git a/app/src/main/java/org/schabi/newpipe/App.java b/app/src/main/java/org/schabi/newpipe/App.java
index d0caeb87d..3ff22dbb2 100644
--- a/app/src/main/java/org/schabi/newpipe/App.java
+++ b/app/src/main/java/org/schabi/newpipe/App.java
@@ -79,6 +79,7 @@ protected void attachBaseContext(final Context base) {
@Override
public void onCreate() {
super.onCreate();
+ EdgeToEdgeWorkaround.apply();
app = this;
diff --git a/app/src/main/java/org/schabi/newpipe/util/EdgeToEdgeWorkaround.java b/app/src/main/java/org/schabi/newpipe/util/EdgeToEdgeWorkaround.java
new file mode 100644
index 000000000..c938d0b4c
--- /dev/null
+++ b/app/src/main/java/org/schabi/newpipe/util/EdgeToEdgeWorkaround.java
@@ -0,0 +1,33 @@
+package org.schabi.newpipe.util;
+
+import android.os.Build;
+import android.util.Log;
+
+import org.lsposed.hiddenapibypass.HiddenApiBypass;
+
+import java.util.Collections;
+
+public final class EdgeToEdgeWorkaround {
+ private static final String TAG = EdgeToEdgeWorkaround.class.getSimpleName();
+ private static final long ENFORCE_EDGE_TO_EDGE = 309578419L;
+
+ private EdgeToEdgeWorkaround() {
+ }
+
+ public static void apply() {
+ if (Build.VERSION.SDK_INT < Build.VERSION_CODES.VANILLA_ICE_CREAM) {
+ return;
+ }
+
+ try {
+ final Class> changeConfigClass =
+ Class.forName("android.compat.Compatibility$ChangeConfig");
+ final Object changeConfig = HiddenApiBypass.newInstance(changeConfigClass,
+ Collections.emptySet(), Collections.singleton(ENFORCE_EDGE_TO_EDGE));
+ final Class> compatibilityClass = Class.forName("android.compat.Compatibility");
+ HiddenApiBypass.invoke(compatibilityClass, null, "setOverrides", changeConfig);
+ } catch (final Throwable throwable) {
+ Log.e(TAG, "Unable to disable edge-to-edge enforcement", throwable);
+ }
+ }
+}