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
95 Commits
v0.121.0-d
...
v1.0.0-dev
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
aa6f591141 | ||
|
|
0bb86694e2 | ||
|
|
d484f35127 | ||
|
|
f4e2d56b18 | ||
|
|
9394c512ba | ||
|
|
5d4c8b0a1b | ||
|
|
3a56431a28 | ||
|
|
fba7181e70 | ||
|
|
3b4f0206ad | ||
|
|
3d660e1b5e | ||
|
|
dd045ad985 | ||
|
|
0a15245f41 | ||
|
|
a18c134aaa | ||
|
|
0ea4e720ed | ||
|
|
c6a1b9fc59 | ||
|
|
d6ed0c061c | ||
|
|
3ba3d5108d | ||
|
|
c2112e066a | ||
|
|
6520499a27 | ||
|
|
b2d9dcd6c0 | ||
|
|
11abdf162f | ||
|
|
b514bdd7d0 | ||
|
|
eede028c96 | ||
|
|
9eb0471989 | ||
|
|
3dbfbf9e6f | ||
|
|
373820eb99 | ||
|
|
f936f240a7 | ||
|
|
b9d50fd3d8 | ||
|
|
11e7c04b70 | ||
|
|
2613e102cc | ||
|
|
2a582f9424 | ||
|
|
bc56aa5f07 | ||
|
|
1ebf8e04a6 | ||
|
|
c13504a0b3 | ||
|
|
0124f41cd6 | ||
|
|
31777e027e | ||
|
|
dedd2f658a | ||
|
|
7f0c2c507c | ||
|
|
17e78824b7 | ||
|
|
36fe5718cf | ||
|
|
355acc7023 | ||
|
|
dcca2e5e8d | ||
|
|
c4d01b2334 | ||
|
|
ce2ad04f60 | ||
|
|
1230d77f94 | ||
|
|
2735f99c0a | ||
|
|
64463dea5b | ||
|
|
4932a71088 | ||
|
|
f6e936812e | ||
|
|
c8510dbb4d | ||
|
|
d3021bcf0b | ||
|
|
ffcee71f79 | ||
|
|
8cbe2b5a92 | ||
|
|
abfbb0d7d5 | ||
|
|
ce0bedc5d3 | ||
|
|
5cf5d86913 | ||
|
|
7dd826ad71 | ||
|
|
58afcec641 | ||
|
|
781cdf88df | ||
|
|
ba15aba063 | ||
|
|
411b0f2ccc | ||
|
|
b078f0ca37 | ||
|
|
46bfeea1a3 | ||
|
|
d0c659ce11 | ||
|
|
25dc754ff5 | ||
|
|
726a2510a5 | ||
|
|
0978e64655 | ||
|
|
a5245b85a8 | ||
|
|
9a6ec6be8c | ||
|
|
8b5d2d1871 | ||
|
|
130f629f6b | ||
|
|
828ff6f31e | ||
|
|
847cce43f6 | ||
|
|
5f30100fd5 | ||
|
|
b1ce7a75eb | ||
|
|
e84b7b328e | ||
|
|
db0fb46a39 | ||
|
|
11f97ac354 | ||
|
|
831041b432 | ||
|
|
50933dc42d | ||
|
|
37b3b6a837 | ||
|
|
6e414ec6c2 | ||
|
|
4f57d56042 | ||
|
|
e94de61eb0 | ||
|
|
6b00f90fb7 | ||
|
|
85705141a8 | ||
|
|
3344375fb9 | ||
|
|
8d534f05d5 | ||
|
|
c048527dc0 | ||
|
|
1b29b7e11d | ||
|
|
f2037316d3 | ||
|
|
55fe1f0592 | ||
|
|
2453d30970 | ||
|
|
75297a52c1 | ||
|
|
df278222e8 |
59
.github/ISSUE_TEMPLATE/bug-issue.yml
vendored
59
.github/ISSUE_TEMPLATE/bug-issue.yml
vendored
@@ -1,59 +0,0 @@
|
||||
name: 🐞 Bug report
|
||||
description: Report a very clearly broken issue.
|
||||
title: 'bug: <title>'
|
||||
labels: [bug]
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
# ReVanced bug report
|
||||
|
||||
Important to note that your issue may have already been reported before. Please check for existing issues [here](https://github.com/revanced/revanced-integrations/labels/bug).
|
||||
|
||||
- type: dropdown
|
||||
attributes:
|
||||
label: Type
|
||||
options:
|
||||
- Cosmetic
|
||||
- Other
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Bug description
|
||||
description: How did you find the bug? Any additional details that might help?
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Steps to reproduce
|
||||
description: Add the steps to reproduce this bug including your environment.
|
||||
placeholder: Step 1. Download some files. Step 2. ...
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Relevant log output
|
||||
description: Please copy and paste any relevant log output. This will be automatically formatted into code, so no need for backticks.
|
||||
render: shell
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Screenshots or videos
|
||||
description: Add screenshots or videos that show the bug here.
|
||||
placeholder: Drag and drop the screenshots/videos into this box.
|
||||
validations:
|
||||
required: false
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Solution
|
||||
description: If applicable, add a possible solution.
|
||||
validations:
|
||||
required: false
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Additional context
|
||||
description: Add additional context here.
|
||||
validations:
|
||||
required: false
|
||||
109
.github/ISSUE_TEMPLATE/bug-report.yml
vendored
Normal file
109
.github/ISSUE_TEMPLATE/bug-report.yml
vendored
Normal file
@@ -0,0 +1,109 @@
|
||||
name: 🐞 Bug report
|
||||
description: Report a bug or an issue.
|
||||
title: 'bug: '
|
||||
labels: ['Bug report']
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
<p align="center">
|
||||
<picture>
|
||||
<source
|
||||
width="256px"
|
||||
media="(prefers-color-scheme: dark)"
|
||||
srcset="https://raw.githubusercontent.com/revanced/revanced-integrations/main/assets/revanced-headline/revanced-headline-vertical-dark.svg"
|
||||
>
|
||||
<img
|
||||
width="256px"
|
||||
src="https://raw.githubusercontent.com/revanced/revanced-integrations/main/assets/revanced-headline/revanced-headline-vertical-light.svg"
|
||||
>
|
||||
</picture>
|
||||
<br>
|
||||
<a href="https://revanced.app/">
|
||||
<picture>
|
||||
<source height="24px" media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/revanced/revanced-integrations/main/assets/revanced-logo/revanced-logo.svg" />
|
||||
<img height="24px" src="https://raw.githubusercontent.com/revanced/revanced-integrations/main/assets/revanced-logo/revanced-logo.svg" />
|
||||
</picture>
|
||||
</a>
|
||||
<a href="https://github.com/ReVanced">
|
||||
<picture>
|
||||
<source height="24px" media="(prefers-color-scheme: dark)" srcset="https://i.ibb.co/dMMmCrW/Git-Hub-Mark.png" />
|
||||
<img height="24px" src="https://i.ibb.co/9wV3HGF/Git-Hub-Mark-Light.png" />
|
||||
</picture>
|
||||
</a>
|
||||
<a href="http://revanced.app/discord">
|
||||
<picture>
|
||||
<source height="24px" media="(prefers-color-scheme: dark)" srcset="https://user-images.githubusercontent.com/13122796/178032563-d4e084b7-244e-4358-af50-26bde6dd4996.png" />
|
||||
<img height="24px" src="https://user-images.githubusercontent.com/13122796/178032563-d4e084b7-244e-4358-af50-26bde6dd4996.png" />
|
||||
</picture>
|
||||
</a>
|
||||
<a href="https://reddit.com/r/revancedapp">
|
||||
<picture>
|
||||
<source height="24px" media="(prefers-color-scheme: dark)" srcset="https://user-images.githubusercontent.com/13122796/178032351-9d9d5619-8ef7-470a-9eec-2744ece54553.png" />
|
||||
<img height="24px" src="https://user-images.githubusercontent.com/13122796/178032351-9d9d5619-8ef7-470a-9eec-2744ece54553.png" />
|
||||
</picture>
|
||||
</a>
|
||||
<a href="https://t.me/app_revanced">
|
||||
<picture>
|
||||
<source height="24px" media="(prefers-color-scheme: dark)" srcset="https://user-images.githubusercontent.com/13122796/178032213-faf25ab8-0bc3-4a94-a730-b524c96df124.png" />
|
||||
<img height="24px" src="https://user-images.githubusercontent.com/13122796/178032213-faf25ab8-0bc3-4a94-a730-b524c96df124.png" />
|
||||
</picture>
|
||||
</a>
|
||||
<a href="https://x.com/revancedapp">
|
||||
<picture>
|
||||
<source media="(prefers-color-scheme: dark)" srcset="https://user-images.githubusercontent.com/93124920/270180600-7c1b38bf-889b-4d68-bd5e-b9d86f91421a.png">
|
||||
<img height="24px" src="https://user-images.githubusercontent.com/93124920/270108715-d80743fa-b330-4809-b1e6-79fbdc60d09c.png" />
|
||||
</picture>
|
||||
</a>
|
||||
<a href="https://www.youtube.com/@ReVanced">
|
||||
<picture>
|
||||
<source height="24px" media="(prefers-color-scheme: dark)" srcset="https://user-images.githubusercontent.com/13122796/178032714-c51c7492-0666-44ac-99c2-f003a695ab50.png" />
|
||||
<img height="24px" src="https://user-images.githubusercontent.com/13122796/178032714-c51c7492-0666-44ac-99c2-f003a695ab50.png" />
|
||||
</picture>
|
||||
</a>
|
||||
<br>
|
||||
<br>
|
||||
Continuing the legacy of Vanced
|
||||
</p>
|
||||
|
||||
# ReVanced Integrations bug report
|
||||
|
||||
Before creating a new bug report, please keep the following in mind:
|
||||
|
||||
- **Do not submit a duplicate bug report**: You can review existing bug reports [here](https://github.com/ReVanced/revanced-integrations/labels/Bug%20report).
|
||||
- **Do not use the issue page for support**: If you need help or have questions, check out other platforms on [revanced.app](https://revanced.app).
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Bug description
|
||||
description: |
|
||||
- Describe your bug in detail
|
||||
- Add steps to reproduce the bug if possible (Step 1. ... Step 2. ...)
|
||||
- Add images and videos if possible
|
||||
- List used patches if applicable
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Error logs
|
||||
description: Exceptions can be captured by running `logcat | grep AndroidRuntime` in a shell.
|
||||
render: shell
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Solution
|
||||
description: If applicable, add a possible solution to the bug.
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Additional context
|
||||
description: Add additional context here.
|
||||
- type: checkboxes
|
||||
id: acknowledgements
|
||||
attributes:
|
||||
label: Acknowledgements
|
||||
description: Your bug report will be closed if you don't follow the checklist below.
|
||||
options:
|
||||
- label: This issue is not a duplicate of an existing bug report.
|
||||
required: true
|
||||
- label: I have chosen an appropriate title.
|
||||
required: true
|
||||
- label: All requested information has been provided properly.
|
||||
required: true
|
||||
46
.github/ISSUE_TEMPLATE/feature-issue.yml
vendored
46
.github/ISSUE_TEMPLATE/feature-issue.yml
vendored
@@ -1,46 +0,0 @@
|
||||
name: ⭐ Feature request
|
||||
description: Create a detailed feature request.
|
||||
title: 'feat: <title>'
|
||||
labels: [feature-request]
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
# ReVanced feature request
|
||||
|
||||
Do not submit requests for patches here. Please submit them [here](https://github.com/orgs/revanced/discussions/categories/patches) instead.
|
||||
Important to note that your feature request may have already been made before. Please check for existing feature requests [here](https://github.com/revanced/revanced-integrations/labels/feature-request).
|
||||
|
||||
- type: dropdown
|
||||
attributes:
|
||||
label: Type
|
||||
options:
|
||||
- Functionality
|
||||
- Cosmetic
|
||||
- Other
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Issue
|
||||
description: What is the current problem. Why does it require a feature request?
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Feature
|
||||
description: Describe your feature in detail. How does it solve the issue?
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Motivation
|
||||
description: Why should your feature should be considered?
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Additional context
|
||||
description: Add additional context here.
|
||||
validations:
|
||||
required: false
|
||||
105
.github/ISSUE_TEMPLATE/feature-request.yml
vendored
Normal file
105
.github/ISSUE_TEMPLATE/feature-request.yml
vendored
Normal file
@@ -0,0 +1,105 @@
|
||||
name: ⭐ Feature request
|
||||
description: Create a detailed request for a new feature.
|
||||
title: 'feat: '
|
||||
labels: ['Feature request']
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
<p align="center">
|
||||
<picture>
|
||||
<source
|
||||
width="256px"
|
||||
media="(prefers-color-scheme: dark)"
|
||||
srcset="https://raw.githubusercontent.com/revanced/revanced-integrations/main/assets/revanced-headline/revanced-headline-vertical-dark.svg"
|
||||
>
|
||||
<img
|
||||
width="256px"
|
||||
src="https://raw.githubusercontent.com/revanced/revanced-integrations/main/assets/revanced-headline/revanced-headline-vertical-light.svg"
|
||||
>
|
||||
</picture>
|
||||
<br>
|
||||
<a href="https://revanced.app/">
|
||||
<picture>
|
||||
<source height="24px" media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/revanced/revanced-integrations/main/assets/revanced-logo/revanced-logo.svg" />
|
||||
<img height="24px" src="https://raw.githubusercontent.com/revanced/revanced-integrations/main/assets/revanced-logo/revanced-logo.svg" />
|
||||
</picture>
|
||||
</a>
|
||||
<a href="https://github.com/ReVanced">
|
||||
<picture>
|
||||
<source height="24px" media="(prefers-color-scheme: dark)" srcset="https://i.ibb.co/dMMmCrW/Git-Hub-Mark.png" />
|
||||
<img height="24px" src="https://i.ibb.co/9wV3HGF/Git-Hub-Mark-Light.png" />
|
||||
</picture>
|
||||
</a>
|
||||
<a href="http://revanced.app/discord">
|
||||
<picture>
|
||||
<source height="24px" media="(prefers-color-scheme: dark)" srcset="https://user-images.githubusercontent.com/13122796/178032563-d4e084b7-244e-4358-af50-26bde6dd4996.png" />
|
||||
<img height="24px" src="https://user-images.githubusercontent.com/13122796/178032563-d4e084b7-244e-4358-af50-26bde6dd4996.png" />
|
||||
</picture>
|
||||
</a>
|
||||
<a href="https://reddit.com/r/revancedapp">
|
||||
<picture>
|
||||
<source height="24px" media="(prefers-color-scheme: dark)" srcset="https://user-images.githubusercontent.com/13122796/178032351-9d9d5619-8ef7-470a-9eec-2744ece54553.png" />
|
||||
<img height="24px" src="https://user-images.githubusercontent.com/13122796/178032351-9d9d5619-8ef7-470a-9eec-2744ece54553.png" />
|
||||
</picture>
|
||||
</a>
|
||||
<a href="https://t.me/app_revanced">
|
||||
<picture>
|
||||
<source height="24px" media="(prefers-color-scheme: dark)" srcset="https://user-images.githubusercontent.com/13122796/178032213-faf25ab8-0bc3-4a94-a730-b524c96df124.png" />
|
||||
<img height="24px" src="https://user-images.githubusercontent.com/13122796/178032213-faf25ab8-0bc3-4a94-a730-b524c96df124.png" />
|
||||
</picture>
|
||||
</a>
|
||||
<a href="https://x.com/revancedapp">
|
||||
<picture>
|
||||
<source media="(prefers-color-scheme: dark)" srcset="https://user-images.githubusercontent.com/93124920/270180600-7c1b38bf-889b-4d68-bd5e-b9d86f91421a.png">
|
||||
<img height="24px" src="https://user-images.githubusercontent.com/93124920/270108715-d80743fa-b330-4809-b1e6-79fbdc60d09c.png" />
|
||||
</picture>
|
||||
</a>
|
||||
<a href="https://www.youtube.com/@ReVanced">
|
||||
<picture>
|
||||
<source height="24px" media="(prefers-color-scheme: dark)" srcset="https://user-images.githubusercontent.com/13122796/178032714-c51c7492-0666-44ac-99c2-f003a695ab50.png" />
|
||||
<img height="24px" src="https://user-images.githubusercontent.com/13122796/178032714-c51c7492-0666-44ac-99c2-f003a695ab50.png" />
|
||||
</picture>
|
||||
</a>
|
||||
<br>
|
||||
<br>
|
||||
Continuing the legacy of Vanced
|
||||
</p>
|
||||
|
||||
# ReVanced Integrations feature request
|
||||
|
||||
Before creating a new feature request, please keep the following in mind:
|
||||
|
||||
- **Do not submit a duplicate feature request**: You can review existing feature requests [here](https://github.com/ReVanced/revanced-integrations/labels/Feature%20request).
|
||||
- **Do not use the issue page for support**: If you need help or have questions, check out other platforms on [revanced.app](https://revanced.app).
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Feature description
|
||||
description: |
|
||||
- Describe your feature in detail
|
||||
- Add images, videos, links, examples, references, etc. if possible
|
||||
- Add the target application name in case you request a new patch
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Motivation
|
||||
description: |
|
||||
A strong motivation is necessary for a feature request to be considered.
|
||||
|
||||
- Why should this feature be implemented?
|
||||
- What is the explicit use case?
|
||||
- What are the benefits?
|
||||
- What makes this feature important?
|
||||
validations:
|
||||
required: true
|
||||
- type: checkboxes
|
||||
id: acknowledgements
|
||||
attributes:
|
||||
label: Acknowledgements
|
||||
description: Your feature request will be closed if you don't follow the checklist below.
|
||||
options:
|
||||
- label: This issue is not a duplicate of an existing feature request.
|
||||
required: true
|
||||
- label: I have chosen an appropriate title.
|
||||
required: true
|
||||
- label: All requested information has been provided properly.
|
||||
required: true
|
||||
2
.github/config.yml
vendored
2
.github/config.yml
vendored
@@ -1,2 +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.
|
||||
Thank you for contributing to ReVanced. Join us on [Discord](https://revanced.app/discord) to receive a role for your contribution.
|
||||
|
||||
1
.github/workflows/pull_request.yml
vendored
1
.github/workflows/pull_request.yml
vendored
@@ -16,6 +16,7 @@ jobs:
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@v4
|
||||
|
||||
- name: Open pull request
|
||||
uses: repo-sync/pull-request@v2
|
||||
with:
|
||||
|
||||
15
.github/workflows/release.yml
vendored
15
.github/workflows/release.yml
vendored
@@ -23,23 +23,28 @@ jobs:
|
||||
# https://github.com/cycjimmy/semantic-release-action#private-packages
|
||||
persist-credentials: false
|
||||
fetch-depth: 0
|
||||
- name: Cache
|
||||
|
||||
- name: Cache Node modules
|
||||
uses: actions/cache@v3
|
||||
with:
|
||||
path: |
|
||||
${{ runner.home }}/.gradle/caches
|
||||
${{ runner.home }}/.gradle/wrapper
|
||||
.gradle
|
||||
node_modules
|
||||
key: ${{ runner.os }}-gradle-npm-${{ hashFiles('**/*.gradle*', '**/gradle-wrapper.properties', 'package-lock.json') }}
|
||||
key: npm-${{ hashFiles('package-lock.json') }}
|
||||
|
||||
- name: Cache Gradle
|
||||
uses: burrunan/gradle-cache-action@v1
|
||||
|
||||
- name: Setup Java
|
||||
run: echo "JAVA_HOME=$JAVA_HOME_17_X64" >> $GITHUB_ENV
|
||||
|
||||
- name: Build with Gradle
|
||||
env:
|
||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||
run: ./gradlew build clean
|
||||
|
||||
- name: Setup semantic-release
|
||||
run: npm install
|
||||
|
||||
- name: Release
|
||||
env:
|
||||
GITHUB_TOKEN: ${{ secrets.REPOSITORY_PUSH_ACCESS }}
|
||||
|
||||
1
.gitignore
vendored
1
.gitignore
vendored
@@ -14,3 +14,4 @@
|
||||
/.idea
|
||||
/.vscode
|
||||
/*.log
|
||||
node_modules
|
||||
338
CHANGELOG.md
338
CHANGELOG.md
File diff suppressed because it is too large
Load Diff
@@ -42,7 +42,7 @@ android {
|
||||
|
||||
dependencies {
|
||||
compileOnly(project(mapOf("path" to ":dummy")))
|
||||
compileOnly("androidx.annotation:annotation:1.6.0")
|
||||
compileOnly("androidx.annotation:annotation:1.7.0")
|
||||
compileOnly("androidx.appcompat:appcompat:1.7.0-alpha03")
|
||||
compileOnly("com.squareup.okhttp3:okhttp:5.0.0-alpha.11")
|
||||
compileOnly("com.squareup.retrofit2:retrofit:2.9.0")
|
||||
|
||||
@@ -5,6 +5,10 @@ import android.view.WindowManager;
|
||||
|
||||
public class RemoveScreenshotRestrictionPatch {
|
||||
|
||||
public static void addFlags(Window window, int flags) {
|
||||
window.addFlags(flags & ~WindowManager.LayoutParams.FLAG_SECURE);
|
||||
}
|
||||
|
||||
public static void setFlags(Window window, int flags, int mask) {
|
||||
window.setFlags(flags & ~WindowManager.LayoutParams.FLAG_SECURE, mask & ~WindowManager.LayoutParams.FLAG_SECURE);
|
||||
}
|
||||
|
||||
@@ -4,14 +4,14 @@ import android.view.MotionEvent;
|
||||
import android.view.VelocityTracker;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public final class DisableFineScrubbingGesturePatch {
|
||||
public final class DisablePreciseSeekingGesturePatch {
|
||||
/**
|
||||
* Disables the fine scrubbing gesture.
|
||||
* Disables the gesture that is used to seek precisely.
|
||||
* @param tracker The velocity tracker that is used to determine the gesture.
|
||||
* @param event The motion event that is used to determine the gesture.
|
||||
*/
|
||||
public static void disableGesture(VelocityTracker tracker, MotionEvent event) {
|
||||
if (SettingsEnum.DISABLE_FINE_SCRUBBING_GESTURE.getBoolean()) return;
|
||||
if (SettingsEnum.DISABLE_PRECISE_SEEKING_GESTURE.getBoolean()) return;
|
||||
|
||||
tracker.addMovement(event);
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
/** @noinspection unused*/
|
||||
public class DisableResumingStartupShortsPlayerPatch {
|
||||
|
||||
/**
|
||||
* Injection point.
|
||||
*/
|
||||
public static boolean disableResumingStartupShortsPlayer() {
|
||||
return SettingsEnum.DISABLE_RESUMING_SHORTS_PLAYER.getBoolean();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public class DisableRollingNumberAnimationsPatch {
|
||||
/**
|
||||
* Injection point.
|
||||
*/
|
||||
public static boolean disableRollingNumberAnimations() {
|
||||
return SettingsEnum.DISABLE_ROLLING_NUMBER_ANIMATIONS.getBoolean();
|
||||
}
|
||||
}
|
||||
@@ -1,10 +0,0 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
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_RESUMING_SHORTS_PLAYER.getBoolean();
|
||||
}
|
||||
}
|
||||
@@ -1,13 +1,30 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import android.annotation.SuppressLint;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.ImageView;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
/** @noinspection unused*/
|
||||
public final class DisableSuggestedVideoEndScreenPatch {
|
||||
public static void closeEndScreen(ImageView imageView) {
|
||||
@SuppressLint("StaticFieldLeak")
|
||||
private static View lastView;
|
||||
|
||||
public static void closeEndScreen(final ImageView imageView) {
|
||||
if (!SettingsEnum.DISABLE_SUGGESTED_VIDEO_END_SCREEN.getBoolean()) return;
|
||||
|
||||
imageView.performClick();
|
||||
// Get a parent view which can be listened to for layout changes.
|
||||
final var parent = imageView.getParent().getParent();
|
||||
|
||||
// Prevent adding the listener multiple times.
|
||||
if (lastView == parent) return;
|
||||
|
||||
lastView = (ViewGroup)parent;
|
||||
lastView.addOnLayoutChangeListener((v, left, top, right, bottom, oldLeft, oldTop, oldRight, oldBottom) -> {
|
||||
// Disable sound effects to prevent the click sound.
|
||||
imageView.setSoundEffectsEnabled(false);
|
||||
imageView.performClick();
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,74 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import android.app.SearchManager;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.net.Uri;
|
||||
import android.os.Build;
|
||||
import androidx.annotation.RequiresApi;
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
import java.util.Objects;
|
||||
|
||||
import static app.revanced.integrations.utils.StringRef.str;
|
||||
|
||||
/**
|
||||
* @noinspection unused
|
||||
*/
|
||||
public class GmsCoreSupport {
|
||||
private static final String GMS_CORE_PACKAGE_NAME
|
||||
= getGmsCoreVendor() + ".android.gms";
|
||||
private static final String DONT_KILL_MY_APP_LINK
|
||||
= "https://dontkillmyapp.com";
|
||||
private static final Uri GMS_CORE_PROVIDER
|
||||
= Uri.parse("content://" + getGmsCoreVendor() + ".android.gsf.gservices/prefix");
|
||||
|
||||
private static void search(Context context, String uriString, String message) {
|
||||
ReVancedUtils.showToastLong(message);
|
||||
|
||||
var intent = new Intent(Intent.ACTION_WEB_SEARCH);
|
||||
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
|
||||
intent.putExtra(SearchManager.QUERY, uriString);
|
||||
context.startActivity(intent);
|
||||
}
|
||||
|
||||
@RequiresApi(api = Build.VERSION_CODES.N)
|
||||
public static void checkAvailability() {
|
||||
var context = Objects.requireNonNull(ReVancedUtils.getContext());
|
||||
|
||||
try {
|
||||
context.getPackageManager().getPackageInfo(GMS_CORE_PACKAGE_NAME, PackageManager.GET_ACTIVITIES);
|
||||
} catch (PackageManager.NameNotFoundException exception) {
|
||||
LogHelper.printInfo(() -> "GmsCore was not found", exception);
|
||||
search(context, getGmsCoreDownloadLink(), str("gms_core_not_installed_warning"));
|
||||
|
||||
// Gracefully exit the app, so it does not crash.
|
||||
System.exit(0);
|
||||
}
|
||||
|
||||
try (var client = context.getContentResolver().acquireContentProviderClient(GMS_CORE_PROVIDER)) {
|
||||
if (client != null) return;
|
||||
LogHelper.printInfo(() -> "GmsCore is not running in the background");
|
||||
search(context, DONT_KILL_MY_APP_LINK, str("gms_core_not_running_warning"));
|
||||
}
|
||||
}
|
||||
|
||||
private static String getGmsCoreDownloadLink() {
|
||||
final var vendor = getGmsCoreVendor();
|
||||
switch (vendor) {
|
||||
case "com.mgoogle":
|
||||
return "https://github.com/TeamVanced/VancedMicroG/releases/latest";
|
||||
case "app.revanced":
|
||||
return "https://github.com/revanced/gmscore/releases/latest";
|
||||
default:
|
||||
return vendor + ".android.gms";
|
||||
}
|
||||
}
|
||||
|
||||
// Modified by a patch. Do not touch.
|
||||
private static String getGmsCoreVendor() {
|
||||
return "app.revanced";
|
||||
}
|
||||
}
|
||||
@@ -2,28 +2,27 @@ package app.revanced.integrations.patches;
|
||||
|
||||
import android.view.View;
|
||||
|
||||
import app.revanced.integrations.patches.spoof.SpoofAppVersionPatch;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
public class HideBreakingNewsPatch {
|
||||
|
||||
/**
|
||||
* When spoofing to app versions older than 17.30.35, the watch history preview bar uses
|
||||
* When spoofing to app versions 17.31.00 and older, 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;
|
||||
}
|
||||
private static final boolean isSpoofingOldVersionWithHorizontalCardListWatchHistory =
|
||||
SpoofAppVersionPatch.isSpoofingToEqualOrLessThan("17.31.00");
|
||||
|
||||
/**
|
||||
* Injection point.
|
||||
*/
|
||||
public static void hideBreakingNews(View view) {
|
||||
if (!SettingsEnum.HIDE_BREAKING_NEWS.getBoolean()
|
||||
|| isSpoofingOldVersionWithHorizontalCardListWatchHistory()) return;
|
||||
|| isSpoofingOldVersionWithHorizontalCardListWatchHistory) return;
|
||||
ReVancedUtils.hideViewByLayoutParams(view);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,53 +0,0 @@
|
||||
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;
|
||||
import android.net.Uri;
|
||||
|
||||
import java.util.Objects;
|
||||
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
import app.revanced.integrations.utils.ReVancedUtils;
|
||||
|
||||
public class MicroGSupport {
|
||||
private static final String MICROG_VENDOR = "com.mgoogle";
|
||||
private static final String MICROG_PACKAGE_NAME = MICROG_VENDOR + ".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://" + MICROG_VENDOR + ".android.gsf.gservices/prefix");
|
||||
|
||||
private static void startIntent(Context context, String uriString, String message) {
|
||||
ReVancedUtils.showToastLong(message);
|
||||
|
||||
var intent = new Intent(Intent.ACTION_VIEW);
|
||||
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
|
||||
intent.setData(Uri.parse(uriString));
|
||||
context.startActivity(intent);
|
||||
}
|
||||
|
||||
@TargetApi(26)
|
||||
public static void checkAvailability() {
|
||||
var context = Objects.requireNonNull(ReVancedUtils.getContext());
|
||||
|
||||
try {
|
||||
context.getPackageManager().getPackageInfo(MICROG_PACKAGE_NAME, PackageManager.GET_ACTIVITIES);
|
||||
} catch (PackageManager.NameNotFoundException exception) {
|
||||
LogHelper.printInfo(() -> "Vanced MicroG was not found", exception);
|
||||
startIntent(context, VANCED_MICROG_DOWNLOAD_LINK, str("microg_not_installed_warning"));
|
||||
|
||||
// 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,16 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public final class RemoveTrackingQueryParameterPatch {
|
||||
private static final String NEW_TRACKING_PARAMETER_REGEX = ".si=.+";
|
||||
private static final String OLD_TRACKING_PARAMETER_REGEX = ".feature=.+";
|
||||
|
||||
public static String sanitize(String url) {
|
||||
if (!SettingsEnum.REMOVE_TRACKING_QUERY_PARAMETER.getBoolean()) return url;
|
||||
|
||||
return url
|
||||
.replaceAll(NEW_TRACKING_PARAMETER_REGEX, "")
|
||||
.replaceAll(OLD_TRACKING_PARAMETER_REGEX, "");
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
public final class RestoreOldSeekbarThumbnailsPatch {
|
||||
public static boolean useFullscreenSeekbarThumbnails() {
|
||||
return !SettingsEnum.RESTORE_OLD_SEEKBAR_THUMBNAILS.getBoolean();
|
||||
}
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,9 @@
|
||||
package app.revanced.integrations.patches;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
public final class SlideToSeekPatch {
|
||||
public static boolean isSlideToSeekDisabled() {
|
||||
return !SettingsEnum.SLIDE_TO_SEEK.getBoolean();
|
||||
}
|
||||
}
|
||||
@@ -12,10 +12,15 @@ import java.util.Objects;
|
||||
|
||||
/**
|
||||
* Hooking class for the current playing video.
|
||||
* @noinspection unused
|
||||
*/
|
||||
public final class VideoInformation {
|
||||
private static final float DEFAULT_YOUTUBE_PLAYBACK_SPEED = 1.0f;
|
||||
private static final String SEEK_METHOD_NAME = "seekTo";
|
||||
/**
|
||||
* Prefix present in all Short player parameters signature.
|
||||
*/
|
||||
private static final String SHORTS_PLAYER_PARAMETERS = "8AEB";
|
||||
|
||||
private static WeakReference<Object> playerControllerRef;
|
||||
private static Method seekMethod;
|
||||
@@ -27,6 +32,7 @@ public final class VideoInformation {
|
||||
|
||||
@NonNull
|
||||
private static volatile String playerResponseVideoId = "";
|
||||
private static volatile boolean videoIdIsShort;
|
||||
|
||||
/**
|
||||
* The current playback speed
|
||||
@@ -64,12 +70,33 @@ public final class VideoInformation {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @return If the player parameters are for a Short.
|
||||
*/
|
||||
public static boolean playerParametersAreShort(@NonNull String parameters) {
|
||||
return parameters.startsWith(SHORTS_PLAYER_PARAMETERS);
|
||||
}
|
||||
|
||||
/**
|
||||
* Injection point.
|
||||
*/
|
||||
public static String newPlayerResponseSignature(@NonNull String signature, boolean isShortAndOpeningOrPlaying) {
|
||||
final boolean isShort = playerParametersAreShort(signature);
|
||||
if (!isShort || isShortAndOpeningOrPlaying) {
|
||||
if (videoIdIsShort != isShort) {
|
||||
videoIdIsShort = isShort;
|
||||
LogHelper.printDebug(() -> "videoIdIsShort: " + isShort);
|
||||
}
|
||||
}
|
||||
return signature; // Return the original value since we are observing and not modifying.
|
||||
}
|
||||
|
||||
/**
|
||||
* Injection point. Called off the main thread.
|
||||
*
|
||||
* @param videoId The id of the last video loaded.
|
||||
*/
|
||||
public static void setPlayerResponseVideoId(@NonNull String videoId, boolean videoIsOpeningOrPlaying) {
|
||||
public static void setPlayerResponseVideoId(@NonNull String videoId, boolean isShortAndOpeningOrPlaying) {
|
||||
if (!playerResponseVideoId.equals(videoId)) {
|
||||
LogHelper.printDebug(() -> "New player response video id: " + videoId);
|
||||
playerResponseVideoId = videoId;
|
||||
@@ -89,7 +116,7 @@ public final class VideoInformation {
|
||||
|
||||
/**
|
||||
* Overrides the current playback speed.
|
||||
*
|
||||
* <p>
|
||||
* <b> Used exclusively by {@link RememberPlaybackSpeedPatch} </b>
|
||||
*/
|
||||
public static void overridePlaybackSpeed(float speedOverride) {
|
||||
@@ -124,32 +151,39 @@ public final class VideoInformation {
|
||||
/**
|
||||
* Seek on the current video.
|
||||
* Does not function for playback of Shorts.
|
||||
*
|
||||
* <p>
|
||||
* Caution: If called from a videoTimeHook() callback,
|
||||
* this will cause a recursive call into the same videoTimeHook() callback.
|
||||
*
|
||||
* @param millisecond The millisecond to seek the video to.
|
||||
* @return if the seek was successful
|
||||
* @return true if the seek was successful.
|
||||
*/
|
||||
public static boolean seekTo(final long millisecond) {
|
||||
final long videoLength = getVideoLength();
|
||||
|
||||
// Prevent issues such as play/ pause button or autoplay not working.
|
||||
final long seekToMilliseconds = Math.min(millisecond, VideoInformation.getVideoLength() - 250);
|
||||
|
||||
ReVancedUtils.verifyOnMainThread();
|
||||
try {
|
||||
LogHelper.printDebug(() -> "Seeking to " + millisecond);
|
||||
return (Boolean) seekMethod.invoke(playerControllerRef.get(), millisecond);
|
||||
LogHelper.printDebug(() -> "Seeking to " + seekToMilliseconds);
|
||||
//noinspection DataFlowIssue
|
||||
return (Boolean) seekMethod.invoke(playerControllerRef.get(), seekToMilliseconds);
|
||||
} catch (Exception ex) {
|
||||
LogHelper.printException(() -> "Failed to seek", ex);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/** @noinspection UnusedReturnValue*/
|
||||
public static boolean seekToRelative(long millisecondsRelative) {
|
||||
return seekTo(videoTime + millisecondsRelative);
|
||||
}
|
||||
|
||||
/**
|
||||
* Id of the current video playing. Includes Shorts.
|
||||
* Id of the last video opened. Includes Shorts.
|
||||
*
|
||||
* @return The id of the video. Empty string if not set yet.
|
||||
* @return The id of the video, or an empty string if no videos have been opened yet.
|
||||
*/
|
||||
@NonNull
|
||||
public static String getVideoId() {
|
||||
@@ -158,20 +192,30 @@ public final class VideoInformation {
|
||||
|
||||
/**
|
||||
* Differs from {@link #videoId} as this is the video id for the
|
||||
* last player response received, which may not be the current video playing.
|
||||
*
|
||||
* last player response received, which may not be the last video opened.
|
||||
* <p>
|
||||
* If Shorts are loading the background, this commonly will be
|
||||
* different from the Short that is currently on screen.
|
||||
*
|
||||
* <p>
|
||||
* For most use cases, you should instead use {@link #getVideoId()}.
|
||||
*
|
||||
* @return The id of the last video loaded. Empty string if not set yet.
|
||||
* @return The id of the last video loaded, or an empty string if no videos have been loaded yet.
|
||||
*/
|
||||
@NonNull
|
||||
public static String getPlayerResponseVideoId() {
|
||||
return playerResponseVideoId;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return If the last player response video id _that was opened_ was a Short.
|
||||
* <p>
|
||||
* Note: This value returned may not match the status of {@link #getPlayerResponseVideoId()}
|
||||
* since that includes player responses for videos not opened.
|
||||
*/
|
||||
public static boolean lastVideoIdIsShort() {
|
||||
return videoIdIsShort;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return The current playback speed.
|
||||
*/
|
||||
@@ -192,9 +236,9 @@ public final class VideoInformation {
|
||||
|
||||
/**
|
||||
* Playback time of the current video playing. Includes Shorts.
|
||||
*
|
||||
* <p>
|
||||
* Value will lag behind the actual playback time by a variable amount based on the playback speed.
|
||||
*
|
||||
* <p>
|
||||
* If playback speed is 2.0x, this value may be up to 2000ms behind the actual playback time.
|
||||
* If playback speed is 1.0x, this value may be up to 1000ms behind the actual playback time.
|
||||
* If playback speed is 0.5x, this value may be up to 500ms behind the actual playback time.
|
||||
@@ -208,12 +252,12 @@ public final class VideoInformation {
|
||||
|
||||
/**
|
||||
* @return If the playback is at the end of the video.
|
||||
*
|
||||
* <p>
|
||||
* If video is playing in the background with no video visible,
|
||||
* this always returns false (even if the video is actually at the end).
|
||||
*
|
||||
* <p>
|
||||
* This is equivalent to checking for {@link VideoState#ENDED},
|
||||
* but can give a more up to date result for code calling from some hooks.
|
||||
* but can give a more up-to-date result for code calling from some hooks.
|
||||
*
|
||||
* @see VideoState
|
||||
*/
|
||||
|
||||
@@ -12,6 +12,7 @@ import app.revanced.integrations.utils.StringTrieSearch;
|
||||
|
||||
public final class AdsFilter extends Filter {
|
||||
private final StringTrieSearch exceptions = new StringTrieSearch();
|
||||
private final StringFilterGroup shoppingLinks;
|
||||
|
||||
public AdsFilter() {
|
||||
exceptions.addPatterns(
|
||||
@@ -71,6 +72,11 @@ public final class AdsFilter extends Filter {
|
||||
"products_in_video"
|
||||
);
|
||||
|
||||
shoppingLinks = new StringFilterGroup(
|
||||
SettingsEnum.HIDE_SHOPPING_LINKS,
|
||||
"expandable_list"
|
||||
);
|
||||
|
||||
final var webLinkPanel = new StringFilterGroup(
|
||||
SettingsEnum.HIDE_WEB_SEARCH_RESULTS,
|
||||
"web_link_panel"
|
||||
@@ -93,6 +99,7 @@ public final class AdsFilter extends Filter {
|
||||
viewProducts,
|
||||
selfSponsor,
|
||||
webLinkPanel,
|
||||
shoppingLinks,
|
||||
movieAds
|
||||
);
|
||||
this.identifierFilterGroupList.addAll(carouselAd);
|
||||
@@ -104,6 +111,10 @@ public final class AdsFilter extends Filter {
|
||||
if (exceptions.matches(path))
|
||||
return false;
|
||||
|
||||
// Check for the index because of likelihood of false positives.
|
||||
if (matchedGroup == shoppingLinks && matchedIndex != 0)
|
||||
return false;
|
||||
|
||||
return super.isFiltered(identifier, path, protobufBufferArray, matchedList, matchedGroup, matchedIndex);
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,69 @@
|
||||
package app.revanced.integrations.patches.components;
|
||||
|
||||
import androidx.annotation.Nullable;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.StringTrieSearch;
|
||||
|
||||
final class DescriptionComponentsFilter extends Filter {
|
||||
|
||||
private final StringTrieSearch exceptions = new StringTrieSearch();
|
||||
|
||||
public DescriptionComponentsFilter() {
|
||||
exceptions.addPatterns(
|
||||
"compact_channel",
|
||||
"description",
|
||||
"grid_video",
|
||||
"inline_expander",
|
||||
"metadata"
|
||||
);
|
||||
|
||||
final StringFilterGroup chapterSection = new StringFilterGroup(
|
||||
SettingsEnum.HIDE_CHAPTERS,
|
||||
"macro_markers_carousel"
|
||||
);
|
||||
|
||||
final StringFilterGroup infoCardsSection = new StringFilterGroup(
|
||||
SettingsEnum.HIDE_INFO_CARDS_SECTION,
|
||||
"infocards_section"
|
||||
);
|
||||
|
||||
final StringFilterGroup gameSection = new StringFilterGroup(
|
||||
SettingsEnum.HIDE_GAME_SECTION,
|
||||
"gaming_section"
|
||||
);
|
||||
|
||||
final StringFilterGroup musicSection = new StringFilterGroup(
|
||||
SettingsEnum.HIDE_MUSIC_SECTION,
|
||||
"music_section",
|
||||
"video_attributes_section"
|
||||
);
|
||||
|
||||
final StringFilterGroup podcastSection = new StringFilterGroup(
|
||||
SettingsEnum.HIDE_PODCAST_SECTION,
|
||||
"playlist_section"
|
||||
);
|
||||
|
||||
final StringFilterGroup transcriptSection = new StringFilterGroup(
|
||||
SettingsEnum.HIDE_TRANSCIPT_SECTION,
|
||||
"transcript_section"
|
||||
);
|
||||
|
||||
pathFilterGroupList.addAll(
|
||||
chapterSection,
|
||||
infoCardsSection,
|
||||
gameSection,
|
||||
musicSection,
|
||||
podcastSection,
|
||||
transcriptSection
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
boolean isFiltered(@Nullable String identifier, String path, byte[] protobufBufferArray,
|
||||
FilterGroupList matchedList, FilterGroup matchedGroup, int matchedIndex) {
|
||||
if (exceptions.matches(path)) return false;
|
||||
|
||||
return super.isFiltered(path, identifier, protobufBufferArray, matchedList, matchedGroup, matchedIndex);
|
||||
}
|
||||
}
|
||||
@@ -2,10 +2,8 @@ package app.revanced.integrations.patches.components;
|
||||
|
||||
|
||||
import android.os.Build;
|
||||
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.annotation.RequiresApi;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.utils.LogHelper;
|
||||
import app.revanced.integrations.utils.StringTrieSearch;
|
||||
@@ -13,6 +11,11 @@ import app.revanced.integrations.utils.StringTrieSearch;
|
||||
@RequiresApi(api = Build.VERSION_CODES.N)
|
||||
public final class LayoutComponentsFilter extends Filter {
|
||||
private final StringTrieSearch exceptions = new StringTrieSearch();
|
||||
private static final StringTrieSearch mixPlaylistsExceptions = new StringTrieSearch();
|
||||
private static final ByteArrayAsStringFilterGroup mixPlaylistsExceptions2 = new ByteArrayAsStringFilterGroup(
|
||||
null,
|
||||
"cell_description_body"
|
||||
);
|
||||
private final CustomFilterGroup custom;
|
||||
|
||||
private static final ByteArrayAsStringFilterGroup mixPlaylists = new ByteArrayAsStringFilterGroup(
|
||||
@@ -24,6 +27,13 @@ public final class LayoutComponentsFilter extends Filter {
|
||||
private final StringFilterGroup notifyMe;
|
||||
private final StringFilterGroup expandableMetadata;
|
||||
|
||||
static {
|
||||
mixPlaylistsExceptions.addPatterns(
|
||||
"V.ED", // Playlist browse id.
|
||||
"java.lang.ref.WeakReference"
|
||||
);
|
||||
}
|
||||
|
||||
@RequiresApi(api = Build.VERSION_CODES.N)
|
||||
public LayoutComponentsFilter() {
|
||||
exceptions.addPatterns(
|
||||
@@ -125,11 +135,6 @@ public final class LayoutComponentsFilter extends Filter {
|
||||
"quality_sheet_footer"
|
||||
);
|
||||
|
||||
final var chapters = new StringFilterGroup(
|
||||
SettingsEnum.HIDE_CHAPTERS,
|
||||
"macro_markers_carousel"
|
||||
);
|
||||
|
||||
final var channelBar = new StringFilterGroup(
|
||||
SettingsEnum.HIDE_CHANNEL_BAR,
|
||||
"channel_bar"
|
||||
@@ -186,6 +191,11 @@ public final class LayoutComponentsFilter extends Filter {
|
||||
"featured_channel_watermark_overlay"
|
||||
);
|
||||
|
||||
final var forYouShelf = new StringFilterGroup(
|
||||
SettingsEnum.HIDE_FOR_YOU_SHELF,
|
||||
"mixed_content_shelf"
|
||||
);
|
||||
|
||||
this.pathFilterGroupList.addAll(
|
||||
channelBar,
|
||||
communityPosts,
|
||||
@@ -210,13 +220,13 @@ public final class LayoutComponentsFilter extends Filter {
|
||||
timedReactions,
|
||||
imageShelf,
|
||||
channelMemberShelf,
|
||||
forYouShelf,
|
||||
custom
|
||||
);
|
||||
|
||||
this.identifierFilterGroupList.addAll(
|
||||
graySeparator,
|
||||
chipsShelf,
|
||||
chapters
|
||||
chipsShelf
|
||||
);
|
||||
}
|
||||
|
||||
@@ -238,18 +248,29 @@ public final class LayoutComponentsFilter extends Filter {
|
||||
return super.isFiltered(identifier, path, protobufBufferArray, matchedList, matchedGroup, matchedIndex);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Injection point.
|
||||
* Called from a different place then the other filters.
|
||||
*/
|
||||
public static boolean filterMixPlaylists(final byte[] bytes) {
|
||||
final boolean isMixPlaylistFiltered = mixPlaylists.check(bytes).isFiltered();
|
||||
public static boolean filterMixPlaylists(final Object conversionContext, @Nullable final byte[] bytes) {
|
||||
if (bytes == null) {
|
||||
LogHelper.printDebug(() -> "bytes is null");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (isMixPlaylistFiltered)
|
||||
LogHelper.printDebug(() -> "Filtered mix playlist");
|
||||
// Prevent playlist items being hidden, if a mix playlist is present in it.
|
||||
if (mixPlaylistsExceptions.matches(conversionContext.toString()))
|
||||
return false;
|
||||
|
||||
return isMixPlaylistFiltered;
|
||||
if (!mixPlaylists.check(bytes).isFiltered())
|
||||
return false;
|
||||
|
||||
// Prevent hiding the description of some videos accidentally.
|
||||
if (mixPlaylistsExceptions2.check(bytes).isFiltered())
|
||||
return false;
|
||||
|
||||
LogHelper.printDebug(() -> "Filtered mix playlist");
|
||||
return true;
|
||||
}
|
||||
|
||||
public static boolean showWatermark() {
|
||||
|
||||
@@ -490,9 +490,15 @@ public final class LithoFilterPatch {
|
||||
|
||||
ByteBuffer protobufBuffer = bufferThreadLocal.get();
|
||||
if (protobufBuffer == null) {
|
||||
LogHelper.printException(() -> "Proto buffer is null"); // Should never happen
|
||||
LogHelper.printException(() -> "Proto buffer is null"); // Should never happen.
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!protobufBuffer.hasArray()) {
|
||||
LogHelper.printDebug(() -> "Proto buffer does not have an array");
|
||||
return false;
|
||||
}
|
||||
|
||||
LithoFilterParameters parameter = new LithoFilterParameters(lithoIdentifier, pathBuilder, protobufBuffer);
|
||||
LogHelper.printDebug(() -> "Searching " + parameter);
|
||||
|
||||
|
||||
@@ -2,7 +2,11 @@ package app.revanced.integrations.patches.components;
|
||||
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
// Abuse LithoFilter for CustomPlaybackSpeedPatch.
|
||||
import app.revanced.integrations.patches.playback.speed.CustomPlaybackSpeedPatch;
|
||||
|
||||
/**
|
||||
* Abuse LithoFilter for {@link CustomPlaybackSpeedPatch}.
|
||||
*/
|
||||
public final class PlaybackSpeedMenuFilterPatch extends Filter {
|
||||
// Must be volatile or synchronized, as litho filtering runs off main thread and this field is then access from the main thread.
|
||||
public static volatile boolean isPlaybackSpeedMenuVisible;
|
||||
|
||||
@@ -6,26 +6,38 @@ import androidx.annotation.Nullable;
|
||||
import androidx.annotation.RequiresApi;
|
||||
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
import app.revanced.integrations.shared.PlayerType;
|
||||
|
||||
public class PlayerFlyoutMenuItemsFilter extends Filter {
|
||||
|
||||
// Search the buffer only if the flyout menu identifier is found.
|
||||
// Search the buffer only if the flyout menu path is found.
|
||||
// Handle the searching in this class instead of adding to the global filter group (which searches all the time)
|
||||
private final ByteArrayFilterGroupList flyoutFilterGroupList = new ByteArrayFilterGroupList();
|
||||
|
||||
private final ByteArrayFilterGroup exception;
|
||||
|
||||
@RequiresApi(api = Build.VERSION_CODES.N)
|
||||
public PlayerFlyoutMenuItemsFilter() {
|
||||
identifierFilterGroupList.addAll(new StringFilterGroup(null, "overflow_menu_item.eml|"));
|
||||
exception = new ByteArrayAsStringFilterGroup(
|
||||
// Whitelist Quality menu item when "Hide Additional settings menu" is enabled
|
||||
SettingsEnum.HIDE_ADDITIONAL_SETTINGS_MENU,
|
||||
"quality_sheet"
|
||||
);
|
||||
|
||||
// Using pathFilterGroupList due to new flyout panel(A/B)
|
||||
pathFilterGroupList.addAll(
|
||||
new StringFilterGroup(null, "overflow_menu_item.eml|")
|
||||
);
|
||||
|
||||
flyoutFilterGroupList.addAll(
|
||||
new ByteArrayAsStringFilterGroup(
|
||||
SettingsEnum.HIDE_QUALITY_MENU,
|
||||
"yt_outline_gear"
|
||||
),
|
||||
new ByteArrayAsStringFilterGroup(
|
||||
SettingsEnum.HIDE_CAPTIONS_MENU,
|
||||
"closed_caption"
|
||||
),
|
||||
new ByteArrayAsStringFilterGroup(
|
||||
SettingsEnum.HIDE_ADDITIONAL_SETTINGS_MENU,
|
||||
"yt_outline_gear"
|
||||
),
|
||||
new ByteArrayAsStringFilterGroup(
|
||||
SettingsEnum.HIDE_LOOP_VIDEO_MENU,
|
||||
"yt_outline_arrow_repeat_1_"
|
||||
@@ -64,6 +76,10 @@ public class PlayerFlyoutMenuItemsFilter extends Filter {
|
||||
@Override
|
||||
boolean isFiltered(@Nullable String identifier, String path, byte[] protobufBufferArray,
|
||||
FilterGroupList matchedList, FilterGroup matchedGroup, int matchedIndex) {
|
||||
// Shorts also use this player flyout panel
|
||||
if (PlayerType.getCurrent().isNoneOrHidden() || exception.check(protobufBufferArray).isFiltered())
|
||||
return false;
|
||||
|
||||
// Only 1 group is added to the parent class, so the matched group must be the overflow menu.
|
||||
if (matchedIndex == 0 && flyoutFilterGroupList.check(protobufBufferArray).isFiltered()) {
|
||||
// Super class handles logging.
|
||||
|
||||
@@ -53,14 +53,14 @@ public final class ReturnYouTubeDislikeFilterPatch extends Filter {
|
||||
/**
|
||||
* Injection point.
|
||||
*/
|
||||
public static void newPlayerResponseVideoId(String videoId, boolean videoIsOpeningOrPlaying) {
|
||||
public static void newPlayerResponseVideoId(String videoId, boolean isShortAndOpeningOrPlaying) {
|
||||
try {
|
||||
if (!videoIsOpeningOrPlaying || !SettingsEnum.RYD_SHORTS.getBoolean()) {
|
||||
if (!isShortAndOpeningOrPlaying || !SettingsEnum.RYD_SHORTS.getBoolean()) {
|
||||
return;
|
||||
}
|
||||
synchronized (lastVideoIds) {
|
||||
if (lastVideoIds.put(videoId, Boolean.TRUE) == null) {
|
||||
LogHelper.printDebug(() -> "New video id: " + videoId);
|
||||
LogHelper.printDebug(() -> "New Short video id: " + videoId);
|
||||
}
|
||||
}
|
||||
} catch (Exception ex) {
|
||||
@@ -93,7 +93,7 @@ public final class ReturnYouTubeDislikeFilterPatch extends Filter {
|
||||
// Must pass a null id to correctly clear out the current video data.
|
||||
// Otherwise if a Short is opened in non-incognito, then incognito is enabled and another Short is opened,
|
||||
// the new incognito Short will show the old prior data.
|
||||
ReturnYouTubeDislikePatch.newVideoLoaded(matchedVideoId, true);
|
||||
ReturnYouTubeDislikePatch.setLastLithoShortsVideoId(matchedVideoId);
|
||||
}
|
||||
|
||||
return false;
|
||||
|
||||
@@ -2,16 +2,19 @@ package app.revanced.integrations.patches.components;
|
||||
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
import app.revanced.integrations.patches.playback.quality.RestoreOldVideoQualityMenuPatch;
|
||||
import app.revanced.integrations.settings.SettingsEnum;
|
||||
|
||||
// Abuse LithoFilter for OldVideoQualityMenuPatch.
|
||||
/**
|
||||
* Abuse LithoFilter for {@link RestoreOldVideoQualityMenuPatch}.
|
||||
*/
|
||||
public final class VideoQualityMenuFilterPatch extends Filter {
|
||||
// Must be volatile or synchronized, as litho filtering runs off main thread and this field is then access from the main thread.
|
||||
public static volatile boolean isVideoQualityMenuVisible;
|
||||
|
||||
public VideoQualityMenuFilterPatch() {
|
||||
pathFilterGroupList.addAll(new StringFilterGroup(
|
||||
SettingsEnum.SHOW_OLD_VIDEO_QUALITY_MENU,
|
||||
SettingsEnum.RESTORE_OLD_VIDEO_QUALITY_MENU,
|
||||
"quick_quality_sheet_content.eml-js"
|
||||
));
|
||||
}
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user