You've already forked revanced-integrations
mirror of
https://github.com/revanced/revanced-integrations
synced 2025-11-19 03:23:27 +01:00
Compare commits
141 Commits
v0.77.1
...
v0.94.0-de
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
f92498d47b | ||
|
|
923e4b99e6 | ||
|
|
9af105dd03 | ||
|
|
d12d74747a | ||
|
|
42346ee3cf | ||
|
|
dbf1f3f0ce | ||
|
|
a70e80dfa0 | ||
|
|
7551f0104c | ||
|
|
d8bd27251c | ||
|
|
04147c17c9 | ||
|
|
32dc8a846c | ||
|
|
03764bcc65 | ||
|
|
0127e7251c | ||
|
|
6e31b7889a | ||
|
|
057e599aec | ||
|
|
4cbe8338b3 | ||
|
|
d65a107c53 | ||
|
|
559bbf9778 | ||
|
|
737246636b | ||
|
|
c2d121f32b | ||
|
|
0af87e2908 | ||
|
|
6960b0bda5 | ||
|
|
5b9a0d3d23 | ||
|
|
9480f20d44 | ||
|
|
557c311825 | ||
|
|
62eb76415c | ||
|
|
5d2cc2ca5d | ||
|
|
09afccce27 | ||
|
|
f393d3790a | ||
|
|
d33c69f8c2 | ||
|
|
b56f472813 | ||
|
|
803130a693 | ||
|
|
8032a3f46a | ||
|
|
d72937c2fd | ||
|
|
fd818a35f5 | ||
|
|
a80fab7070 | ||
|
|
c3eff913dd | ||
|
|
2a16da15d9 | ||
|
|
d076fe0dce | ||
|
|
e833d16bb8 | ||
|
|
bcd93db9b8 | ||
|
|
212d3a72d8 | ||
|
|
758b645913 | ||
|
|
e9fd05f4c6 | ||
|
|
31df68d2c3 | ||
|
|
56c1a3c03c | ||
|
|
915b8d371a | ||
|
|
eea37a9bad | ||
|
|
05cca001ac | ||
|
|
a45a354d19 | ||
|
|
070e1666b7 | ||
|
|
b5c0c843a5 | ||
|
|
2e74fc55eb | ||
|
|
114a1c4004 | ||
|
|
f5c5fcb5e4 | ||
|
|
954e60191e | ||
|
|
499a4deab3 | ||
|
|
01f79a3398 | ||
|
|
8f8e8ea87e | ||
|
|
0fc94e2305 | ||
|
|
25604cec0a | ||
|
|
dd11c6e062 | ||
|
|
64c31b84e7 | ||
|
|
843dd9de9e | ||
|
|
bc635a79c5 | ||
|
|
4c18633c36 | ||
|
|
4a3d20e1f0 | ||
|
|
8de014583e | ||
|
|
993aadd4df | ||
|
|
89f866d739 | ||
|
|
6fd81770bf | ||
|
|
a600239bbf | ||
|
|
cb560ff097 | ||
|
|
a9f55d7512 | ||
|
|
fcc5337d76 | ||
|
|
76c36daee0 | ||
|
|
f6335267f2 | ||
|
|
e856d9dccd | ||
|
|
1f74ccf800 | ||
|
|
240c3888cb | ||
|
|
b839600728 | ||
|
|
a26975611e | ||
|
|
8d233a2f82 | ||
|
|
115af48d86 | ||
|
|
c9bd832ee5 | ||
|
|
35fb757258 | ||
|
|
87799e5c55 | ||
|
|
311524c2c9 | ||
|
|
b9fa8d6c09 | ||
|
|
f122598e08 | ||
|
|
12ee45bb68 | ||
|
|
eec90ee04c | ||
|
|
0682c4c671 | ||
|
|
59031d95ea | ||
|
|
38e3906240 | ||
|
|
5ed6a57df2 | ||
|
|
33b99f0061 | ||
|
|
f4e8afe7ba | ||
|
|
878ac2a9fa | ||
|
|
b663880741 | ||
|
|
9ab8a646ed | ||
|
|
2002bf8063 | ||
|
|
693ef08c6c | ||
|
|
84377b2da4 | ||
|
|
71e81a6473 | ||
|
|
5839f6ca4a | ||
|
|
d125d20974 | ||
|
|
5dd68e23f8 | ||
|
|
98ce2df47d | ||
|
|
0a6022c258 | ||
|
|
a550d16c3f | ||
|
|
04a89af1c9 | ||
|
|
bf368e8dd4 | ||
|
|
4afa162f46 | ||
|
|
66f5808863 | ||
|
|
57c56b630a | ||
|
|
edaf70fd10 | ||
|
|
c309646d35 | ||
|
|
934b981605 | ||
|
|
57969661dd | ||
|
|
376168fecf | ||
|
|
e8342ec15b | ||
|
|
d64a0f9599 | ||
|
|
b93b03dc19 | ||
|
|
a098594706 | ||
|
|
8805851a09 | ||
|
|
a9d24872a8 | ||
|
|
080e22b1bf | ||
|
|
5a028ab834 | ||
|
|
7840bc48ba | ||
|
|
718c5a75c1 | ||
|
|
2f32786661 | ||
|
|
3a2536a86e | ||
|
|
37869dc5b8 | ||
|
|
9dc9ce364c | ||
|
|
00ea006b8c | ||
|
|
617a4eb5d0 | ||
|
|
1351358268 | ||
|
|
35aa4f92c6 | ||
|
|
bca96cc8b4 | ||
|
|
cea3a5edc7 |
25
.github/workflows/pull_request.yml
vendored
Normal file
25
.github/workflows/pull_request.yml
vendored
Normal file
@@ -0,0 +1,25 @@
|
||||
name: PR to main
|
||||
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- dev
|
||||
workflow_dispatch:
|
||||
|
||||
env:
|
||||
MESSAGE: merge branch `${{ github.head_ref || github.ref_name }}` to `main`
|
||||
|
||||
jobs:
|
||||
pull-request:
|
||||
name: Open pull request
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@v3
|
||||
- name: Open pull request
|
||||
uses: repo-sync/pull-request@v2
|
||||
with:
|
||||
destination_branch: 'main'
|
||||
pr_title: 'chore: ${{ env.MESSAGE }}'
|
||||
pr_body: 'This pull request will ${{ env.MESSAGE }}.'
|
||||
pr_draft: true
|
||||
27
.github/workflows/release.yml
vendored
27
.github/workflows/release.yml
vendored
@@ -12,29 +12,32 @@ on:
|
||||
- dev
|
||||
|
||||
jobs:
|
||||
build:
|
||||
release:
|
||||
name: Release
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Cancel Previous Runs
|
||||
- name: Cancel previou runs
|
||||
uses: styfle/cancel-workflow-action@0.11.0
|
||||
with:
|
||||
access_token: ${{ secrets.GITHUB_TOKEN }}
|
||||
- name: Checkout Repo
|
||||
- name: Checkout
|
||||
uses: actions/checkout@v3
|
||||
- name: Set up JDK 11
|
||||
with:
|
||||
# Make sure the release step uses its own credentials:
|
||||
# https://github.com/cycjimmy/semantic-release-action#private-packages
|
||||
persist-credentials: false
|
||||
fetch-depth: 0
|
||||
- name: Set up JDK
|
||||
uses: actions/setup-java@v3
|
||||
with:
|
||||
java-version: '11'
|
||||
java-version: '17'
|
||||
distribution: 'zulu'
|
||||
- name: Setup Node.js
|
||||
uses: actions/setup-node@v3
|
||||
with:
|
||||
node-version: "lts/*"
|
||||
- name: Build with Gradle
|
||||
run: ./gradlew --no-daemon build
|
||||
node-version: "latest"
|
||||
cache: 'npm'
|
||||
- name: Setup semantic-release
|
||||
run: npm install -g semantic-release @semantic-release/git @semantic-release/changelog gradle-semantic-release-plugin -D
|
||||
run: npm install semantic-release@19.0.5 @saithodev/semantic-release-backmerge @semantic-release/git @semantic-release/changelog gradle-semantic-release-plugin@1.7.4 -D
|
||||
- name: Release
|
||||
env:
|
||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||
GITHUB_TOKEN: ${{ secrets.REPOSITORY_PUSH_ACCESS }}
|
||||
run: npx semantic-release
|
||||
|
||||
16
.releaserc
16
.releaserc
@@ -7,11 +7,7 @@
|
||||
}
|
||||
],
|
||||
"plugins": [
|
||||
["@semantic-release/commit-analyzer", {
|
||||
"releaseRules": [
|
||||
{"type": "build", "release": "patch"}
|
||||
]
|
||||
}],
|
||||
"@semantic-release/commit-analyzer",
|
||||
"@semantic-release/release-notes-generator",
|
||||
"@semantic-release/changelog",
|
||||
"gradle-semantic-release-plugin",
|
||||
@@ -31,7 +27,15 @@
|
||||
{
|
||||
"path": "app/build/outputs/apk/release/*.apk"
|
||||
}
|
||||
]
|
||||
],
|
||||
successComment: false
|
||||
}
|
||||
],
|
||||
[
|
||||
"@saithodev/semantic-release-backmerge",
|
||||
{
|
||||
branches: [{from: "main", to: "dev"}],
|
||||
clearWorkspace: true
|
||||
}
|
||||
]
|
||||
]
|
||||
|
||||
359
CHANGELOG.md
359
CHANGELOG.md
File diff suppressed because it is too large
Load Diff
@@ -8,29 +8,31 @@ plugins {
|
||||
|
||||
android {
|
||||
compileSdk = 33
|
||||
buildToolsVersion = "33.0.0"
|
||||
buildToolsVersion = "33.0.1"
|
||||
namespace = "app.revanced.integrations"
|
||||
|
||||
defaultConfig {
|
||||
applicationId = "app.revanced.integrations"
|
||||
minSdk = 23
|
||||
targetSdk = 33
|
||||
versionCode = 1
|
||||
versionName = "1.0"
|
||||
multiDexEnabled = false
|
||||
|
||||
val properties = Properties()
|
||||
if (rootProject.file("local.properties").exists()) {
|
||||
properties.load(FileInputStream(rootProject.file("local.properties")))
|
||||
}
|
||||
|
||||
buildConfigField("String", "YT_API_KEY", "\"${properties.getProperty("youtubeAPIKey", "")}\"")
|
||||
versionName = project.version as String
|
||||
}
|
||||
|
||||
buildTypes {
|
||||
release {
|
||||
isMinifyEnabled = true
|
||||
proguardFiles(getDefaultProguardFile("proguard-android-optimize.txt"), "proguard-rules.pro")
|
||||
proguardFiles(
|
||||
getDefaultProguardFile("proguard-android-optimize.txt"),
|
||||
"proguard-rules.pro"
|
||||
)
|
||||
}
|
||||
applicationVariants.all {
|
||||
outputs.all {
|
||||
this as com.android.build.gradle.internal.api.ApkVariantOutputImpl
|
||||
|
||||
outputFileName = "${rootProject.name}-$versionName.apk"
|
||||
}
|
||||
}
|
||||
}
|
||||
compileOptions {
|
||||
@@ -46,4 +48,8 @@ dependencies {
|
||||
compileOnly(project(mapOf("path" to ":dummy")))
|
||||
compileOnly("androidx.annotation:annotation:1.5.0")
|
||||
compileOnly("androidx.appcompat:appcompat:1.5.1")
|
||||
compileOnly("com.squareup.okhttp3:okhttp:5.0.0-alpha.11")
|
||||
compileOnly("com.squareup.retrofit2:retrofit:2.9.0")
|
||||
}
|
||||
|
||||
tasks.register("publish") { dependsOn("build") }
|
||||
|
||||
@@ -0,0 +1,11 @@
|
||||
package app.revanced.all.screenshot.removerestriction;
|
||||
|
||||
import android.view.Window;
|
||||
import android.view.WindowManager;
|
||||
|
||||
public class RemoveScreenshotRestrictionPatch {
|
||||
|
||||
public static void setFlags(Window window, int flags, int mask) {
|
||||
window.setFlags(flags & ~WindowManager.LayoutParams.FLAG_SECURE, mask & ~WindowManager.LayoutParams.FLAG_SECURE);
|
||||
}
|
||||
}
|
||||
@@ -35,7 +35,7 @@ public class AdRemoverAPI {
|
||||
ViewGroup.LayoutParams layoutParams5 = new ViewGroup.LayoutParams(1, 1);
|
||||
view.setLayoutParams(layoutParams5);
|
||||
} else {
|
||||
LogHelper.debug(AdRemoverAPI.class, "HideViewWithLayout1dp - Id: " + view.getId() + " Type: " + view.getClass().getName());
|
||||
LogHelper.printDebug(() -> "HideViewWithLayout1dp - Id: " + view.getId() + " Type: " + view.getClass().getName());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1,12 +1,11 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import app.revanced.integrations.adremover.AdRemoverAPI;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public class BrandingWaterMarkPatch {
|
||||
|
||||
//Used by: app.revanced.patches.youtube.layout.watermark.patch.HideWatermarkPatch
|
||||
// Used by: app.revanced.patches.youtube.layout.watermark.patch.HideWatermarkPatch
|
||||
public static boolean isBrandingWatermarkShown() {
|
||||
return SettingsEnum.BRANDING_SHOWN.getBoolean();
|
||||
return SettingsEnum.HIDE_VIDEO_WATERMARK.getBoolean() == false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -43,13 +43,13 @@ final class ButtonsPatch extends Filter {
|
||||
|
||||
if (currentIsActionButton && ActionButton.doNotBlockCounter-- > 0) {
|
||||
if (SettingsEnum.HIDE_SHARE_BUTTON.getBoolean()) {
|
||||
LogHelper.debug(ButtonsPatch.class, "Hiding share button");
|
||||
LogHelper.printDebug(() -> "Hiding share button");
|
||||
return true;
|
||||
} else return false;
|
||||
}
|
||||
|
||||
if ((currentIsActionButton && ActionButton.doNotBlockCounter <= 0 && actionButtonsRule.isEnabled()) || pathRegister.contains(path)) {
|
||||
LogHelper.debug(ButtonsPatch.class, "Blocked: " + path);
|
||||
LogHelper.printDebug(() -> "Blocked: " + path);
|
||||
return true;
|
||||
} else return false;
|
||||
}
|
||||
|
||||
@@ -24,7 +24,7 @@ final class CommentsPatch extends Filter {
|
||||
boolean filter(String path, String _identifier) {
|
||||
if (!pathRegister.contains(path)) return false;
|
||||
|
||||
LogHelper.debug(CommentsPatch.class, "Blocked: " + path);
|
||||
LogHelper.printDebug(() -> "Blocked: " + path);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,27 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import android.content.Context;
|
||||
import android.widget.Toast;
|
||||
|
||||
import app.revanced.integrations.sponsorblock.StringRef;
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
public class CopyVideoUrlPatch {
|
||||
public static void copyUrl(Boolean withTimestamp) {
|
||||
try {
|
||||
String url = String.format("https://youtu.be/%s", VideoInformation.getCurrentVideoId());
|
||||
if (withTimestamp) {
|
||||
long seconds = VideoInformation.getVideoTime() / 1000;
|
||||
url += String.format("?t=%s", seconds);
|
||||
}
|
||||
|
||||
Context context = ReVancedUtils.getContext();
|
||||
|
||||
ReVancedUtils.setClipboard(url);
|
||||
if (context != null) Toast.makeText(context, StringRef.str("share_copy_url_success"), Toast.LENGTH_SHORT).show();
|
||||
} catch (Exception e) {
|
||||
LogHelper.printException(() -> "Failed to generate video url", e);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,42 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import com.google.android.apps.youtube.app.watchwhile.WatchWhileActivity;
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
|
||||
public class FixBackToExitGesturePatch {
|
||||
/**
|
||||
* State whether the scroll position reaches the top.
|
||||
*/
|
||||
public static boolean isTopView = false;
|
||||
|
||||
/**
|
||||
* Handle the event after clicking the back button.
|
||||
*
|
||||
* @param activity The activity, the app is launched with to finish.
|
||||
*/
|
||||
public static void onBackPressed(WatchWhileActivity activity) {
|
||||
if (!isTopView) return;
|
||||
|
||||
LogHelper.printDebug(() -> "Activity is closed");
|
||||
|
||||
activity.finish();
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle the event when the homepage list of views is being scrolled.
|
||||
*/
|
||||
public static void onScrollingViews() {
|
||||
LogHelper.printDebug(() -> "Views are scrolling");
|
||||
|
||||
isTopView = false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle the event when the homepage list of views reached the top.
|
||||
*/
|
||||
public static void onTopView() {
|
||||
LogHelper.printDebug(() -> "Scrolling reached the top");
|
||||
|
||||
isTopView = true;
|
||||
}
|
||||
}
|
||||
@@ -31,7 +31,7 @@ public final class FixPlaybackPatch {
|
||||
Thread.sleep(10);
|
||||
}
|
||||
} catch (InterruptedException e) {
|
||||
LogHelper.debug(FixPlaybackPatch.class, "Thread was interrupted");
|
||||
LogHelper.printDebug(() -> "Thread was interrupted");
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
@@ -7,7 +7,7 @@ import app.revanced.integrations.settings.SettingsEnum;
|
||||
public class FullscreenPanelsRemoverPatch {
|
||||
|
||||
public static int getFullscreenPanelsVisibility() {
|
||||
return SettingsEnum.FULLSCREEN_PANELS_SHOWN.getBoolean() ? View.VISIBLE : View.GONE;
|
||||
return SettingsEnum.HIDE_FULLSCREEN_PANELS.getBoolean() ? View.GONE : View.VISIBLE;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
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;
|
||||
@@ -12,14 +11,8 @@ public final class GeneralAdsPatch extends Filter {
|
||||
"home_video_with_context",
|
||||
"related_video_with_context",
|
||||
"comment_thread", // skip blocking anything in the comments
|
||||
"download_",
|
||||
"|comment.", // skip blocking anything in the comments replies
|
||||
"library_recent_shelf",
|
||||
"menu",
|
||||
"root",
|
||||
"-count",
|
||||
"-space",
|
||||
"-button",
|
||||
"playlist_add_to_option_wrapper" // do not block on "add to playlist" flyout menu
|
||||
};
|
||||
|
||||
private final BlockRule custom = new CustomBlockRule(
|
||||
@@ -30,13 +23,14 @@ public final class GeneralAdsPatch extends Filter {
|
||||
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");
|
||||
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 suggestions = new BlockRule(SettingsEnum.ADREMOVER_SUGGESTIONS_REMOVAL, "horizontal_video_shelf");
|
||||
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_CARD, "official_card");
|
||||
@@ -55,6 +49,7 @@ public final class GeneralAdsPatch extends Filter {
|
||||
SettingsEnum.ADREMOVER_GENERAL_ADS_REMOVAL,
|
||||
"ads_video_with_context",
|
||||
"banner_text_icon",
|
||||
"square_image_layout",
|
||||
"watch_metadata_app_promo",
|
||||
"video_display_full_layout"
|
||||
);
|
||||
@@ -72,7 +67,6 @@ public final class GeneralAdsPatch extends Filter {
|
||||
buttonedAd,
|
||||
communityPosts,
|
||||
paidContent,
|
||||
suggestions,
|
||||
latestPosts,
|
||||
movieAds,
|
||||
chapterTeaser,
|
||||
@@ -84,7 +78,9 @@ public final class GeneralAdsPatch extends Filter {
|
||||
infoPanel,
|
||||
channelGuidelines,
|
||||
artistCard,
|
||||
selfSponsor
|
||||
selfSponsor,
|
||||
subscribersCommunityGuidelines,
|
||||
channelMemberShelf
|
||||
);
|
||||
|
||||
var carouselAd = new BlockRule(SettingsEnum.ADREMOVER_GENERAL_ADS_REMOVAL,
|
||||
@@ -93,7 +89,8 @@ public final class GeneralAdsPatch extends Filter {
|
||||
var shorts = new BlockRule(SettingsEnum.ADREMOVER_SHORTS_REMOVAL,
|
||||
"reels_player_overlay",
|
||||
"shorts_shelf",
|
||||
"inline_shorts"
|
||||
"inline_shorts",
|
||||
"shorts_grid"
|
||||
);
|
||||
|
||||
this.identifierRegister.registerAll(
|
||||
@@ -115,7 +112,7 @@ public final class GeneralAdsPatch extends Filter {
|
||||
else
|
||||
result = BlockResult.UNBLOCKED;
|
||||
|
||||
log(String.format("%s (ID: %s): %s", result.message, identifier, path));
|
||||
LogHelper.printDebug(() -> String.format("%s (ID: %s): %s", result.message, identifier, path));
|
||||
|
||||
return result.filter;
|
||||
}
|
||||
@@ -144,7 +141,7 @@ public final class GeneralAdsPatch extends Filter {
|
||||
private static void hideView(SettingsEnum condition, View view) {
|
||||
if (!condition.getBoolean()) return;
|
||||
|
||||
log("Hiding view with setting: " + condition);
|
||||
LogHelper.printDebug(() -> "Hiding view with setting: " + condition);
|
||||
|
||||
AdRemoverAPI.HideViewWithLayout1dp(view);
|
||||
}
|
||||
@@ -167,7 +164,4 @@ public final class GeneralAdsPatch extends Filter {
|
||||
hideView(SettingsEnum.ADREMOVER_SHORTS_REMOVAL, view);
|
||||
}
|
||||
|
||||
private static void log(String message) {
|
||||
LogHelper.debug(GeneralAdsPatch.class, message);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -5,6 +5,6 @@ import app.revanced.integrations.settings.SettingsEnum;
|
||||
public class HideAutoplayButtonPatch {
|
||||
|
||||
public static boolean isButtonShown() {
|
||||
return SettingsEnum.AUTOPLAY_BUTTON_SHOWN.getBoolean();
|
||||
return SettingsEnum.HIDE_AUTOPLAY_BUTTON.getBoolean() == false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,14 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import android.view.View;
|
||||
|
||||
import app.revanced.integrations.adremover.AdRemoverAPI;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public class HideBreakingNewsPatch {
|
||||
//Used by app.revanced.patches.youtube.layout.homepage.breakingnews.patch.BreakingNewsPatch
|
||||
public static void hideBreakingNews(View view) {
|
||||
if (!SettingsEnum.HIDE_BREAKING_NEWS.getBoolean()) return;
|
||||
AdRemoverAPI.HideViewWithLayout1dp(view);
|
||||
}
|
||||
}
|
||||
@@ -6,8 +6,8 @@ import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public class HideCastButtonPatch {
|
||||
|
||||
//Used by app.revanced.patches.youtube.layout.castbutton.patch.HideCastButonPatch
|
||||
// Used by app.revanced.patches.youtube.layout.castbutton.patch.HideCastButonPatch
|
||||
public static int getCastButtonOverrideV2(int original) {
|
||||
return SettingsEnum.CAST_BUTTON_SHOWN.getBoolean() ? original : View.GONE;
|
||||
return SettingsEnum.HIDE_CAST_BUTTON.getBoolean() ? View.GONE : original;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -9,9 +9,8 @@ public class HideCreateButtonPatch {
|
||||
|
||||
//Used by app.revanced.patches.youtube.layout.createbutton.patch.CreateButtonRemoverPatch
|
||||
public static void hideCreateButton(View view) {
|
||||
boolean enabled = SettingsEnum.CREATE_BUTTON_ENABLED.getBoolean();
|
||||
String message = "Create button: " + (enabled ? "shown" : "hidden");
|
||||
LogHelper.debug(HideCreateButtonPatch.class, message);
|
||||
view.setVisibility(enabled ? View.VISIBLE : View.GONE);
|
||||
boolean hidden = SettingsEnum.HIDE_CREATE_BUTTON.getBoolean();
|
||||
LogHelper.printDebug(() -> "Create button: " + (hidden ? "hidden" : "shown"));
|
||||
view.setVisibility(hidden ? View.GONE : View.VISIBLE);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -13,7 +13,7 @@ public class HideReelsPatch {
|
||||
* @param view
|
||||
*/
|
||||
public static void HideReel(View view) {
|
||||
if (!SettingsEnum.REEL_BUTTON_SHOWN.getBoolean()) {
|
||||
if (SettingsEnum.HIDE_REEL_BUTTON.getBoolean()) {
|
||||
AdRemoverAPI.HideViewWithLayout1dp(view);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,20 +3,18 @@ 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;
|
||||
|
||||
public class HideShortsButtonPatch {
|
||||
|
||||
//Used by app.revanced.patches.youtube.layout.shorts.button.patch.ShortsButtonRemoverPatch
|
||||
// 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 show = SettingsEnum.SHORTS_BUTTON_SHOWN.getBoolean();
|
||||
String message = show ? "Shorts button: shown" : "Shorts button: hidden";
|
||||
LogHelper.debug(HideShortsButtonPatch.class, message);
|
||||
if (!show) {
|
||||
view.setVisibility(show ? View.VISIBLE : View.GONE);
|
||||
boolean hide = SettingsEnum.HIDE_SHORTS_BUTTON.getBoolean();
|
||||
LogHelper.printDebug(() -> hide ? "Shorts button: hidden" : "Shorts button: shown");
|
||||
if (hide) {
|
||||
view.setVisibility(View.GONE);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -128,7 +128,7 @@ public final class LithoFilterPatch {
|
||||
var path = pathBuilder.toString();
|
||||
if (path.isEmpty()) return false;
|
||||
|
||||
LogHelper.debug(LithoFilterPatch.class, String.format("Searching (ID: %s): %s", identifier, path));
|
||||
LogHelper.printDebug(() -> String.format("Searching (ID: %s): %s", identifier, path));
|
||||
|
||||
for (var filter : filters) {
|
||||
if (filter.filter(path, identifier)) return true;
|
||||
|
||||
@@ -1,34 +1,72 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import android.util.Log;
|
||||
import static app.revanced.integrations.utils.ReVancedUtils.getContext;
|
||||
|
||||
import android.content.Context;
|
||||
|
||||
import app.revanced.integrations.utils.ThemeHelper;
|
||||
|
||||
public class LithoThemePatch {
|
||||
// color constants used in relation with litho components
|
||||
private static final int[] WHITECONSTANTS = {
|
||||
-1, // comments chip background
|
||||
-394759, // music related results panel background
|
||||
-83886081, // video chapters list background
|
||||
private static final int[] WHITE_VALUES = {
|
||||
-1, // comments chip background
|
||||
-394759, // music related results panel background
|
||||
-83886081, // video chapters list background
|
||||
};
|
||||
|
||||
private static final int[] DARKCONSTANTS = {
|
||||
-14145496, // explore drawer background
|
||||
-14606047, // comments chip background
|
||||
-15198184, // music related results panel background
|
||||
-15790321, // comments chip background (new layout)
|
||||
-98492127 // video chapters list background
|
||||
private static final int[] DARK_VALUES = {
|
||||
-14145496, // explore drawer background
|
||||
-14606047, // comments chip background
|
||||
-15198184, // music related results panel background
|
||||
-15790321, // comments chip background (new layout)
|
||||
-98492127 // video chapters list background
|
||||
};
|
||||
|
||||
// background colors
|
||||
private static int whiteColor = 0;
|
||||
private static int blackColor = 0;
|
||||
|
||||
// Used by app.revanced.patches.youtube.layout.theme.patch.LithoThemePatch
|
||||
/**
|
||||
* Change the color of Litho components.
|
||||
* If the color of the component matches one of the values, return the background color .
|
||||
*
|
||||
* @param originalValue The original color value.
|
||||
* @return The new or original color value
|
||||
*/
|
||||
public static int applyLithoTheme(int originalValue) {
|
||||
var isDarkTheme = ThemeHelper.isDarkTheme();
|
||||
|
||||
if ((isDarkTheme && anyEquals(originalValue, DARKCONSTANTS)) || (!isDarkTheme && anyEquals(originalValue, WHITECONSTANTS)))
|
||||
return 0;
|
||||
if (ThemeHelper.isDarkTheme()) {
|
||||
if (anyEquals(originalValue, DARK_VALUES)) return getBlackColor();
|
||||
} else {
|
||||
if (anyEquals(originalValue, WHITE_VALUES)) return getWhiteColor();
|
||||
}
|
||||
return originalValue;
|
||||
}
|
||||
|
||||
private static int getBlackColor() {
|
||||
if (blackColor == 0) blackColor = getColor("yt_black1");
|
||||
return blackColor;
|
||||
}
|
||||
|
||||
private static int getWhiteColor() {
|
||||
if (whiteColor == 0) whiteColor = getColor("yt_white1");
|
||||
return whiteColor;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determines the color for a color resource.
|
||||
*
|
||||
* @param name The color resource name.
|
||||
* @return The value of the color.
|
||||
*/
|
||||
private static int getColor(String name) {
|
||||
Context context = getContext();
|
||||
|
||||
return context != null ? context.getColor(context.getResources()
|
||||
.getIdentifier(name, "color", context.getPackageName())
|
||||
) : 0;
|
||||
}
|
||||
|
||||
private static boolean anyEquals(int value, int... of) {
|
||||
for (int v : of) if (value == v) return true;
|
||||
return false;
|
||||
|
||||
@@ -2,11 +2,14 @@ package app.revanced.integrations.patches;
|
||||
|
||||
import static app.revanced.integrations.sponsorblock.StringRef.str;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.net.Uri;
|
||||
import android.widget.Toast;
|
||||
|
||||
import java.util.Objects;
|
||||
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
@@ -14,20 +17,35 @@ public class MicroGSupport {
|
||||
private static final String MICROG_VENDOR = "com.mgoogle";
|
||||
private static final String MICROG_PACKAGE_NAME = "com.mgoogle.android.gms";
|
||||
private static final String VANCED_MICROG_DOWNLOAD_LINK = "https://github.com/TeamVanced/VancedMicroG/releases/latest";
|
||||
private static final String DONT_KILL_MY_APP_LINK = "https://dontkillmyapp.com";
|
||||
private static final Uri VANCED_MICROG_PROVIDER = Uri.parse("content://com.mgoogle.android.gsf.gservices/prefix");
|
||||
|
||||
private static void startIntent(Context context, String uriString, String message) {
|
||||
Toast.makeText(context, message, Toast.LENGTH_LONG).show();
|
||||
|
||||
var intent = new Intent(Intent.ACTION_VIEW);
|
||||
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
|
||||
intent.setData(Uri.parse(uriString));
|
||||
context.startActivity(intent);
|
||||
}
|
||||
|
||||
public static void checkAvailability() {
|
||||
var context = ReVancedUtils.getContext();
|
||||
assert context != null;
|
||||
var context = Objects.requireNonNull(ReVancedUtils.getContext());
|
||||
|
||||
try {
|
||||
context.getPackageManager().getPackageInfo(MICROG_PACKAGE_NAME, PackageManager.GET_ACTIVITIES);
|
||||
LogHelper.debug(ReVancedUtils.class, "MicroG is installed on the device");
|
||||
} catch (PackageManager.NameNotFoundException exception) {
|
||||
LogHelper.printException(ReVancedUtils.class, "MicroG was not found", exception);
|
||||
Toast.makeText(context, str("microg_not_installed_warning"), Toast.LENGTH_LONG).show();
|
||||
LogHelper.printInfo(() -> "Vanced MicroG was not found", exception);
|
||||
startIntent(context, VANCED_MICROG_DOWNLOAD_LINK, str("microg_not_installed_warning"));
|
||||
|
||||
var intent = new Intent(Intent.ACTION_VIEW);
|
||||
intent.setData(Uri.parse(VANCED_MICROG_DOWNLOAD_LINK));
|
||||
context.startActivity(intent);
|
||||
// Gracefully exit the app, so it does not crash.
|
||||
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,19 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public class OpenLinksExternallyPatch {
|
||||
/**
|
||||
* Override 'android.support.customtabs.action.CustomTabsService',
|
||||
* in order to open links in the default browser. This is done by returning an empty string,
|
||||
* for the service that handles custom tabs in the Android support library
|
||||
* which opens links in the default service instead.
|
||||
*
|
||||
* @param original The original custom tabs service.
|
||||
* @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 = "";
|
||||
return original;
|
||||
}
|
||||
}
|
||||
@@ -2,8 +2,8 @@ package app.revanced.integrations.patches;
|
||||
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
import app.revanced.integrations.shared.PlayerType;
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
|
||||
/**
|
||||
* Hook receiver class for 'player-type-hook' patch
|
||||
@@ -24,9 +24,11 @@ public class PlayerTypeHookPatch {
|
||||
|
||||
// update current player type
|
||||
final PlayerType newType = PlayerType.safeParseFromString(type.toString());
|
||||
if (newType != null) {
|
||||
if (newType == null) {
|
||||
LogHelper.printException(() -> "Unknown PlayerType encountered: " + type);
|
||||
} else {
|
||||
PlayerType.setCurrent(newType);
|
||||
LogHelper.debug(PlayerTypeHookPatch.class, "YouTubePlayerOverlaysLayout player type was updated to " + newType);
|
||||
LogHelper.printDebug(() -> "YouTubePlayerOverlaysLayout player type was updated to " + newType);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,15 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public class SpoofAppVersionPatch {
|
||||
|
||||
public static String getYouTubeVersionOverride(String version) {
|
||||
if (SettingsEnum.SPOOF_APP_VERSION.getBoolean()){
|
||||
// Override with the most recent version that does not show the new UI player layout.
|
||||
// If the new UI shows up for some users, then change this to an older version (such as 17.29.34).
|
||||
return "17.30.34";
|
||||
}
|
||||
return version;
|
||||
}
|
||||
}
|
||||
@@ -17,6 +17,7 @@ public final class VideoInformation {
|
||||
private static WeakReference<Object> playerController;
|
||||
private static Method seekMethod;
|
||||
|
||||
private static String videoId = "";
|
||||
private static long videoLength = 1;
|
||||
private static long videoTime = -1;
|
||||
|
||||
@@ -35,17 +36,28 @@ public final class VideoInformation {
|
||||
seekMethod = thisRef.getClass().getMethod(SEEK_METHOD_NAME, Long.TYPE);
|
||||
seekMethod.setAccessible(true);
|
||||
} catch (NoSuchMethodException ex) {
|
||||
LogHelper.debug(VideoInformation.class, "Failed to initialize: " + ex.getMessage());
|
||||
LogHelper.printException(() -> "Failed to initialize", ex);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the video id.
|
||||
*
|
||||
* @param videoId The id of the video.
|
||||
*/
|
||||
public static void setVideoId(String videoId) {
|
||||
LogHelper.printDebug(() -> "Setting current video id to: " + videoId);
|
||||
|
||||
VideoInformation.videoId = videoId;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the video length.
|
||||
*
|
||||
* @param length The length of the video in milliseconds.
|
||||
*/
|
||||
public static void setVideoLength(final long length) {
|
||||
LogHelper.debug(VideoInformation.class, "Setting current video length to " + length);
|
||||
LogHelper.printDebug(() -> "Setting current video length to " + length);
|
||||
videoLength = length;
|
||||
}
|
||||
|
||||
@@ -55,7 +67,7 @@ public final class VideoInformation {
|
||||
* @param time The time of the video in milliseconds.
|
||||
*/
|
||||
public static void setVideoTime(final long time) {
|
||||
LogHelper.debug(VideoInformation.class, "Current video time " + time);
|
||||
LogHelper.printDebug(() -> "Current video time " + time);
|
||||
videoTime = time;
|
||||
}
|
||||
|
||||
@@ -67,19 +79,28 @@ public final class VideoInformation {
|
||||
public static void seekTo(final long millisecond) {
|
||||
new Handler(Looper.getMainLooper()).post(() -> {
|
||||
if (seekMethod == null) {
|
||||
LogHelper.debug(VideoInformation.class, "seekMethod was null");
|
||||
LogHelper.printDebug(() -> "seekMethod was null");
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
LogHelper.debug(VideoInformation.class, "Seeking to " + millisecond);
|
||||
LogHelper.printDebug(() -> "Seeking to " + millisecond);
|
||||
seekMethod.invoke(playerController.get(), millisecond);
|
||||
} catch (Exception ex) {
|
||||
LogHelper.debug(VideoInformation.class, "Failed to seek: " + ex.getMessage());
|
||||
LogHelper.printException(() -> "Failed to seek", ex);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the id of the current video playing.
|
||||
*
|
||||
* @return The id of the video. Empty string if not set yet.
|
||||
*/
|
||||
public static String getCurrentVideoId() {
|
||||
return videoId;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the length of the current video playing.
|
||||
*
|
||||
|
||||
@@ -1,172 +0,0 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import java.lang.reflect.Field;
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
public class VideoSpeedPatch {
|
||||
|
||||
public static final float[] videoSpeeds = { 0, 0 }; // Values are useless as they are being overridden by the respective patch
|
||||
private static Boolean userChangedSpeed = false;
|
||||
|
||||
public static int getDefaultSpeed(Object[] speeds, int speed, Object qInterface) {
|
||||
int speed2;
|
||||
Exception e;
|
||||
if (!ReVancedUtils.isNewVideoStarted()) {
|
||||
return speed;
|
||||
}
|
||||
ReVancedUtils.setNewVideo(false);
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Speed: " + speed);
|
||||
float preferredSpeed = SettingsEnum.PREFERRED_VIDEO_SPEED.getFloat();
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Preferred speed: " + preferredSpeed);
|
||||
if (preferredSpeed == -2.0f) {
|
||||
return speed;
|
||||
}
|
||||
Class<?> floatType = Float.TYPE;
|
||||
ArrayList<Float> iStreamSpeeds = new ArrayList<>();
|
||||
try {
|
||||
for (Object streamSpeed : speeds) {
|
||||
Field[] fields = streamSpeed.getClass().getFields();
|
||||
for (Field field : fields) {
|
||||
if (field.getType().isAssignableFrom(floatType)) {
|
||||
float value = field.getFloat(streamSpeed);
|
||||
if (field.getName().length() <= 2) {
|
||||
iStreamSpeeds.add(value);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (Exception ignored) {
|
||||
}
|
||||
Iterator<Float> it = iStreamSpeeds.iterator();
|
||||
int index = 0;
|
||||
while (it.hasNext()) {
|
||||
float streamSpeed2 = it.next();
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Speed at index " + index + ": " + streamSpeed2);
|
||||
index++;
|
||||
}
|
||||
int speed3 = -1;
|
||||
for (float streamSpeed3 : iStreamSpeeds) {
|
||||
if (streamSpeed3 <= preferredSpeed) {
|
||||
speed3++;
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Speed loop at index " + speed3 + ": " + streamSpeed3);
|
||||
}
|
||||
}
|
||||
if (speed3 == -1) {
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Speed was not found");
|
||||
speed2 = 3;
|
||||
} else {
|
||||
speed2 = speed3;
|
||||
}
|
||||
try {
|
||||
Method[] declaredMethods = qInterface.getClass().getDeclaredMethods();
|
||||
for (Method method : declaredMethods) {
|
||||
if (method.getName().length() <= 2) {
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Method name: " + method.getName());
|
||||
try {
|
||||
try {
|
||||
method.invoke(qInterface, videoSpeeds[speed2]);
|
||||
} catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException ignored) {
|
||||
} catch (Exception e6) {
|
||||
e = e6;
|
||||
LogHelper.printException(VideoSpeedPatch.class, e.getMessage());
|
||||
return speed2;
|
||||
}
|
||||
} catch (Exception ignored) {
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (Exception e10) {
|
||||
e = e10;
|
||||
}
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Speed changed to: " + speed2);
|
||||
return speed2;
|
||||
}
|
||||
|
||||
public static void userChangedSpeed() {
|
||||
userChangedSpeed = true;
|
||||
}
|
||||
|
||||
public static float getSpeedValue(Object[] speeds, int speed) {
|
||||
int i = 0;
|
||||
if (!ReVancedUtils.isNewVideoStarted() || userChangedSpeed) {
|
||||
if (SettingsEnum.DEBUG.getBoolean() && userChangedSpeed) {
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Skipping speed change because user changed it: " + speed);
|
||||
}
|
||||
userChangedSpeed = false;
|
||||
return -1.0f;
|
||||
}
|
||||
ReVancedUtils.setNewVideo(false);
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Speed: " + speed);
|
||||
float preferredSpeed = SettingsEnum.PREFERRED_VIDEO_SPEED.getFloat();
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Preferred speed: " + preferredSpeed);
|
||||
if (preferredSpeed == -2.0f) {
|
||||
return -1.0f;
|
||||
}
|
||||
Class<?> floatType = Float.TYPE;
|
||||
ArrayList<Float> iStreamSpeeds = new ArrayList<>();
|
||||
try {
|
||||
int length = speeds.length;
|
||||
int i2 = 0;
|
||||
while (i2 < length) {
|
||||
Object streamSpeed = speeds[i2];
|
||||
Field[] fields = streamSpeed.getClass().getFields();
|
||||
int length2 = fields.length;
|
||||
while (i < length2) {
|
||||
Field field = fields[i];
|
||||
if (field.getType().isAssignableFrom(floatType)) {
|
||||
float value = field.getFloat(streamSpeed);
|
||||
if (field.getName().length() <= 2) {
|
||||
iStreamSpeeds.add(value);
|
||||
}
|
||||
}
|
||||
i++;
|
||||
}
|
||||
i2++;
|
||||
i = 0;
|
||||
}
|
||||
} catch (Exception ignored) {
|
||||
}
|
||||
int index = 0;
|
||||
for (Float iStreamSpeed : iStreamSpeeds) {
|
||||
float streamSpeed2 = iStreamSpeed;
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Speed at index " + index + ": " + streamSpeed2);
|
||||
index++;
|
||||
}
|
||||
int newSpeedIndex = -1;
|
||||
for (Float iStreamSpeed : iStreamSpeeds) {
|
||||
float streamSpeed3 = iStreamSpeed;
|
||||
if (streamSpeed3 <= preferredSpeed) {
|
||||
newSpeedIndex++;
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Speed loop at index " + newSpeedIndex + ": " + streamSpeed3);
|
||||
}
|
||||
}
|
||||
if (newSpeedIndex == -1) {
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Speed was not found");
|
||||
newSpeedIndex = 3;
|
||||
}
|
||||
if (newSpeedIndex == speed) {
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Trying to set speed to what it already is, skipping...: " + newSpeedIndex);
|
||||
return -1.0f;
|
||||
}
|
||||
LogHelper.debug(VideoSpeedPatch.class, "Speed changed to: " + newSpeedIndex);
|
||||
return getSpeedByIndex(newSpeedIndex);
|
||||
}
|
||||
|
||||
private static float getSpeedByIndex(int index) {
|
||||
if (index == -2) {
|
||||
return 1.0f;
|
||||
}
|
||||
try {
|
||||
return videoSpeeds[index];
|
||||
} catch (Exception e) {
|
||||
return 1.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,27 +0,0 @@
|
||||
package app.revanced.integrations.patches.downloads;
|
||||
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
|
||||
/**
|
||||
* Used by app.revanced.patches.youtube.interaction.downloads.bytecode.patch.DownloadsBytecodePatch
|
||||
*/
|
||||
public class DownloadsPatch {
|
||||
private static String videoId;
|
||||
|
||||
/**
|
||||
* Called when the video changes
|
||||
* @param videoId The current video id
|
||||
*/
|
||||
public static void setVideoId(String videoId) {
|
||||
LogHelper.debug(DownloadsPatch.class, "newVideoLoaded - " + videoId);
|
||||
|
||||
DownloadsPatch.videoId = videoId;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return The current video id
|
||||
*/
|
||||
public static String getCurrentVideoId() {
|
||||
return videoId;
|
||||
}
|
||||
}
|
||||
@@ -10,19 +10,19 @@ import app.revanced.integrations.utils.LogHelper;
|
||||
public class OldQualityLayoutPatch {
|
||||
public static void showOldQualityMenu(ListView listView)
|
||||
{
|
||||
if (!SettingsEnum.OLD_STYLE_QUALITY_SETTINGS.getBoolean()) return;
|
||||
if (!SettingsEnum.OLD_STYLE_VIDEO_QUALITY_PLAYER_SETTINGS.getBoolean()) return;
|
||||
|
||||
listView.setOnHierarchyChangeListener(new ViewGroup.OnHierarchyChangeListener() {
|
||||
@Override
|
||||
public void onChildViewAdded(View parent, View child) {
|
||||
LogHelper.debug(OldQualityLayoutPatch.class, "Added: " + child);
|
||||
LogHelper.printDebug(() -> "Added: " + child);
|
||||
|
||||
parent.setVisibility(View.GONE);
|
||||
|
||||
final var indexOfAdvancedQualityMenuItem = 4;
|
||||
if (listView.indexOfChild(child) != indexOfAdvancedQualityMenuItem) return;
|
||||
|
||||
LogHelper.debug(OldQualityLayoutPatch.class, "Found advanced menu: " + child);
|
||||
LogHelper.printDebug(() -> "Found advanced menu: " + child);
|
||||
|
||||
final var qualityItemMenuPosition = 4;
|
||||
listView.performItemClick(null, qualityItemMenuPosition, 0);
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
package app.revanced.integrations.patches.playback.quality;
|
||||
|
||||
import android.annotation.SuppressLint;
|
||||
import android.content.Context;
|
||||
import android.net.ConnectivityManager;
|
||||
import android.net.NetworkInfo;
|
||||
@@ -25,25 +26,26 @@ public class RememberVideoQualityPatch {
|
||||
Context context = ReVancedUtils.getContext();
|
||||
if (isConnectedWifi(context)) {
|
||||
try {
|
||||
SharedPrefHelper.saveString(context, SharedPrefHelper.SharedPrefNames.REVANCED_PREFS, "wifi_quality", defaultQuality + "");
|
||||
SharedPrefHelper.saveString(SharedPrefHelper.SharedPrefNames.REVANCED_PREFS, "wifi_quality", defaultQuality + "");
|
||||
String message = "Changing default Wi-Fi quality to: " + defaultQuality;
|
||||
LogHelper.printDebug(() -> message);
|
||||
Toast.makeText(context, message, Toast.LENGTH_SHORT).show();
|
||||
} catch (Exception ex) {
|
||||
LogHelper.printException(RememberVideoQualityPatch.class, "Failed to change default WI-FI quality:" + ex);
|
||||
Toast.makeText(context, "Failed to change default WI-FI quality:", Toast.LENGTH_SHORT).show();
|
||||
LogHelper.printException(() -> "Failed to change default WI-FI quality", ex);
|
||||
}
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "Changing default Wi-Fi quality to: " + defaultQuality);
|
||||
Toast.makeText(context, "Changing default Wi-Fi quality to: " + defaultQuality, Toast.LENGTH_SHORT).show();
|
||||
} else if (isConnectedMobile(context)) {
|
||||
try {
|
||||
SharedPrefHelper.saveString(context, SharedPrefHelper.SharedPrefNames.REVANCED_PREFS, "mobile_quality", defaultQuality + "");
|
||||
SharedPrefHelper.saveString(SharedPrefHelper.SharedPrefNames.REVANCED_PREFS, "mobile_quality", defaultQuality + "");
|
||||
String message = "Changing default mobile data quality to:" + defaultQuality;
|
||||
LogHelper.printDebug(() -> message);
|
||||
Toast.makeText(context, message, Toast.LENGTH_SHORT).show();
|
||||
} catch (Exception ex) {
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "Failed to change default mobile data quality" + ex);
|
||||
Toast.makeText(context, "Failed to change default mobile data quality", Toast.LENGTH_SHORT).show();
|
||||
LogHelper.printException(() -> "Failed to change default mobile data quality", ex);
|
||||
}
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "Changing default mobile data quality to:" + defaultQuality);
|
||||
Toast.makeText(context, "Changing default mobile data quality to:" + defaultQuality, Toast.LENGTH_SHORT).show();
|
||||
} else {
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "No internet connection.");
|
||||
Toast.makeText(context, "No internet connection.", Toast.LENGTH_SHORT).show();
|
||||
String message = "No internet connection.";
|
||||
LogHelper.printDebug(() -> message);
|
||||
Toast.makeText(context, message, Toast.LENGTH_SHORT).show();
|
||||
}
|
||||
userChangedQuality = false;
|
||||
}
|
||||
@@ -76,34 +78,37 @@ public class RememberVideoQualityPatch {
|
||||
int selectedQuality2 = qualities.length - selectedQuality1 + 1;
|
||||
index++;
|
||||
if (selectedQuality2 == index) {
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "Quality index is: " + index + " and corresponding value is: " + convertedQuality);
|
||||
final int indexToLog = index; // must be final for lambda
|
||||
LogHelper.printDebug(() -> "Quality index is: " + indexToLog + " and corresponding value is: " + convertedQuality);
|
||||
changeDefaultQuality(convertedQuality);
|
||||
return selectedQuality2;
|
||||
}
|
||||
}
|
||||
}
|
||||
newVideo = false;
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "Quality: " + quality);
|
||||
final int qualityToLog = quality;
|
||||
LogHelper.printDebug(() -> "Quality: " + qualityToLog);
|
||||
Context context = ReVancedUtils.getContext();
|
||||
if (context == null) {
|
||||
LogHelper.printException(RememberVideoQualityPatch.class, "Context is null or settings not initialized, returning quality: " + quality);
|
||||
LogHelper.printException(() -> "Context is null or settings not initialized, returning quality: " + qualityToLog);
|
||||
return quality;
|
||||
}
|
||||
if (isConnectedWifi(context)) {
|
||||
preferredQuality = SharedPrefHelper.getInt(context, SharedPrefHelper.SharedPrefNames.REVANCED_PREFS, "wifi_quality", -2);
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "Wi-Fi connection detected, preferred quality: " + preferredQuality);
|
||||
preferredQuality = SharedPrefHelper.getInt(SharedPrefHelper.SharedPrefNames.REVANCED_PREFS, "wifi_quality", -2);
|
||||
LogHelper.printDebug(() -> "Wi-Fi connection detected, preferred quality: " + preferredQuality);
|
||||
} else if (isConnectedMobile(context)) {
|
||||
preferredQuality = SharedPrefHelper.getInt(context, SharedPrefHelper.SharedPrefNames.REVANCED_PREFS, "mobile_quality", -2);
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "Mobile data connection detected, preferred quality: " + preferredQuality);
|
||||
preferredQuality = SharedPrefHelper.getInt(SharedPrefHelper.SharedPrefNames.REVANCED_PREFS, "mobile_quality", -2);
|
||||
LogHelper.printDebug(() -> "Mobile data connection detected, preferred quality: " + preferredQuality);
|
||||
} else {
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "No Internet connection!");
|
||||
LogHelper.printDebug(() -> "No Internet connection!");
|
||||
return quality;
|
||||
}
|
||||
if (preferredQuality == -2) {
|
||||
return quality;
|
||||
}
|
||||
for (int streamQuality2 : iStreamQualities) {
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "Quality at index " + index + ": " + streamQuality2);
|
||||
final int indexToLog = index;
|
||||
LogHelper.printDebug(() -> "Quality at index " + indexToLog + ": " + streamQuality2);
|
||||
index++;
|
||||
}
|
||||
for (Integer iStreamQuality : iStreamQualities) {
|
||||
@@ -116,24 +121,24 @@ public class RememberVideoQualityPatch {
|
||||
return quality;
|
||||
}
|
||||
int qualityIndex = iStreamQualities.indexOf(quality);
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "Index of quality " + quality + " is " + qualityIndex);
|
||||
final int qualityToLog2 = quality;
|
||||
LogHelper.printDebug(() -> "Index of quality " + qualityToLog2 + " is " + qualityIndex);
|
||||
try {
|
||||
Class<?> cl = qInterface.getClass();
|
||||
Method m = cl.getMethod(qIndexMethod, Integer.TYPE);
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "Method is: " + qIndexMethod);
|
||||
LogHelper.printDebug(() -> "Method is: " + qIndexMethod);
|
||||
m.invoke(qInterface, iStreamQualities.get(qualityIndex));
|
||||
LogHelper.debug(RememberVideoQualityPatch.class, "Quality changed to: " + qualityIndex);
|
||||
LogHelper.printDebug(() -> "Quality changed to: " + qualityIndex);
|
||||
return qualityIndex;
|
||||
} catch (Exception ex) {
|
||||
LogHelper.printException(RememberVideoQualityPatch.class, "Failed to set quality", ex);
|
||||
Toast.makeText(context, "Failed to set quality", Toast.LENGTH_SHORT).show();
|
||||
LogHelper.printException(() -> "Failed to set quality", ex);
|
||||
return qualityIndex;
|
||||
}
|
||||
}
|
||||
|
||||
public static void userChangedQuality(int selectedQuality) {
|
||||
// Do not remember a **new** quality if REMEMBER_VIDEO_QUALITY is true
|
||||
if (SettingsEnum.REMEMBER_VIDEO_QUALITY.getBoolean()) return;
|
||||
// Do not remember a **new** quality if REMEMBER_VIDEO_QUALITY is false
|
||||
if (!SettingsEnum.REMEMBER_VIDEO_QUALITY_LAST_SELECTED.getBoolean()) return;
|
||||
|
||||
selectedQuality1 = selectedQuality;
|
||||
userChangedQuality = true;
|
||||
@@ -143,6 +148,7 @@ public class RememberVideoQualityPatch {
|
||||
newVideo = true;
|
||||
}
|
||||
|
||||
@SuppressLint("MissingPermission")
|
||||
private static NetworkInfo getNetworkInfo(Context context) {
|
||||
ConnectivityManager cm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
|
||||
return cm.getActiveNetworkInfo();
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user