You've already forked revanced-integrations
mirror of
https://github.com/revanced/revanced-integrations
synced 2025-11-21 18:35:37 +01:00
Compare commits
104 Commits
v0.106.0-d
...
v0.109.0-d
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
023ccbfec6 | ||
|
|
25925085ad | ||
|
|
85e776dc63 | ||
|
|
f13a99351c | ||
|
|
4d7c62bb6d | ||
|
|
1714700fb1 | ||
|
|
f7a940ca06 | ||
|
|
40def9e036 | ||
|
|
8ff9ebc592 | ||
|
|
f5df20134c | ||
|
|
592e7ed85b | ||
|
|
31251f0214 | ||
|
|
fa44f1227b | ||
|
|
b3c7e7f638 | ||
|
|
3bd94b2f6a | ||
|
|
60f25a2af0 | ||
|
|
301a0327bc | ||
|
|
7dc71e6861 | ||
|
|
69cc56c921 | ||
|
|
307315c43c | ||
|
|
985c0d0c48 | ||
|
|
191cc711de | ||
|
|
d9a75ea46a | ||
|
|
c7cabc0b57 | ||
|
|
cd93917148 | ||
|
|
932e3356a1 | ||
|
|
0c55d70370 | ||
|
|
d63f24f7be | ||
|
|
80689eff5b | ||
|
|
71e94e8d67 | ||
|
|
6d32f1ebc2 | ||
|
|
b47a781ba7 | ||
|
|
eb02c92773 | ||
|
|
ac13d10305 | ||
|
|
5ec90db28a | ||
|
|
5652c32345 | ||
|
|
2a15f902d6 | ||
|
|
7da56738a1 | ||
|
|
fc2ad5fa76 | ||
|
|
ae18edd047 | ||
|
|
4acbccd947 | ||
|
|
c3f08d8d7e | ||
|
|
224221cd80 | ||
|
|
6a94bd2237 | ||
|
|
7ed0f46a7c | ||
|
|
e30d1201c9 | ||
|
|
feed762707 | ||
|
|
a3d754c209 | ||
|
|
d9d9538873 | ||
|
|
6544b87118 | ||
|
|
d7f050ba2f | ||
|
|
ab87cce7e5 | ||
|
|
9649c3dbc8 | ||
|
|
701f88460d | ||
|
|
b42790fbca | ||
|
|
3645a4a580 | ||
|
|
ae99408636 | ||
|
|
a97eab5fcd | ||
|
|
415c1948fc | ||
|
|
1f72d17d49 | ||
|
|
4c7f737913 | ||
|
|
9e6176886b | ||
|
|
c97d1b7ee5 | ||
|
|
4fe923527e | ||
|
|
111d2f21f9 | ||
|
|
1b4aa0fcc6 | ||
|
|
9e9399ddc3 | ||
|
|
7da9d440ee | ||
|
|
43b007e865 | ||
|
|
8997ab7962 | ||
|
|
ad812cd011 | ||
|
|
e2f52905dc | ||
|
|
2882ec1c9c | ||
|
|
cb5a4d0c9b | ||
|
|
b9ffd3853c | ||
|
|
2dc431f1bf | ||
|
|
513d4e4542 | ||
|
|
486b79b4e4 | ||
|
|
680f17257d | ||
|
|
6c36beeda1 | ||
|
|
12c7c6844b | ||
|
|
9b47361af4 | ||
|
|
8ba636a910 | ||
|
|
68f42fc980 | ||
|
|
8255909b2f | ||
|
|
a91b0363a8 | ||
|
|
e34e75133c | ||
|
|
1185ceedf7 | ||
|
|
2ee18fce69 | ||
|
|
e774be0f05 | ||
|
|
8a7098cce4 | ||
|
|
a93a704c22 | ||
|
|
061ebc6546 | ||
|
|
0c6b22e929 | ||
|
|
7fc73368f1 | ||
|
|
8923fa9fd6 | ||
|
|
15f9c90941 | ||
|
|
c8784a5966 | ||
|
|
d3f8fb9739 | ||
|
|
ff0d64287c | ||
|
|
36fd2844c4 | ||
|
|
0de83fff0e | ||
|
|
24a609288f | ||
|
|
78d56d4fe1 |
2
.github/config.yml
vendored
Normal file
2
.github/config.yml
vendored
Normal file
@@ -0,0 +1,2 @@
|
||||
firstPRMergeComment: >
|
||||
Thank you for contributing to ReVanced. Join us on [Discord](https://revanced.app/discord) if you want to receive a contributor role.
|
||||
387
CHANGELOG.md
387
CHANGELOG.md
File diff suppressed because it is too large
Load Diff
@@ -1,8 +1,10 @@
|
||||
# ReVanced Integrations
|
||||
# 🔩 ReVanced Integrations
|
||||
|
||||
The official ReVanced Integrations containing classes to be merged by ReVanced Patcher.
|
||||
|
||||
## ❓ How to use debugging:
|
||||
|
||||
# How to use debugging:
|
||||
- Usage on Windows: ```adb logcat | findstr "revanced" > log.txt```
|
||||
- Usage on Linux: ```adb logcat | grep --line-buffered "revanced" > log.txt```
|
||||
|
||||
This will write the log to a file called log.txt which you can view then.
|
||||
|
||||
|
||||
@@ -44,7 +44,7 @@ android {
|
||||
dependencies {
|
||||
compileOnly(project(mapOf("path" to ":dummy")))
|
||||
compileOnly("androidx.annotation:annotation:1.6.0")
|
||||
compileOnly("androidx.appcompat:appcompat:1.6.1")
|
||||
compileOnly("androidx.appcompat:appcompat:1.7.0-alpha02")
|
||||
compileOnly("com.squareup.okhttp3:okhttp:5.0.0-alpha.11")
|
||||
compileOnly("com.squareup.retrofit2:retrofit:2.9.0")
|
||||
}
|
||||
|
||||
@@ -0,0 +1,21 @@
|
||||
package app.revanced.all.screencapture.removerestriction;
|
||||
|
||||
import android.media.AudioAttributes;
|
||||
import android.os.Build;
|
||||
|
||||
import androidx.annotation.RequiresApi;
|
||||
|
||||
public final class RemoveScreencaptureRestrictionPatch {
|
||||
// Member of AudioAttributes.Builder
|
||||
@RequiresApi(api = Build.VERSION_CODES.Q)
|
||||
public static AudioAttributes.Builder setAllowedCapturePolicy(final AudioAttributes.Builder builder, final int capturePolicy) {
|
||||
builder.setAllowedCapturePolicy(AudioAttributes.ALLOW_CAPTURE_BY_ALL);
|
||||
|
||||
return builder;
|
||||
}
|
||||
|
||||
// Member of AudioManager static class
|
||||
public static void setAllowedCapturePolicy(final int capturePolicy) {
|
||||
// Ignore request
|
||||
}
|
||||
}
|
||||
@@ -1,42 +0,0 @@
|
||||
package app.revanced.integrations.adremover;
|
||||
|
||||
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.FrameLayout;
|
||||
import android.widget.LinearLayout;
|
||||
import android.widget.RelativeLayout;
|
||||
import android.widget.Toolbar;
|
||||
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
|
||||
public class AdRemoverAPI {
|
||||
|
||||
/**
|
||||
* Removes Reels and Home ads
|
||||
*
|
||||
* @param view
|
||||
*/
|
||||
//ToDo: refactor this
|
||||
public static void HideViewWithLayout1dp(View view) {
|
||||
if (view instanceof LinearLayout) {
|
||||
LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(1, 1);
|
||||
view.setLayoutParams(layoutParams);
|
||||
} else if (view instanceof FrameLayout) {
|
||||
FrameLayout.LayoutParams layoutParams2 = new FrameLayout.LayoutParams(1, 1);
|
||||
view.setLayoutParams(layoutParams2);
|
||||
} else if (view instanceof RelativeLayout) {
|
||||
RelativeLayout.LayoutParams layoutParams3 = new RelativeLayout.LayoutParams(1, 1);
|
||||
view.setLayoutParams(layoutParams3);
|
||||
} else if (view instanceof Toolbar) {
|
||||
Toolbar.LayoutParams layoutParams4 = new Toolbar.LayoutParams(1, 1);
|
||||
view.setLayoutParams(layoutParams4);
|
||||
} else if (view instanceof ViewGroup) {
|
||||
ViewGroup.LayoutParams layoutParams5 = new ViewGroup.LayoutParams(1, 1);
|
||||
view.setLayoutParams(layoutParams5);
|
||||
} else {
|
||||
LogHelper.printDebug(() -> "HideViewWithLayout1dp - Id: " + view.getId() + " Type: " + view.getClass().getName());
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -5,6 +5,6 @@ import app.revanced.integrations.settings.SettingsEnum;
|
||||
public class AutoRepeatPatch {
|
||||
//Used by app.revanced.patches.youtube.layout.autorepeat.patch.AutoRepeatPatch
|
||||
public static boolean shouldAutoRepeat() {
|
||||
return SettingsEnum.PREFERRED_AUTO_REPEAT.getBoolean();
|
||||
return SettingsEnum.AUTO_REPEAT.getBoolean();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,31 +0,0 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
final class ButtonsPatch extends Filter {
|
||||
private final BlockRule actionBarRule;
|
||||
|
||||
public ButtonsPatch() {
|
||||
actionBarRule = new BlockRule(null, "video_action_bar");
|
||||
pathRegister.registerAll(
|
||||
new BlockRule(SettingsEnum.HIDE_LIKE_DISLIKE_BUTTON, "|like_button", "dislike_button"),
|
||||
new BlockRule(SettingsEnum.HIDE_DOWNLOAD_BUTTON, "download_button"),
|
||||
new BlockRule(SettingsEnum.HIDE_PLAYLIST_BUTTON, "save_to_playlist_button"),
|
||||
new BlockRule(SettingsEnum.HIDE_CLIP_BUTTON, "|clip_button.eml|"),
|
||||
new BlockRule(SettingsEnum.HIDE_ACTION_BUTTONS, "ContainerType|video_action_button", "|CellType|CollectionType|CellType|ContainerType|button.eml|")
|
||||
);
|
||||
}
|
||||
|
||||
private boolean canHideActionBar() {
|
||||
for (BlockRule rule : pathRegister) if (!rule.isEnabled()) return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean filter(final String path, final String identifier) {
|
||||
// If everything is hidden, then also hide the video bar itself.
|
||||
if (canHideActionBar() && actionBarRule.check(identifier).isBlocked()) return true;
|
||||
|
||||
return pathRegister.contains(path);
|
||||
}
|
||||
}
|
||||
@@ -1,31 +0,0 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
|
||||
final class CommentsPatch extends Filter {
|
||||
|
||||
public CommentsPatch() {
|
||||
var comments = new BlockRule(SettingsEnum.HIDE_COMMENTS_SECTION, "video_metadata_carousel", "_comments");
|
||||
var previewComment = new BlockRule(
|
||||
SettingsEnum.HIDE_PREVIEW_COMMENT,
|
||||
"|carousel_item",
|
||||
"comments_entry_point_teaser",
|
||||
"comments_entry_point_simplebox"
|
||||
);
|
||||
|
||||
this.pathRegister.registerAll(
|
||||
comments,
|
||||
previewComment
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
boolean filter(String path, String _identifier) {
|
||||
if (!pathRegister.contains(path)) return false;
|
||||
|
||||
LogHelper.printDebug(() -> "Blocked: " + path);
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@@ -2,22 +2,46 @@ package app.revanced.integrations.patches;
|
||||
|
||||
import static app.revanced.integrations.utils.StringRef.str;
|
||||
|
||||
import android.os.Build;
|
||||
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
public class CopyVideoUrlPatch {
|
||||
public static void copyUrl(Boolean withTimestamp) {
|
||||
|
||||
public static void copyUrl(boolean withTimestamp) {
|
||||
try {
|
||||
String url = String.format("https://youtu.be/%s", VideoInformation.getVideoId());
|
||||
if (withTimestamp) {
|
||||
long seconds = VideoInformation.getVideoTime() / 1000;
|
||||
url += String.format("?t=%s", seconds);
|
||||
StringBuilder builder = new StringBuilder("https://youtu.be/");
|
||||
builder.append(VideoInformation.getVideoId());
|
||||
final long currentVideoTimeInSeconds = VideoInformation.getVideoTime() / 1000;
|
||||
if (withTimestamp && currentVideoTimeInSeconds > 0) {
|
||||
final long hour = currentVideoTimeInSeconds / (60 * 60);
|
||||
final long minute = (currentVideoTimeInSeconds / 60) % 60;
|
||||
final long second = currentVideoTimeInSeconds % 60;
|
||||
builder.append("?t=");
|
||||
if (hour > 0) {
|
||||
builder.append(hour).append("h");
|
||||
}
|
||||
if (minute > 0) {
|
||||
builder.append(minute).append("m");
|
||||
}
|
||||
if (second > 0) {
|
||||
builder.append(second).append("s");
|
||||
}
|
||||
}
|
||||
|
||||
ReVancedUtils.setClipboard(url);
|
||||
ReVancedUtils.showToastShort(str("share_copy_url_success"));
|
||||
ReVancedUtils.setClipboard(builder.toString());
|
||||
// Do not show a toast if using Android 13+ as it shows it's own toast.
|
||||
// But if the user copied with a timestamp then show a toast.
|
||||
// Unfortunately this will show 2 toasts on Android 13+, but no way around this.
|
||||
if (Build.VERSION.SDK_INT <= Build.VERSION_CODES.S_V2 || (withTimestamp && currentVideoTimeInSeconds > 0)) {
|
||||
ReVancedUtils.showToastShort(withTimestamp && currentVideoTimeInSeconds > 0
|
||||
? str("revanced_share_copy_url_timestamp_success")
|
||||
: str("revanced_share_copy_url_success"));
|
||||
}
|
||||
} catch (Exception e) {
|
||||
LogHelper.printException(() -> "Failed to generate video url", e);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -4,10 +4,13 @@ import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public class DisableAutoCaptionsPatch {
|
||||
|
||||
/**
|
||||
* Used by injected code. Do not delete.
|
||||
*/
|
||||
public static boolean captionsButtonDisabled;
|
||||
|
||||
public static boolean autoCaptionsEnabled() {
|
||||
return SettingsEnum.CAPTIONS_ENABLED.getBoolean();
|
||||
return SettingsEnum.AUTO_CAPTIONS.getBoolean();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -5,6 +5,6 @@ import app.revanced.integrations.settings.SettingsEnum;
|
||||
public class DisableStartupShortsPlayerPatch {
|
||||
//Used by app.revanced.patches.youtube.layout.startupshortsreset.patch.DisableShortsOnStartupPatch
|
||||
public static boolean disableStartupShortsPlayer() {
|
||||
return SettingsEnum.DISABLE_STARTUP_SHORTS_PLAYER.getBoolean();
|
||||
return SettingsEnum.DISABLE_RESUMING_SHORTS_PLAYER.getBoolean();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,189 +0,0 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import android.view.View;
|
||||
import app.revanced.integrations.adremover.AdRemoverAPI;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
public final class GeneralAdsPatch extends Filter {
|
||||
private final String[] IGNORE = {
|
||||
"home_video_with_context",
|
||||
"related_video_with_context",
|
||||
"comment_thread", // skip blocking anything in the comments
|
||||
"|comment.", // skip blocking anything in the comments replies
|
||||
"library_recent_shelf",
|
||||
};
|
||||
|
||||
private final BlockRule custom = new CustomBlockRule(
|
||||
SettingsEnum.ADREMOVER_CUSTOM_ENABLED,
|
||||
SettingsEnum.ADREMOVER_CUSTOM_REMOVAL
|
||||
);
|
||||
|
||||
public GeneralAdsPatch() {
|
||||
var communityPosts = new BlockRule(SettingsEnum.ADREMOVER_COMMUNITY_POSTS_REMOVAL, "post_base_wrapper");
|
||||
var communityGuidelines = new BlockRule(SettingsEnum.ADREMOVER_COMMUNITY_GUIDELINES_REMOVAL, "community_guidelines");
|
||||
var subscribersCommunityGuidelines = new BlockRule(SettingsEnum.ADREMOVER_SUBSCRIBERS_COMMUNITY_GUIDELINES_REMOVAL, "sponsorships_comments_upsell");
|
||||
var channelMemberShelf = new BlockRule(SettingsEnum.ADREMOVER_CHANNEL_MEMBER_SHELF_REMOVAL, "member_recognition_shelf");
|
||||
var compactBanner = new BlockRule(SettingsEnum.ADREMOVER_COMPACT_BANNER_REMOVAL, "compact_banner");
|
||||
var inFeedSurvey = new BlockRule(SettingsEnum.ADREMOVER_FEED_SURVEY_REMOVAL, "in_feed_survey", "slimline_survey");
|
||||
var medicalPanel = new BlockRule(SettingsEnum.ADREMOVER_MEDICAL_PANEL_REMOVAL, "medical_panel");
|
||||
var paidContent = new BlockRule(SettingsEnum.ADREMOVER_PAID_CONTENT_REMOVAL, "paid_content_overlay");
|
||||
var merchandise = new BlockRule(SettingsEnum.ADREMOVER_MERCHANDISE_REMOVAL, "product_carousel");
|
||||
var infoPanel = new BlockRule(SettingsEnum.ADREMOVER_INFO_PANEL_REMOVAL, "publisher_transparency_panel", "single_item_information_panel");
|
||||
var latestPosts = new BlockRule(SettingsEnum.ADREMOVER_HIDE_LATEST_POSTS, "post_shelf");
|
||||
var channelGuidelines = new BlockRule(SettingsEnum.ADREMOVER_HIDE_CHANNEL_GUIDELINES, "channel_guidelines_entry_banner");
|
||||
var artistCard = new BlockRule(SettingsEnum.HIDE_ARTIST_CARDS, "official_card");
|
||||
var selfSponsor = new BlockRule(SettingsEnum.ADREMOVER_SELF_SPONSOR_REMOVAL, "cta_shelf_card");
|
||||
var chapterTeaser = new BlockRule(SettingsEnum.ADREMOVER_CHAPTER_TEASER_REMOVAL, "expandable_metadata", "macro_markers_carousel");
|
||||
var viewProducts = new BlockRule(SettingsEnum.ADREMOVER_VIEW_PRODUCTS, "product_item", "products_in_video");
|
||||
var webLinkPanel = new BlockRule(SettingsEnum.ADREMOVER_WEB_SEARCH_RESULTS, "web_link_panel");
|
||||
var channelBar = new BlockRule(SettingsEnum.ADREMOVER_CHANNEL_BAR, "channel_bar");
|
||||
var relatedVideos = new BlockRule(SettingsEnum.ADREMOVER_RELATED_VIDEOS, "fullscreen_related_videos");
|
||||
var quickActions = new BlockRule(SettingsEnum.ADREMOVER_QUICK_ACTIONS, "quick_actions");
|
||||
var imageShelf = new BlockRule(SettingsEnum.ADREMOVER_IMAGE_SHELF, "image_shelf");
|
||||
var graySeparator = new BlockRule(SettingsEnum.ADREMOVER_GRAY_SEPARATOR,
|
||||
"cell_divider" // layout residue (gray line above the buttoned ad),
|
||||
);
|
||||
var buttonedAd = new BlockRule(SettingsEnum.ADREMOVER_BUTTONED_REMOVAL,
|
||||
"_buttoned_layout",
|
||||
"full_width_square_image_layout",
|
||||
"_ad_with",
|
||||
"video_display_button_group_layout",
|
||||
"landscape_image_wide_button_layout"
|
||||
);
|
||||
var generalAds = new BlockRule(
|
||||
SettingsEnum.ADREMOVER_GENERAL_ADS_REMOVAL,
|
||||
"ads_video_with_context",
|
||||
"banner_text_icon",
|
||||
"square_image_layout",
|
||||
"watch_metadata_app_promo",
|
||||
"video_display_full_layout",
|
||||
"hero_promo_image",
|
||||
"statement_banner",
|
||||
"carousel_footered_layout",
|
||||
"text_image_button_layout",
|
||||
"primetime_promo",
|
||||
"feature_grid_interstitial",
|
||||
"product_details",
|
||||
"brand_video_shelf"
|
||||
);
|
||||
var movieAds = new BlockRule(
|
||||
SettingsEnum.ADREMOVER_MOVIE_REMOVAL,
|
||||
"browsy_bar",
|
||||
"compact_movie",
|
||||
"horizontal_movie_shelf",
|
||||
"movie_and_show_upsell_card",
|
||||
"compact_tvfilm_item",
|
||||
"offer_module_root"
|
||||
);
|
||||
|
||||
this.pathRegister.registerAll(
|
||||
generalAds,
|
||||
buttonedAd,
|
||||
channelBar,
|
||||
communityPosts,
|
||||
paidContent,
|
||||
latestPosts,
|
||||
movieAds,
|
||||
chapterTeaser,
|
||||
communityGuidelines,
|
||||
quickActions,
|
||||
relatedVideos,
|
||||
compactBanner,
|
||||
inFeedSurvey,
|
||||
viewProducts,
|
||||
medicalPanel,
|
||||
merchandise,
|
||||
infoPanel,
|
||||
channelGuidelines,
|
||||
artistCard,
|
||||
selfSponsor,
|
||||
webLinkPanel,
|
||||
imageShelf,
|
||||
subscribersCommunityGuidelines,
|
||||
channelMemberShelf
|
||||
);
|
||||
|
||||
var carouselAd = new BlockRule(SettingsEnum.ADREMOVER_GENERAL_ADS_REMOVAL,
|
||||
"carousel_ad"
|
||||
);
|
||||
var shorts = new BlockRule(SettingsEnum.ADREMOVER_SHORTS_REMOVAL,
|
||||
"reels_player_overlay",
|
||||
"shorts_shelf",
|
||||
"inline_shorts",
|
||||
"shorts_grid"
|
||||
);
|
||||
|
||||
this.identifierRegister.registerAll(
|
||||
shorts,
|
||||
graySeparator,
|
||||
carouselAd
|
||||
);
|
||||
}
|
||||
|
||||
public boolean filter(final String path, final String identifier) {
|
||||
BlockResult result;
|
||||
|
||||
if (custom.isEnabled() && custom.check(path).isBlocked())
|
||||
result = BlockResult.CUSTOM;
|
||||
else if (ReVancedUtils.containsAny(path, IGNORE))
|
||||
result = BlockResult.IGNORED;
|
||||
else if (pathRegister.contains(path) || identifierRegister.contains(identifier))
|
||||
result = BlockResult.DEFINED;
|
||||
else
|
||||
result = BlockResult.UNBLOCKED;
|
||||
|
||||
LogHelper.printDebug(() -> String.format("%s (ID: %s): %s", result.message, identifier, path));
|
||||
|
||||
return result.filter;
|
||||
}
|
||||
|
||||
private enum BlockResult {
|
||||
UNBLOCKED(false, "Unblocked"),
|
||||
IGNORED(false, "Ignored"),
|
||||
DEFINED(true, "Blocked"),
|
||||
CUSTOM(true, "Custom");
|
||||
|
||||
final Boolean filter;
|
||||
final String message;
|
||||
|
||||
BlockResult(boolean filter, String message) {
|
||||
this.filter = filter;
|
||||
this.message = message;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Hide a view.
|
||||
*
|
||||
* @param condition The setting to check for hiding the view.
|
||||
* @param view The view to hide.
|
||||
*/
|
||||
private static void hideView(SettingsEnum condition, View view) {
|
||||
if (!condition.getBoolean()) return;
|
||||
|
||||
LogHelper.printDebug(() -> "Hiding view with setting: " + condition);
|
||||
|
||||
AdRemoverAPI.HideViewWithLayout1dp(view);
|
||||
}
|
||||
|
||||
/**
|
||||
* Hide the view, which shows ads in the homepage.
|
||||
*
|
||||
* @param view The view, which shows ads.
|
||||
*/
|
||||
public static void hideAdAttributionView(View view) {
|
||||
hideView(SettingsEnum.ADREMOVER_GENERAL_ADS_REMOVAL, view);
|
||||
}
|
||||
|
||||
/**
|
||||
* Hide the view, which shows reels in the homepage.
|
||||
*
|
||||
* @param view The view, which shows reels.
|
||||
*/
|
||||
public static void hideReelView(View view) {
|
||||
hideView(SettingsEnum.ADREMOVER_SHORTS_REMOVAL, view);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -21,7 +21,7 @@ public class HDRAutoBrightnessPatch {
|
||||
*/
|
||||
public static float getHDRBrightness(float original) {
|
||||
// do nothing if disabled
|
||||
if (!SettingsEnum.USE_HDR_AUTO_BRIGHTNESS.getBoolean()) {
|
||||
if (!SettingsEnum.HDR_AUTO_BRIGHTNESS.getBoolean()) {
|
||||
return original;
|
||||
}
|
||||
|
||||
|
||||
@@ -2,13 +2,12 @@ package app.revanced.integrations.patches;
|
||||
|
||||
import android.view.View;
|
||||
|
||||
import app.revanced.integrations.adremover.AdRemoverAPI;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
public class HideAlbumCardsPatch {
|
||||
//Used by app.revanced.patches.youtube.layout.hidealbumcards.patch.HideAlbumCardsPatch
|
||||
public static void hideAlbumCards(View view) {
|
||||
public static void hideAlbumCard(View view) {
|
||||
if (!SettingsEnum.HIDE_ALBUM_CARDS.getBoolean()) return;
|
||||
AdRemoverAPI.HideViewWithLayout1dp(view);
|
||||
ReVancedUtils.hideViewByLayoutParams(view);
|
||||
}
|
||||
}
|
||||
@@ -2,13 +2,28 @@ package app.revanced.integrations.patches;
|
||||
|
||||
import android.view.View;
|
||||
|
||||
import app.revanced.integrations.adremover.AdRemoverAPI;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
public class HideBreakingNewsPatch {
|
||||
//Used by app.revanced.patches.youtube.layout.homepage.breakingnews.patch.BreakingNewsPatch
|
||||
|
||||
/**
|
||||
* When spoofing to app versions older than 17.30.35, the watch history preview bar uses
|
||||
* the same layout components as the breaking news shelf.
|
||||
*
|
||||
* Breaking news does not appear to be present in these older versions anyways.
|
||||
*/
|
||||
private static boolean isSpoofingOldVersionWithHorizontalCardListWatchHistory() {
|
||||
return SettingsEnum.SPOOF_APP_VERSION.getBoolean()
|
||||
&& SettingsEnum.SPOOF_APP_VERSION_TARGET.getString().compareTo("17.30.35") < 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Injection point.
|
||||
*/
|
||||
public static void hideBreakingNews(View view) {
|
||||
if (!SettingsEnum.HIDE_BREAKING_NEWS.getBoolean()) return;
|
||||
AdRemoverAPI.HideViewWithLayout1dp(view);
|
||||
if (!SettingsEnum.HIDE_BREAKING_NEWS.getBoolean()
|
||||
|| isSpoofingOldVersionWithHorizontalCardListWatchHistory()) return;
|
||||
ReVancedUtils.hideViewByLayoutParams(view);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,16 +0,0 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import android.view.View;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
|
||||
public class HideCreateButtonPatch {
|
||||
|
||||
//Used by app.revanced.patches.youtube.layout.createbutton.patch.CreateButtonRemoverPatch
|
||||
public static void hideCreateButton(View view) {
|
||||
boolean hidden = SettingsEnum.HIDE_CREATE_BUTTON.getBoolean();
|
||||
LogHelper.printDebug(() -> "Create button: " + (hidden ? "hidden" : "shown"));
|
||||
view.setVisibility(hidden ? View.GONE : View.VISIBLE);
|
||||
}
|
||||
}
|
||||
@@ -2,13 +2,13 @@ package app.revanced.integrations.patches;
|
||||
|
||||
import android.view.View;
|
||||
|
||||
import app.revanced.integrations.adremover.AdRemoverAPI;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
public class HideCrowdfundingBoxPatch {
|
||||
//Used by app.revanced.patches.youtube.layout.hidecrowdfundingbox.patch.HideCrowdfundingBoxPatch
|
||||
public static void hideCrowdfundingBox(View view) {
|
||||
if (!SettingsEnum.HIDE_CROWDFUNDING_BOX.getBoolean()) return;
|
||||
AdRemoverAPI.HideViewWithLayout1dp(view);
|
||||
ReVancedUtils.hideViewByLayoutParams(view);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,25 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import android.view.View;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
public final class HideFilterBarPatch {
|
||||
public static int hideInFeed(final int height) {
|
||||
if (SettingsEnum.HIDE_FILTER_BAR_FEED_IN_FEED.getBoolean()) return 0;
|
||||
|
||||
return height;
|
||||
}
|
||||
|
||||
public static void hideInRelatedVideos(final View chipView) {
|
||||
if (!SettingsEnum.HIDE_FILTER_BAR_FEED_IN_RELATED_VIDEOS.getBoolean()) return;
|
||||
|
||||
ReVancedUtils.hideViewByLayoutParams(chipView);
|
||||
}
|
||||
|
||||
public static int hideInSearch(final int height) {
|
||||
if (SettingsEnum.HIDE_FILTER_BAR_FEED_IN_SEARCH.getBoolean()) return 0;
|
||||
|
||||
return height;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public class HideGetPremiumPatch {
|
||||
/**
|
||||
* Injection point.
|
||||
*/
|
||||
public static boolean hideGetPremiumView() {
|
||||
return SettingsEnum.HIDE_GET_PREMIUM.getBoolean();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import android.view.View;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
public class HideLoadMoreButtonPatch {
|
||||
public static void hideLoadMoreButton(View view){
|
||||
if(!SettingsEnum.HIDE_LOAD_MORE_BUTTON.getBoolean()) return;
|
||||
ReVancedUtils.hideViewByLayoutParams(view);
|
||||
}
|
||||
}
|
||||
@@ -1,11 +1,16 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public final class HidePlayerButtonsPatch {
|
||||
|
||||
public static boolean hideButtons() {
|
||||
return SettingsEnum.HIDE_PLAYER_BUTTONS.getBoolean();
|
||||
/**
|
||||
* Injection point.
|
||||
*/
|
||||
public static boolean previousOrNextButtonIsVisible(boolean previousOrNextButtonVisible) {
|
||||
if (SettingsEnum.HIDE_PLAYER_BUTTONS.getBoolean()) {
|
||||
return false;
|
||||
}
|
||||
return previousOrNextButtonVisible;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,12 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import android.widget.ImageView;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public class HidePlayerOverlayPatch {
|
||||
public static void hidePlayerOverlay(ImageView view) {
|
||||
if (!SettingsEnum.HIDE_PLAYER_OVERLAY.getBoolean()) return;
|
||||
view.setImageResource(android.R.color.transparent);
|
||||
}
|
||||
}
|
||||
@@ -1,24 +0,0 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
|
||||
import android.view.View;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
|
||||
public class HideShortsButtonPatch {
|
||||
|
||||
// Used by app.revanced.patches.youtube.layout.shorts.button.patch.ShortsButtonRemoverPatch
|
||||
public static void hideShortsButton(View view) {
|
||||
if (lastPivotTab != null && lastPivotTab.name() == "TAB_SHORTS") {
|
||||
boolean hide = SettingsEnum.HIDE_SHORTS_BUTTON.getBoolean();
|
||||
LogHelper.printDebug(() -> hide ? "Shorts button: hidden" : "Shorts button: shown");
|
||||
if (hide) {
|
||||
view.setVisibility(View.GONE);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//Needed for the ShortsButtonRemoverPatch
|
||||
public static Enum lastPivotTab;
|
||||
}
|
||||
@@ -1,13 +0,0 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import android.view.View;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public class HideShortsCommentsButtonPatch {
|
||||
//Used by app.revanced.patches.youtube.layout.comments.patch.CommentsPatch
|
||||
public static void hideShortsCommentsButton(View view) {
|
||||
if (!SettingsEnum.HIDE_SHORTS_COMMENTS_BUTTON.getBoolean()) return;
|
||||
view.setVisibility(View.GONE);
|
||||
}
|
||||
}
|
||||
@@ -1,140 +0,0 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import android.os.Build;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.RequiresApi;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Iterator;
|
||||
import java.util.Spliterator;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
class BlockRule {
|
||||
final static class BlockResult {
|
||||
private final boolean blocked;
|
||||
private final SettingsEnum setting;
|
||||
|
||||
public BlockResult(final SettingsEnum setting, final boolean blocked) {
|
||||
this.setting = setting;
|
||||
this.blocked = blocked;
|
||||
}
|
||||
|
||||
public SettingsEnum getSetting() {
|
||||
return setting;
|
||||
}
|
||||
|
||||
public boolean isBlocked() {
|
||||
return blocked;
|
||||
}
|
||||
}
|
||||
|
||||
protected final SettingsEnum setting;
|
||||
private final String[] blocks;
|
||||
|
||||
/**
|
||||
* Initialize a new rule for components.
|
||||
*
|
||||
* @param setting The setting which controls the blocking of this component.
|
||||
* @param blocks The rules to block the component on.
|
||||
*/
|
||||
public BlockRule(final SettingsEnum setting, final String... blocks) {
|
||||
this.setting = setting;
|
||||
this.blocks = blocks;
|
||||
}
|
||||
|
||||
public boolean isEnabled() {
|
||||
return setting.getBoolean();
|
||||
}
|
||||
|
||||
public BlockResult check(final String string) {
|
||||
return new BlockResult(setting, string != null && ReVancedUtils.containsAny(string, blocks));
|
||||
}
|
||||
}
|
||||
|
||||
final class CustomBlockRule extends BlockRule {
|
||||
/**
|
||||
* Initialize a new rule for components.
|
||||
*
|
||||
* @param setting The setting which controls the blocking of the components.
|
||||
* @param filter The setting which contains the list of component names.
|
||||
*/
|
||||
public CustomBlockRule(final SettingsEnum setting, final SettingsEnum filter) {
|
||||
super(setting, filter.getString().split(","));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
abstract class Filter {
|
||||
final protected LithoBlockRegister pathRegister = new LithoBlockRegister();
|
||||
final protected LithoBlockRegister identifierRegister = new LithoBlockRegister();
|
||||
|
||||
abstract boolean filter(final String path, final String identifier);
|
||||
}
|
||||
|
||||
final class LithoBlockRegister implements Iterable<BlockRule> {
|
||||
private final ArrayList<BlockRule> blocks = new ArrayList<>();
|
||||
|
||||
public void registerAll(BlockRule... blocks) {
|
||||
this.blocks.addAll(Arrays.asList(blocks));
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Iterator<BlockRule> iterator() {
|
||||
return blocks.iterator();
|
||||
}
|
||||
|
||||
@RequiresApi(api = Build.VERSION_CODES.N)
|
||||
@Override
|
||||
public void forEach(@NonNull Consumer<? super BlockRule> action) {
|
||||
blocks.forEach(action);
|
||||
}
|
||||
|
||||
@RequiresApi(api = Build.VERSION_CODES.N)
|
||||
@NonNull
|
||||
@Override
|
||||
public Spliterator<BlockRule> spliterator() {
|
||||
return blocks.spliterator();
|
||||
}
|
||||
|
||||
public boolean contains(String path) {
|
||||
for (var rule : this) {
|
||||
if (!rule.isEnabled()) continue;
|
||||
|
||||
var result = rule.check(path);
|
||||
if (result.isBlocked()) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public final class LithoFilterPatch {
|
||||
private static final Filter[] filters = new Filter[]{
|
||||
new GeneralAdsPatch(),
|
||||
new ButtonsPatch(),
|
||||
new CommentsPatch(),
|
||||
};
|
||||
|
||||
public static boolean filter(final StringBuilder pathBuilder, final String identifier) {
|
||||
var path = pathBuilder.toString();
|
||||
if (path.isEmpty()) return false;
|
||||
|
||||
LogHelper.printDebug(() -> String.format("Searching (ID: %s): %s", identifier, path));
|
||||
|
||||
for (var filter : filters) {
|
||||
if (filter.filter(path, identifier)) return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,6 +2,7 @@ package app.revanced.integrations.patches;
|
||||
|
||||
import static app.revanced.integrations.utils.StringRef.str;
|
||||
|
||||
import android.annotation.TargetApi;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.content.pm.PackageManager;
|
||||
@@ -28,6 +29,7 @@ public class MicroGSupport {
|
||||
context.startActivity(intent);
|
||||
}
|
||||
|
||||
@TargetApi(26)
|
||||
public static void checkAvailability() {
|
||||
var context = Objects.requireNonNull(ReVancedUtils.getContext());
|
||||
|
||||
@@ -41,10 +43,11 @@ public class MicroGSupport {
|
||||
System.exit(0);
|
||||
}
|
||||
|
||||
|
||||
try (var client = context.getContentResolver().acquireContentProviderClient(VANCED_MICROG_PROVIDER)) {
|
||||
if (client != null) return;
|
||||
LogHelper.printInfo(() -> "Vanced MicroG is not running in the background");
|
||||
startIntent(context, DONT_KILL_MY_APP_LINK, str("microg_not_running_warning"));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
|
||||
import android.view.View;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public final class NavigationButtonsPatch {
|
||||
public static Enum lastNavigationButton;
|
||||
|
||||
public static void hideCreateButton(final View view) {
|
||||
view.setVisibility(SettingsEnum.HIDE_CREATE_BUTTON.getBoolean() ? View.GONE : View.VISIBLE);
|
||||
}
|
||||
|
||||
public static boolean switchCreateWithNotificationButton() {
|
||||
return SettingsEnum.SWITCH_CREATE_WITH_NOTIFICATIONS_BUTTON.getBoolean();
|
||||
}
|
||||
|
||||
public static void hideButton(final View buttonView) {
|
||||
if (lastNavigationButton == null) return;
|
||||
|
||||
for (NavigationButton button : NavigationButton.values())
|
||||
if (button.name.equals(lastNavigationButton.name()))
|
||||
if (button.enabled) buttonView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
private enum NavigationButton {
|
||||
HOME("PIVOT_HOME", SettingsEnum.HIDE_HOME_BUTTON.getBoolean()),
|
||||
SHORTS("TAB_SHORTS", SettingsEnum.HIDE_SHORTS_BUTTON.getBoolean()),
|
||||
SUBSCRIPTIONS("PIVOT_SUBSCRIPTIONS", SettingsEnum.HIDE_SUBSCRIPTIONS_BUTTON.getBoolean());
|
||||
private final boolean enabled;
|
||||
private final String name;
|
||||
|
||||
NavigationButton(final String name, final boolean enabled) {
|
||||
this.name = name;
|
||||
this.enabled = enabled;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -13,7 +13,7 @@ public class OpenLinksExternallyPatch {
|
||||
* @return The new, default service to open links with or the original service.
|
||||
*/
|
||||
public static String enableExternalBrowser(String original) {
|
||||
if (SettingsEnum.ENABLE_EXTERNAL_BROWSER.getBoolean()) original = "";
|
||||
if (SettingsEnum.EXTERNAL_BROWSER.getBoolean()) original = "";
|
||||
return original;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -15,7 +15,7 @@ import app.revanced.integrations.shared.PlayerOverlays;
|
||||
@SuppressWarnings("unused")
|
||||
public class PlayerOverlaysHookPatch {
|
||||
/**
|
||||
* Hook into YouTubePlayerOverlaysLayout.onFinishInflate() method
|
||||
* Injection point.
|
||||
*
|
||||
* @param thisRef reference to the view
|
||||
* @smali YouTubePlayerOverlaysLayout_onFinishInflateHook(Ljava / lang / Object ;)V
|
||||
|
||||
@@ -3,32 +3,25 @@ package app.revanced.integrations.patches;
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
import app.revanced.integrations.shared.PlayerType;
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
import app.revanced.integrations.shared.VideoState;
|
||||
|
||||
/**
|
||||
* Hook receiver class for 'player-type-hook' patch
|
||||
*
|
||||
* @usedBy app.revanced.patches.youtube.misc.playertype.patch.PlayerTypeHookPatch
|
||||
* @smali Lapp/revanced/integrations/patches/PlayerTypeHookPatch;
|
||||
*/
|
||||
@SuppressWarnings("unused")
|
||||
public class PlayerTypeHookPatch {
|
||||
/**
|
||||
* Hook into YouTubePlayerOverlaysLayout.updatePlayerLayout() method
|
||||
*
|
||||
* @param type the new player type
|
||||
* @smali YouTubePlayerOverlaysLayout_updatePlayerTypeHookEX(Ljava/lang/Object;)V
|
||||
* Injection point.
|
||||
*/
|
||||
public static void YouTubePlayerOverlaysLayout_updatePlayerTypeHookEX(@Nullable Object type) {
|
||||
if (type == null) return;
|
||||
public static void setPlayerType(@Nullable Enum<?> youTubePlayerType) {
|
||||
if (youTubePlayerType == null) return;
|
||||
|
||||
// update current player type
|
||||
final PlayerType newType = PlayerType.safeParseFromString(type.toString());
|
||||
if (newType == null) {
|
||||
LogHelper.printException(() -> "Unknown PlayerType encountered: " + type);
|
||||
} else {
|
||||
PlayerType.setCurrent(newType);
|
||||
LogHelper.printDebug(() -> "PlayerType was updated to: " + newType);
|
||||
}
|
||||
PlayerType.setFromString(youTubePlayerType.name());
|
||||
}
|
||||
|
||||
/**
|
||||
* Injection point.
|
||||
*/
|
||||
public static void setVideoState(@Nullable Enum<?> youTubeVideoState) {
|
||||
if (youTubeVideoState == null) return;
|
||||
|
||||
VideoState.setFromString(youTubeVideoState.name());
|
||||
}
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user