Skip to content

Commit

Permalink
feat(YouTube - Hide Shorts components): Add option to hide Shorts in …
Browse files Browse the repository at this point in the history
…watch history (#4214)
  • Loading branch information
LisoUseInAIKyrios authored Dec 24, 2024
1 parent 892f86c commit 19c2742
Show file tree
Hide file tree
Showing 5 changed files with 54 additions and 37 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -297,7 +297,7 @@ boolean isFiltered(@Nullable String identifier, String path, byte[] protobufBuff
if (matchedGroup == suggestedAction) {
// Skip searching the buffer if all suggested actions are set to hidden.
// This has a secondary effect of hiding all new un-identified actions
// under the assumption that the user wants all actions hidden.
// under the assumption that the user wants all suggestions hidden.
if (isEverySuggestedActionFilterEnabled()) {
return super.isFiltered(path, identifier, protobufBufferArray, matchedGroup, contentType, contentIndex);
}
Expand All @@ -324,19 +324,22 @@ boolean isFiltered(@Nullable String identifier, String path, byte[] protobufBuff
}

private static boolean shouldHideShortsFeedItems() {
// Known issue if hide home is on but at least one other hide is off:
//
// Shorts suggestions will load in the background if a video is opened and
// immediately minimized before any suggestions are loaded.
// In this state the player type will show minimized, which cannot
// distinguish between Shorts suggestions loading in the player and between
// scrolling thru search/home/subscription tabs while a player is minimized.
final boolean hideHome = Settings.HIDE_SHORTS_HOME.get();
final boolean hideSubscriptions = Settings.HIDE_SHORTS_SUBSCRIPTIONS.get();
final boolean hideSearch = Settings.HIDE_SHORTS_SEARCH.get();
final boolean hideHistory = Settings.HIDE_SHORTS_HISTORY.get();

if (hideHome && hideSubscriptions && hideSearch) {
// Shorts suggestions can load in the background if a video is opened and
// then immediately minimized before any suggestions are loaded.
// In this state the player type will show minimized, which makes it not possible to
// distinguish between Shorts suggestions loading in the player and between
// scrolling thru search/home/subscription tabs while a player is minimized.
//
// To avoid this situation for users that never want to show Shorts (all hide Shorts options are enabled)
// then hide all Shorts everywhere including the Library history and Library playlists.
if (!hideHome && !hideSubscriptions && !hideSearch && !hideHistory) {
return false;
}
if (hideHome && hideSubscriptions && hideSearch && hideHistory) {
return true;
}

Expand All @@ -352,24 +355,29 @@ private static boolean shouldHideShortsFeedItems() {
}

// Avoid checking navigation button status if all other Shorts should show.
if (!hideHome && !hideSubscriptions) {
if (!hideHome && !hideSubscriptions && !hideHistory) {
return false;
}

// Check navigation absolutely last since the check may block this thread.
NavigationButton selectedNavButton = NavigationButton.getSelectedNavigationButton();
if (selectedNavButton == null) {
return hideHome; // Unknown tab, treat the same as home.
}
if (selectedNavButton == NavigationButton.HOME) {
return hideHome;
}
if (selectedNavButton == NavigationButton.SUBSCRIPTIONS) {
return hideSubscriptions;
}
// User must be in the library tab. Don't hide the history or any playlists here.
return false;

return switch (selectedNavButton) {
case HOME -> hideHome;
case SUBSCRIPTIONS -> hideSubscriptions;
case LIBRARY -> hideHistory;
default -> false;
};
}

/**
* Injection point. Only used if patching older than 19.03.
* This hook may be obsolete even for old versions
* as they now use a litho layout like newer versions.
*/
public static void hideShortsShelf(final View shortsShelfView) {
if (shouldHideShortsFeedItems()) {
Utils.hideViewByLayoutParams(shortsShelfView);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -233,6 +233,7 @@ public class Settings extends BaseSettings {
public static final BooleanSetting HIDE_SHORTS_FULL_VIDEO_LINK_LABEL = new BooleanSetting("revanced_hide_shorts_full_video_link_label", FALSE);
public static final BooleanSetting HIDE_SHORTS_GREEN_SCREEN_BUTTON = new BooleanSetting("revanced_hide_shorts_green_screen_button", TRUE);
public static final BooleanSetting HIDE_SHORTS_HASHTAG_BUTTON = new BooleanSetting("revanced_hide_shorts_hashtag_button", TRUE);
public static final BooleanSetting HIDE_SHORTS_HISTORY = new BooleanSetting("revanced_hide_shorts_history", FALSE);
public static final BooleanSetting HIDE_SHORTS_HOME = new BooleanSetting("revanced_hide_shorts_home", FALSE);
public static final BooleanSetting HIDE_SHORTS_INFO_PANEL = new BooleanSetting("revanced_hide_shorts_info_panel", TRUE);
public static final BooleanSetting HIDE_SHORTS_JOIN_BUTTON = new BooleanSetting("revanced_hide_shorts_join_button", TRUE);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -54,20 +54,21 @@ public static boolean isSearchBarActive() {
* How long to wait for the set nav button latch to be released. Maximum wait time must
* be as small as possible while still allowing enough time for the nav bar to update.
*
* YT calls it's back button handlers out of order,
* and litho starts filtering before the navigation bar is updated.
* YT calls it's back button handlers out of order, and litho starts filtering before the
* navigation bar is updated. Fixing this situation and not needlessly waiting requires
* somehow detecting if a back button key/gesture will not change the active tab.
*
* Fixing this situation and not needlessly waiting requires somehow
* detecting if a back button key-press will cause a tab change.
* On average the time between pressing the back button and the first litho event is
* about 10-20ms. Waiting up to 75-150ms should be enough time to handle normal use cases
* and not be noticeable, since YT typically takes 100-200ms (or more) to update the view.
*
* Typically after pressing the back button, the time between the first litho event and
* when the nav button is updated is about 10-20ms. Using 50-100ms here should be enough time
* and not noticeable, since YT typically takes 100-200ms (or more) to update the view anyways.
* This delay is only noticeable when the device back button/gesture will not
* change the current navigation tab, such as backing out of the watch history.
*
* This issue can also be avoided on a patch by patch basis, by avoiding calls to
* {@link NavigationButton#getSelectedNavigationButton()} unless absolutely necessary.
*/
private static final long LATCH_AWAIT_TIMEOUT_MILLISECONDS = 75;
private static final long LATCH_AWAIT_TIMEOUT_MILLISECONDS = 120;

/**
* Used as a workaround to fix the issue of YT calling back button handlers out of order.
Expand Down Expand Up @@ -113,7 +114,8 @@ private static void waitForNavButtonLatchIfNeeded() {
// The latch is released from the main thread, and waiting from the main thread will always timeout.
// This situation has only been observed when navigating out of a submenu and not changing tabs.
// and for that use case the nav bar does not change so it's safe to return here.
Logger.printDebug(() -> "Cannot block main thread waiting for nav button. Using last known navbar button status.");
Logger.printDebug(() -> "Cannot block main thread waiting for nav button. " +
"Using last known navbar button status.");
return;
}

Expand All @@ -131,7 +133,9 @@ private static void waitForNavButtonLatchIfNeeded() {
Logger.printDebug(() -> "Latch wait timed out");

} catch (InterruptedException ex) {
Logger.printException(() -> "Latch wait interrupted failure", ex); // Will never happen.
// Calling YouTube thread was interrupted.
Logger.printException(() -> "Latch wait interrupted", ex);
Thread.currentThread().interrupt(); // Restore interrupt status flag.
}
}

Expand Down Expand Up @@ -283,8 +287,8 @@ public enum NavigationButton {
*
* All code calling this method should handle a null return value.
*
* <b>Due to issues with how YT processes physical back button events,
* this patch uses workarounds that can cause this method to take up to 75ms
* <b>Due to issues with how YT processes physical back button/gesture events,
* this patch uses workarounds that can cause this method to take up to 120ms
* if the device back button was recently pressed.</b>
*
* @return The active navigation tab.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ private val hideShortsComponentsResourcePatch = resourcePatch {
SwitchPreference("revanced_hide_shorts_home"),
SwitchPreference("revanced_hide_shorts_subscriptions"),
SwitchPreference("revanced_hide_shorts_search"),
SwitchPreference("revanced_hide_shorts_history"),

PreferenceScreenPreference(
key = "revanced_shorts_player_screen",
Expand Down
15 changes: 9 additions & 6 deletions patches/src/main/resources/addresources/values/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -632,15 +632,18 @@ Note: Enabling this also forcibly hides video ads"</string>
<string name="revanced_shorts_player_screen_summary">Hide or show components in the Shorts player</string>
<!-- 'home' should be translated using the same localized wording YouTube displays for the home tab. -->
<string name="revanced_hide_shorts_home_title">Hide Shorts in home feed</string>
<string name="revanced_hide_shorts_home_summary_on">Shorts in home feed are hidden</string>
<string name="revanced_hide_shorts_home_summary_off">Shorts in home feed are shown</string>
<string name="revanced_hide_shorts_home_summary_on">Home feed and related videos are hidden</string>
<string name="revanced_hide_shorts_home_summary_off">Home feed and related videos are shown</string>
<!-- 'subscription' should be translated using the same localized wording YouTube displays for the subscription tab. -->
<string name="revanced_hide_shorts_subscriptions_title">Hide Shorts in subscription feed</string>
<string name="revanced_hide_shorts_subscriptions_summary_on">Shorts in subscription feed are hidden</string>
<string name="revanced_hide_shorts_subscriptions_summary_off">Shorts in subscription feed are shown</string>
<string name="revanced_hide_shorts_subscriptions_summary_on">Hidden in subscription feed</string>
<string name="revanced_hide_shorts_subscriptions_summary_off">Shown in subscription feed</string>
<string name="revanced_hide_shorts_search_title">Hide Shorts in search results</string>
<string name="revanced_hide_shorts_search_summary_on">Shorts in search results are hidden</string>
<string name="revanced_hide_shorts_search_summary_off">Shorts in search results are shown</string>
<string name="revanced_hide_shorts_search_summary_on">Hidden in search results</string>
<string name="revanced_hide_shorts_search_summary_off">Shown in search results</string>
<string name="revanced_hide_shorts_history_title">Hide Shorts in watch history</string>
<string name="revanced_hide_shorts_history_summary_on">Hidden in watch history</string>
<string name="revanced_hide_shorts_history_summary_off">Shown in watch history</string>
<!-- 'join' should be translated using the same localized wording YouTube displays for the button. -->
<string name="revanced_hide_shorts_join_button_title">Hide join button</string>
<string name="revanced_hide_shorts_join_button_summary_on">Join button is hidden</string>
Expand Down

0 comments on commit 19c2742

Please sign in to comment.