Skip to content
This repository has been archived by the owner on Oct 26, 2024. It is now read-only.

Commit

Permalink
chore: Merge branch dev to main (#559)
Browse files Browse the repository at this point in the history
  • Loading branch information
oSumAtrIX authored Feb 5, 2024
2 parents 192faf0 + ba3e602 commit 2634552
Show file tree
Hide file tree
Showing 14 changed files with 369 additions and 135 deletions.
28 changes: 28 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,31 @@
# [1.3.0-dev.1](https://github.com/ReVanced/revanced-integrations/compare/v1.2.2-dev.3...v1.3.0-dev.1) (2024-02-02)


### Features

* **YouTube - Custom filter:** Custom filtering of the protocol buffer ([#562](https://github.com/ReVanced/revanced-integrations/issues/562)) ([0eb7f3f](https://github.com/ReVanced/revanced-integrations/commit/0eb7f3f3af99bf6566526f9c48db2248d93e166c))

## [1.2.2-dev.3](https://github.com/ReVanced/revanced-integrations/compare/v1.2.2-dev.2...v1.2.2-dev.3) (2024-01-31)


### Bug Fixes

* **TikTok:** Add missing settings strings ([#561](https://github.com/ReVanced/revanced-integrations/issues/561)) ([04621f8](https://github.com/ReVanced/revanced-integrations/commit/04621f8a36490df0b35a3940ecc1fbebd6ee287f))

## [1.2.2-dev.2](https://github.com/ReVanced/revanced-integrations/compare/v1.2.2-dev.1...v1.2.2-dev.2) (2024-01-29)


### Bug Fixes

* **YouTube - ReturnYouTubeDislike:** Do not show more than 1 connection toasts if the API is broken ([#560](https://github.com/ReVanced/revanced-integrations/issues/560)) ([2c73209](https://github.com/ReVanced/revanced-integrations/commit/2c7320937adc01221017c740b86c4d6851c96797))

## [1.2.2-dev.1](https://github.com/ReVanced/revanced-integrations/compare/v1.2.1...v1.2.2-dev.1) (2024-01-28)


### Bug Fixes

* **YouTube:** Correctly show channel page on tablet devices ([#558](https://github.com/ReVanced/revanced-integrations/issues/558)) ([d0edafb](https://github.com/ReVanced/revanced-integrations/commit/d0edafb1afc7b87a8eeb085a9e48dc2d20af2f3a))

## [1.2.1](https://github.com/ReVanced/revanced-integrations/compare/v1.2.0...v1.2.1) (2024-01-28)


Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -97,7 +97,7 @@ public static List<Setting<?>> allLoadedSettings() {
@NonNull
private static List<Setting<?>> allLoadedSettingsSorted() {
Collections.sort(SETTINGS, (Setting<?> o1, Setting<?> o2) -> o1.key.compareTo(o2.key));
return Collections.unmodifiableList(SETTINGS);
return allLoadedSettings();
}

/**
Expand Down Expand Up @@ -131,6 +131,7 @@ private static List<Setting<?>> allLoadedSettingsSorted() {

/**
* Confirmation message to display, if the user tries to change the setting from the default value.
* Currently this works only for Boolean setting types.
*/
@Nullable
public final StringRef userDialogMessage;
Expand Down Expand Up @@ -206,10 +207,9 @@ public Setting(@NonNull String key,
/**
* Migrate a setting value if the path is renamed but otherwise the old and new settings are identical.
*/
public static void migrateOldSettingToNew(@NonNull Setting<?> oldSetting, @NonNull Setting newSetting) {
public static <T> void migrateOldSettingToNew(@NonNull Setting<T> oldSetting, @NonNull Setting<T> newSetting) {
if (!oldSetting.isSetToDefault()) {
Logger.printInfo(() -> "Migrating old setting value: " + oldSetting + " into replacement setting: " + newSetting);
//noinspection unchecked
newSetting.save(oldSetting.value);
oldSetting.resetToDefault();
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@
import android.os.Bundle;
import android.preference.*;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;

import app.revanced.integrations.shared.Logger;
import app.revanced.integrations.shared.Utils;
import app.revanced.integrations.shared.settings.BooleanSetting;
Expand All @@ -25,6 +27,13 @@ public abstract class AbstractPreferenceFragment extends PreferenceFragment {
*/
public static boolean settingImportInProgress;

/**
* Confirm and restart dialog button text and title.
* Set by subclasses if Strings cannot be added as a resource.
*/
@Nullable
protected static String restartDialogButtonText, restartDialogTitle, confirmDialogTitle;

/**
* Used to prevent showing reboot dialog, if user cancels a setting user dialog.
*/
Expand Down Expand Up @@ -80,11 +89,15 @@ protected void initialize() {
}

private void showSettingUserDialogConfirmation(SwitchPreference switchPref, BooleanSetting setting) {
final var context = getContext();
Utils.verifyOnMainThread();

final var context = getContext();
if (confirmDialogTitle == null) {
confirmDialogTitle = str("revanced_settings_confirm_user_dialog_title");
}
showingUserDialogMessage = true;
new AlertDialog.Builder(context)
.setTitle(str("revanced_settings_confirm_user_dialog_title"))
.setTitle(confirmDialogTitle)
.setMessage(setting.userDialogMessage.toString())
.setPositiveButton(android.R.string.ok, (dialog, id) -> {
if (setting.rebootApp) {
Expand Down Expand Up @@ -201,12 +214,17 @@ protected void updateListPreferenceSummary(ListPreference listPreference, Settin
}

public static void showRestartDialog(@NonNull final Context context) {
String positiveButton = str("revanced_settings_restart");

new AlertDialog.Builder(context).setMessage(str("revanced_settings_restart_title"))
.setPositiveButton(positiveButton, (dialog, id) -> {
Utils.restartApp(context);
})
Utils.verifyOnMainThread();
if (restartDialogTitle == null) {
restartDialogTitle = str("revanced_settings_restart_title");
}
if (restartDialogButtonText == null) {
restartDialogButtonText = str("revanced_settings_restart");
}
new AlertDialog.Builder(context)
.setMessage(restartDialogTitle)
.setPositiveButton(restartDialogButtonText, (dialog, id)
-> Utils.restartApp(context))
.setNegativeButton(android.R.string.cancel, null)
.setCancelable(false)
.show();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,12 @@ public class ReVancedPreferenceFragment extends AbstractPreferenceFragment {
protected void initialize() {
final var context = getContext();

// Currently no resources can be compiled for TikTok (fails with aapt error).
// So all TikTok Strings are hard coded in integrations.
restartDialogTitle = "Refresh and restart";
restartDialogButtonText = "Restart";
confirmDialogTitle = "Do you wish to proceed?";

PreferenceScreen preferenceScreen = getPreferenceManager().createPreferenceScreen(context);
setPreferenceScreen(preferenceScreen);

Expand Down
76 changes: 43 additions & 33 deletions app/src/main/java/app/revanced/integrations/youtube/TrieSearch.java
Original file line number Diff line number Diff line change
Expand Up @@ -231,47 +231,57 @@ private static int hashIndexForTableSize(int arraySize, char nodeValue) {
}

/**
* This method is static and uses a loop to avoid all recursion.
* This is done for performance since the JVM does not do tail recursion optimization.
*
* @param startNode Node to start the search from.
* @param searchText Text to search for patterns in.
* @param searchTextLength Length of the search text.
* @param searchTextIndex Current recursive search text index. Also, the end index of the current pattern match.
* @param currentMatchLength current search depth, and also the length of the current pattern match.
* @return If any pattern matches, and it's associated callback halted the search.
*/
private boolean matches(T searchText, int searchTextLength, int searchTextIndex, int currentMatchLength,
Object callbackParameter) {
if (leaf != null && leaf.matches(this,
searchText, searchTextLength, searchTextIndex, callbackParameter)) {
return true; // Leaf exists and it matched the search text.
}
if (endOfPatternCallback != null) {
final int matchStartIndex = searchTextIndex - currentMatchLength;
for (@Nullable TriePatternMatchedCallback<T> callback : endOfPatternCallback) {
if (callback == null) {
return true; // No callback and all matches are valid.
}
if (callback.patternMatched(searchText, matchStartIndex, currentMatchLength, callbackParameter)) {
return true; // Callback confirmed the match.
private static <T> boolean matches(final TrieNode<T> startNode, final T searchText, final int searchTextLength,
int searchTextIndex, final Object callbackParameter) {
TrieNode<T> node = startNode;
int currentMatchLength = 0;

while (true) {
TrieCompressedPath<T> leaf = node.leaf;
if (leaf != null && leaf.matches(node, searchText, searchTextLength, searchTextIndex, callbackParameter)) {
return true; // Leaf exists and it matched the search text.
}
List<TriePatternMatchedCallback<T>> endOfPatternCallback = node.endOfPatternCallback;
if (endOfPatternCallback != null) {
final int matchStartIndex = searchTextIndex - currentMatchLength;
for (@Nullable TriePatternMatchedCallback<T> callback : endOfPatternCallback) {
if (callback == null) {
return true; // No callback and all matches are valid.
}
if (callback.patternMatched(searchText, matchStartIndex, currentMatchLength, callbackParameter)) {
return true; // Callback confirmed the match.
}
}
}
}
if (children == null) {
return false; // Reached a graph end point and there's no further patterns to search.
}
if (searchTextIndex == searchTextLength) {
return false; // Reached end of the search text and found no matches.
}
TrieNode<T>[] children = node.children;
if (children == null) {
return false; // Reached a graph end point and there's no further patterns to search.
}
if (searchTextIndex == searchTextLength) {
return false; // Reached end of the search text and found no matches.
}

final char character = getCharValue(searchText, searchTextIndex);
if (isInvalidRange(character)) {
return false; // Not an ASCII letter/number/symbol.
}
final int arrayIndex = hashIndexForTableSize(children.length, character);
TrieNode<T> child = children[arrayIndex];
if (child == null || child.nodeValue != character) {
return false;
// Use the start node to reduce VM method lookup, since all nodes are the same class type.
final char character = startNode.getCharValue(searchText, searchTextIndex);
final int arrayIndex = hashIndexForTableSize(children.length, character);
TrieNode<T> child = children[arrayIndex];
if (child == null || child.nodeValue != character) {
return false;
}

node = child;
searchTextIndex++;
currentMatchLength++;
}
return child.matches(searchText, searchTextLength, searchTextIndex + 1,
currentMatchLength + 1, callbackParameter);
}

/**
Expand Down Expand Up @@ -388,7 +398,7 @@ private boolean matches(@NonNull T textToSearch, int textToSearchLength, int sta
return false; // No patterns were added.
}
for (int i = startIndex; i < endIndex; i++) {
if (root.matches(textToSearch, endIndex, i, 0, callbackParameter)) return true;
if (TrieNode.matches(root, textToSearch, endIndex, i, callbackParameter)) return true;
}
return false;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
import app.revanced.integrations.youtube.patches.components.ReturnYouTubeDislikeFilterPatch;
import app.revanced.integrations.youtube.patches.spoof.SpoofAppVersionPatch;
import app.revanced.integrations.youtube.returnyoutubedislike.ReturnYouTubeDislike;
import app.revanced.integrations.youtube.returnyoutubedislike.requests.ReturnYouTubeDislikeApi;
import app.revanced.integrations.youtube.settings.Settings;
import app.revanced.integrations.youtube.shared.PlayerType;
import app.revanced.integrations.shared.Logger;
Expand All @@ -21,7 +22,6 @@
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import java.util.concurrent.atomic.AtomicReference;

import static app.revanced.integrations.youtube.returnyoutubedislike.ReturnYouTubeDislike.Vote;

Expand Down Expand Up @@ -70,17 +70,16 @@ public class ReturnYouTubeDislikePatch {
private static volatile boolean lithoShortsShouldUseCurrentData;

/**
* Last video id prefetched. Field is prevent prefetching the same video id multiple times in a row.
* Last video id prefetched. Field is to prevent prefetching the same video id multiple times in a row.
*/
@Nullable
private static volatile String lastPrefetchedVideoId;

public static void onRYDStatusChange(boolean rydEnabled) {
if (!rydEnabled) {
// Must remove all values to protect against using stale data
// if the user enables RYD while a video is on screen.
clearData();
}
ReturnYouTubeDislikeApi.resetRateLimits();
// Must remove all values to protect against using stale data
// if the user enables RYD while a video is on screen.
clearData();
}

private static void clearData() {
Expand Down Expand Up @@ -240,10 +239,6 @@ private static CharSequence onLithoTextLoaded(@NonNull Object conversionContext,
}
replacement = videoData.getDislikesSpanForRegularVideo((Spanned) original,
true, isRollingNumber);

// When spoofing between 17.09.xx and 17.30.xx the UI is the old layout
// but uses litho and the dislikes is "|dislike_button.eml|".
// But spoofing to that range gives a broken UI layout so no point checking for that.
} else if (!isRollingNumber && conversionContextString.contains("|shorts_dislike_button.eml|")) {
// Litho Shorts player.
if (!Settings.RYD_SHORTS.get()) {
Expand Down Expand Up @@ -300,9 +295,10 @@ public static String onRollingNumberLoaded(@NonNull Object conversionContext,
@NonNull String original) {
try {
CharSequence replacement = onLithoTextLoaded(conversionContext, original, true);
if (!replacement.toString().equals(original)) {
String replacementString = replacement.toString();
if (!replacementString.equals(original)) {
rollingNumberSpan = replacement;
return replacement.toString();
return replacementString;
} // Else, the text was not a likes count but instead the view count or something else.
} catch (Exception ex) {
Logger.printException(() -> "onRollingNumberLoaded failure", ex);
Expand Down Expand Up @@ -348,9 +344,8 @@ private static void addRollingNumberPatchChanges(TextView view) {
} else {
view.setCompoundDrawables(separator, null, null, null);
}
// Liking/disliking can cause the span to grow in size,
// which is ok and is laid out correctly,
// but if the user then undoes their action the layout will not remove the extra padding.
// Disliking can cause the span to grow in size, which is ok and is laid out correctly,
// but if the user then removes their dislike the layout will not adjust to the new shorter width.
// Use a center alignment to take up any extra space.
view.setTextAlignment(View.TEXT_ALIGNMENT_CENTER);
// Single line mode does not clip words if the span is larger than the view bounds.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,8 @@

@SuppressWarnings("unused")
public final class WideSearchbarPatch {
public static boolean enableWideSearchbar() {
return Settings.WIDE_SEARCHBAR.get();

public static boolean enableWideSearchbar(boolean original) {
return Settings.WIDE_SEARCHBAR.get() || original;
}
}
Loading

0 comments on commit 2634552

Please sign in to comment.