From 4e77f04270325752c2289bcc33fda41b99dbbab2 Mon Sep 17 00:00:00 2001 From: inotia00 <108592928+inotia00@users.noreply.github.com> Date: Fri, 28 Feb 2025 09:20:13 +0900 Subject: [PATCH] fix(YouTube Music - Hide ads): `Hide premium promotion popups` setting hides the playlist dialog https://github.com/inotia00/ReVanced_Extended/issues/2798 --- .../patches/ads/PremiumPromotionPatch.java | 57 +++++++++++++++---- .../patches/music/ads/general/AdsPatch.kt | 15 +++++ 2 files changed, 62 insertions(+), 10 deletions(-) diff --git a/extensions/shared/src/main/java/app/revanced/extension/music/patches/ads/PremiumPromotionPatch.java b/extensions/shared/src/main/java/app/revanced/extension/music/patches/ads/PremiumPromotionPatch.java index e8dd2be41..6024e818d 100644 --- a/extensions/shared/src/main/java/app/revanced/extension/music/patches/ads/PremiumPromotionPatch.java +++ b/extensions/shared/src/main/java/app/revanced/extension/music/patches/ads/PremiumPromotionPatch.java @@ -1,6 +1,5 @@ package app.revanced.extension.music.patches.ads; -import static app.revanced.extension.music.patches.general.GeneralPatch.disableDimBehind; import static app.revanced.extension.shared.utils.StringRef.str; import android.app.Dialog; @@ -46,15 +45,53 @@ public class PremiumPromotionPatch { } } - public static void hidePremiumPromotionDialog(Dialog dialog, View contentView) { - if (HIDE_PREMIUM_PROMOTION) { - disableDimBehind(dialog.getWindow()); - dialog.setOnShowListener(DialogInterface::dismiss); - if (BaseSettings.ENABLE_DEBUG_LOGGING.get()) { - Utils.showToastShort(str("revanced_hide_premium_promotion_closed_toast")); - } - } else { - dialog.setContentView(contentView); + /** + * YouTube Premium promotion dialog is shown under the following conditions: + * 1. Patch YouTube Music 7.28.51 or later. + * 2. Log in with a Non-Premium account. + * 3. Change the Default client (Spoof client) to Android Music 4.27.53 or 5.29.53. + * 4. Play music. + * 5. Switch to the background. + * 6. Turn off the screen and turn it back on. + * 7. Switch to the foreground. + * 8. YouTube Premium promotion dialog is shown. + *
+ * In other words, if a dialog builder is called within 1000ms of the app being switched to the foreground, + * it is very likely a YouTube Premium promotion dialog. + */ + private static volatile boolean promotionDialogShown = false; + private static long foregroundStartTime = -1L; + + /** + * Injection point. + */ + public static void onAppBackgrounded() { + if (HIDE_PREMIUM_PROMOTION && !promotionDialogShown) { + foregroundStartTime = 0L; } } + + /** + * Injection point. + */ + public static void onAppForegrounded() { + if (HIDE_PREMIUM_PROMOTION && !promotionDialogShown && foregroundStartTime == 0L) { + foregroundStartTime = System.currentTimeMillis(); + } + } + + public static void hidePremiumPromotionDialog(Dialog dialog, View contentView) { + if (HIDE_PREMIUM_PROMOTION && !promotionDialogShown) { + final long foregroundTime = System.currentTimeMillis() - foregroundStartTime; + if (foregroundTime < 1000L) { + promotionDialogShown = true; + dialog.setOnShowListener(DialogInterface::dismiss); + if (BaseSettings.ENABLE_DEBUG_LOGGING.get()) { + Utils.showToastShort(str("revanced_hide_premium_promotion_closed_toast")); + } + return; + } + } + dialog.setContentView(contentView); + } } \ No newline at end of file diff --git a/patches/src/main/kotlin/app/revanced/patches/music/ads/general/AdsPatch.kt b/patches/src/main/kotlin/app/revanced/patches/music/ads/general/AdsPatch.kt index 9ae14aea4..56e345c17 100644 --- a/patches/src/main/kotlin/app/revanced/patches/music/ads/general/AdsPatch.kt +++ b/patches/src/main/kotlin/app/revanced/patches/music/ads/general/AdsPatch.kt @@ -8,6 +8,7 @@ import app.revanced.patches.music.navigation.components.navigationBarComponentsP import app.revanced.patches.music.utils.compatibility.Constants.COMPATIBLE_PACKAGE import app.revanced.patches.music.utils.extension.Constants.ADS_PATH import app.revanced.patches.music.utils.extension.Constants.COMPONENTS_PATH +import app.revanced.patches.music.utils.mainactivity.mainActivityResolvePatch import app.revanced.patches.music.utils.navigation.navigationBarHookPatch import app.revanced.patches.music.utils.patch.PatchList.HIDE_ADS import app.revanced.patches.music.utils.playservice.is_7_28_or_greater @@ -26,6 +27,8 @@ import app.revanced.patches.shared.ads.hookLithoFullscreenAds import app.revanced.patches.shared.ads.hookNonLithoFullscreenAds import app.revanced.patches.shared.litho.addLithoFilter import app.revanced.patches.shared.litho.lithoFilterPatch +import app.revanced.patches.shared.mainactivity.onStartMethod +import app.revanced.patches.shared.mainactivity.onStopMethod import app.revanced.util.fingerprint.matchOrThrow import app.revanced.util.fingerprint.methodOrThrow import app.revanced.util.getReference @@ -63,6 +66,7 @@ val adsPatch = bytecodePatch( navigationBarHookPatch, sharedResourceIdPatch, versionCheckPatch, + mainActivityResolvePatch, ) execute { @@ -94,8 +98,19 @@ val adsPatch = bytecodePatch( ) } + // get premium dialog in player if (is_7_28_or_greater) { + mapOf( + onStartMethod to "onAppForegrounded", + onStopMethod to "onAppBackgrounded" + ).forEach { (method, name) -> + method.addInstruction( + 0, + "invoke-static {}, $PREMIUM_PROMOTION_POP_UP_CLASS_DESCRIPTOR->$name()V" + ) + } + getPremiumDialogFingerprint .methodOrThrow(getPremiumDialogParentFingerprint) .apply {